/* Multiple Choice Game
 *
 * Start with:
 * game = new MultiChoiceGame();
 * jutils.AddEventListener(window, 'load', function(e) {
 * 	game.Initiate();
 * }, false);
 * 
 * @dependency: /jutils/util.js - Fisher-Yates, DebugUtil
 */

/*****************************************
 * FlashCard
 *****************************************/	
	function FlashCard() {};
	FlashCard.prototype.id=-1;
	FlashCard.prototype.kanji='';
	FlashCard.prototype.kana='';
	FlashCard.prototype.roomaji='';
	FlashCard.prototype.english='';
	FlashCard.prototype.image='';
	FlashCard.prototype.jsound='';
	FlashCard.prototype.examplej='';
	FlashCard.prototype.examplee='';
	FlashCard.prototype.exampleimg='';
	FlashCard.prototype.comment='';
	FlashCard.prototype.isAnswer=false;

/*****************************************
 * Util Classes
 *****************************************/	

/* Parse the strings returned from Python framework, return date */
function SJDate() {}; 
SJDate.Parse = function (p_DateString) {
 return p_DateString.split("T")[0]; 
}
	function CountDownPanel(p_frame,p_element) {

			this.frameObj = new Element('div', {id: '_ctFrame'});
			this.countObj  = new Element('div', {id: '_ctCounter'});

			this.countObj.setStyles({
				'vertical-align':'middle',
				'margin-top':'50px',
				'margin-left':'auto',
				'margin-right':'auto'
			});
			this.frameObj.setStyles({
				'text-align':'center',
				'position':'absolute',
				'z-index':'999',
				'top':'0',
				'left':'0',
				'width':'100%',
				'height':'100%',
				'font-size':'100px'
			});

			this.frameObj.injectInside($(document.body));			
			this.countObj.injectInside(this.frameObj);			
		};

		CountDownPanel.prototype.delay = 1000;
		CountDownPanel.prototype.ticks = 3;
		CountDownPanel.prototype.texts = ['スタート','一','二','三','四','五'];
		CountDownPanel.prototype.Tick = function() {
				if(typeof(this.texts[this.ticks])!='undefined') {
					this.countObj.innerHTML = this.texts[this.ticks];
				} else {
					this.countObj.innerHTML = this.ticks;
				}		
				if(this.ticks>0) {
					mt=this;
					setTimeout(function(){mt.Tick();},1000);
					
					this.countObj.set('morph',{'font-size':0,
																			'unit':'em',
																			'transition':'bounce:out'
					});
					this.frameObj.set('morph',{
																		'color':"#090",
																		'border-color':"#040",
																		'opacity':0
																		});
					this.frameObj.morph({'color':['#000','#FFF'],'background-color':['#FFF','#F90']});
					this.countObj.morph({'font-size':[0,2]});
					this.ticks--;
				} else {
					m_thisCounter = this;
					this.countObj.set('morph',{'font-size':0,
																			'unit':'em',
																			'duration':500,
																			'transition':'bounce:out'
					});
					this.frameObj.set('morph',{
						'link':'chain',
						'color':"#090",
						'opacity':0,
						'duration':500,
						onChainComplete: function(){ 
							m_thisCounter.frameObj.dispose();
							m_thisCounter.frameObj.dispose();
							if(typeof(m_thisCounter.onComplete)=='function')m_thisCounter.onComplete();
						}
					});
					this.countObj.morph({'font-size':[0,1]});
					this.frameObj.morph({'color':['#000','#FFF'],'background-color':['#FFF','#090']}).morph({'opacity':99});
			};
		};
					 	 
/*****************************************
 * Multiple Choice Game
 *
 * @dependency: /jutils/util.js - Fisher-Yates, DebugUtil
 *****************************************/	
	function MultiChoiceGame() {};

	MultiChoiceGame.prototype.timeCountAlive = true;
	MultiChoiceGame.prototype.leftSet = Array();
	MultiChoiceGame.prototype.stats = Array();
	MultiChoiceGame.prototype.currentQuestions = Array();
	MultiChoiceGame.prototype.currentAnswer = Array();
	MultiChoiceGame.prototype.gameStartTS = null;
	MultiChoiceGame.prototype.gameEndTS = null;
	MultiChoiceGame.prototype.currentCardStartTS = Array();
	MultiChoiceGame.prototype.lastCardPassTime = Array();

	MultiChoiceGame.prototype.points = 0;
	MultiChoiceGame.prototype.username = "";
	MultiChoiceGame.prototype.timerInterval = 100;

	MultiChoiceGame.prototype.currentGame = 
	{
		gameID : null,
		originalSet : Array(),
		gameHighScore : 0
	};
	MultiChoiceGame.prototype.myScores = [];

	// User answer stats	
	MultiChoiceGame.prototype.answersCorrect = Array();
	MultiChoiceGame.prototype.answersWrong = Array();

	MultiChoiceGame.prototype.settings = {
		"useCardTimer": true,
		"useSounds" : true,
		"randomizeTemplate" : true,
		"cardTimeout":5, // seconds
		"alternatives":4
	};

	// Where to show a field - binary pattern
	// 0 = none, 1=question, 2=answer button, (not implemented: 4=answer commentary)
	MultiChoiceGame.prototype.templateConfig = {
		"kanji"		:1,
		"kana"		:1,
		"roomaji"	:2,
		"english"	:4,
		"image"		:4,
		"jsound"	:4,
		"examplej"	:4,
		"examplee"	:4,
		"exampleimg":4,
		"comment"	:4,
		"sod"		:4  /*stroke order diagram */
	};
	MultiChoiceGame.prototype.templateConfigExample = new Object();
	MultiChoiceGame.prototype.templateConfigExample.kanaToRoomaji = {
		"kanji"		:0,
		"kana"		:1,
		"roomaji"	:2,
		"english"	:0,
		"image"		:0,
		"jsound"	:0,
		"examplej"	:0,
		"examplee"	:0,
		"exampleimg":0,
		"comment"	:4,
		"sod"		:4
	};
	MultiChoiceGame.prototype.templateConfigExample.imageToKana = {
		"kanji"		:0,
		"kana"		:4,
		"roomaji"	:2,
		"english"	:0,
		"image"		:1,
		"jsound"	:0,
		"examplej"	:0,
		"examplee"	:0,
		"exampleimg":0,
		"comment"	:4,
		"sod"		:4
	};
	MultiChoiceGame.prototype.templateConfigExample.roomajiToKana = {
		"kanji"		:0,
		"kana"		:2,
		"roomaji"	:1,
		"english"	:0,
		"image"		:0,
		"jsound"	:0,
		"examplej"	:0,
		"examplee"	:0,
		"exampleimg":0,
		"comment"	:4,
		"sod"		:4
	};

	MultiChoiceGame.prototype.Initiate = function() {
		// Stop timer if started.
		this.timeCountAlive = false;
		this.points = 0;

		$('startpanel').setStyle('display', 'block');
		$('statspanel').setStyle('display', 'none');
		$('endpanel').setStyle('display', 'none');
		$('gamepanel').setStyle('display', 'none');
		this.ShowMessage("");


		if(this.username=="") {
			$('pnlNotLoggedIn_hiragana1').setStyle('display', 'block');
			$('pnlNotLoggedIn_katakana1').setStyle('display', 'block');
		} else {
			$('pnlNotLoggedIn_hiragana1').setStyle('display', 'none');
			$('pnlNotLoggedIn_katakana1').setStyle('display', 'none');
		}

/*		if(this.username!="") {
			this.GetHighScorePersonal("hiragana1",'pnlMyHighScore_hiragana1');
			this.GetHighScorePersonal("katakana1",'pnlMyHighScore_katakana1');
		}

		this.GetHighScoreToday("hiragana1",'highScoresToday_hiragana1');
		this.GetHighScoreAllTime("hiragana1",'highScoresAllTime_hiragana1');
		this.GetHighScoreToday("katakana1",'highScoresToday_katakana1');
		this.GetHighScoreAllTime("katakana1",'highScoresAllTime_katakana1');		
*/
	};

	MultiChoiceGame.prototype.GetAnswerKeyEvent = function(event){
	    //The passed event parameter is already an instance of the Event class.
		evt = new Event(event); // mootools Event class

		//$("header").innerHTML="key:"+evt.key;

	    switch(evt.key)
		{
			case "1":
				game.Answer(0);
				break;
			case "2":
				game.Answer(1);
				break;
			case "3":
				game.Answer(2);
				break;
			case "4":
				game.Answer(3);
				break;	
			case "5":
				game.Answer(4);
				break;	
			default:
				//alert("Key without function");
		}	
	};

	MultiChoiceGame.prototype.StartGame = function(p_gameChoice) {
		this.ShowMessage("");
		
		graphutils.HideElement("startpanel");
		graphutils.ShowElement("statspanel");
		graphutils.HideElement("endpanel");

		//$("myHighScoreMarker").setStyle("visibility","hidden");
		//$("gameHighScoreMarker").setStyle("visibility","hidden");
	
		var thisobj = this;
		document.addEvent('keydown', thisobj.GetAnswerKeyEvent);

		this.timeCountAlive = true;
		this.answersCorrect = Array();
		this.answersWrong = Array();
		
		this.Load(p_gameChoice);		
		
		this.leftSet = this.currentGame.originalSet.slice(); // value copy of array


		// Count down and start game
		var multiChoiceGame = this;
		cdp = new CountDownPanel();
		cdp.onComplete = function() {
			// Set timer and load first card
			graphutils.ShowElement("gamepanel");
			multiChoiceGame.gameStartTS = new Date();
			multiChoiceGame.PrepareNext();
			multiChoiceGame.UpdateTime();
		};
		cdp.Tick();

	};
	
	MultiChoiceGame.prototype.Load = function(p_set) {
		this.LoadGame("./" + p_set + ".json");
	};
	
	MultiChoiceGame.prototype.PrepareNext = function() {
		if(this.leftSet.length==0) {
			this.EndGame();
		} else {
			// Timestamp card time
			this.currentCardStartTS = new Date();
			this.currentCardPauseTS = this.currentCardStartTS;

			this.UpdateStats();

			this.ClearQuestionaire();
			this.RandomizeTemplate();
			this.BuildQuestionaire();
			this.PrintOut();
		}
		cp.SetCompleteness(100,false);
	};
	
	MultiChoiceGame.prototype.EndGame = function(isForced) {
		this.gameEndTS = new Date();		
		this.timeCountAlive = false;
		
		var thisobj = this;
		document.removeEvent('keydown', thisobj.GetAnswerKeyEvent);

		graphutils.HideElement("gamepanel");
		graphutils.HideElement("startpanel");
		graphutils.ShowElement("endpanel");
		graphutils.HideElement("statspanel");
		this.ShowMessage("");

		if($defined(isForced) && isForced) {
			$("endmessage").innerHTML = "Game exited.";
		} else {
			$("endmessage").innerHTML = "Congratulations, you have now finished the whole set!";
			
			// Get user's current session max score
			var myMaxScoreOnGame = 0;
			var myScoresOnGame = this.myScores[this.currentGame.gameID];
			if(myScoresOnGame) {
				for(ix=0;ix<myScoresOnGame.length;ix++){
					myMaxScoreOnGame = Math.max(myMaxScoreOnGame,myScoresOnGame[ix])
				}
			} 
			if(!this.myScores[this.currentGame.gameID])
			{
				this.myScores[this.currentGame.gameID] = []; 
			}
			this.myScores[this.currentGame.gameID].push(this.points);
			if(this.points > myMaxScoreOnGame && $defined($("myHighScore_"+this.currentGame.gameID)) ) {
				this.currentGame.myHighScore = Math.max(this.points,this.currentGame.myHighScore);
				$("myHighScore_"+this.currentGame.gameID).innerHTML = this.points;
			};

			// Submit score to server online
			this.SubmitScore(this.username, this.currentGame.gameID, this.points);
		}
	};

	 /** Take an index of the current question and evaluate if it is right */
	MultiChoiceGame.prototype.Answer = function(alt) {
		var pctAtAnswer = this.cardTimeLeftPct;
		var msg="";
	
		if(alt==null) {
			// Missed card
			this.answersWrong.push(this.currentAnswer);
			msg = "<span class='msgWrongAnswer'>Timeout! It should have been: "+this.currentAnswer.kana + " = "+ this.currentAnswer.roomaji + "</span>";
			this.ShowMessage(msg,'#FF6666');
		} else if(typeof(alt)!="number" || alt>=this.currentQuestions[length]) {
			alert("MultiChoiceGame.Answer: Error. Alternative not available");
		} else {
			var rightAnswer = this.currentQuestions[alt].isAnswer;
			if(rightAnswer) {
				this.points += pctAtAnswer;

				this.answersCorrect.push(this.currentAnswer);
				msg = "<span class='msgRightAnswer'>Right!</span>";
				this.ShowMessage(msg,'#66FF66');
			} else {
				this.answersWrong.push(this.currentAnswer);
				msg = "<span class='msgWrongAnswer'>Wrong! It should have been: "+this.currentAnswer.kana + " = "+ this.currentAnswer.roomaji + "</span>";
				//msg = "<span class='msgWrongAnswer'>Wrong! You said: "+this.currentQuestions[alt].kana + " = "+ this.currentQuestions[alt].roomaji + ". Please try again!</span>";
				this.ShowMessage(msg,'#FF6666');
				
				// make available points less.
			}
		}
	
		this.UpdateStats();
	
//		if(alt==null || rightAnswer) {
			// Timestamp card time
			this.lastCardPassTime = new Date(this.currentCardStartTS-new Date());
			this.PrepareNext();
//		}
	};

	MultiChoiceGame.prototype.SubmitScore = function(p_username,p_gameID,p_score) {
		if(p_username=="") {
			return;
		};
		var m_url = "http://scores.studyjapanese.org/scores/"+ p_gameID +"/";
		var thisObj = this;
		new JsonP(m_url, {
		    data: {
					'action': "POST",
					'name': p_username,
					'score': p_score
		    },
		    onComplete: function(p_response){
					// sit back and enjoy
				}
		}).request();		
	};

	MultiChoiceGame.prototype.GetHighScorePersonal = function(p_game, p_targetTagID) {
		var m_url = "http://scores.studyjapanese.org/scores/"+p_game+"/?name="+this.username+"&count=3";
		var m_msgNoScores = "<em>Be the first to score today!</em>";
		var m_highScores = null;

		new JsonP(m_url, {
		    onComplete: function(p_response){
					var m_output = "";
					m_highScores = p_response.data.scores;
					if(!$defined(m_highScores) || m_highScores.length==0) {
						m_output += m_msgNoScores;
					} else {
						m_output += "<table>";
						for(ix=0;ix<m_highScores.length;ix++) {
							var m_dateStr = SJDate.Parse(m_highScores[ix].date);
							m_output +="<tr><td class='label'>"+m_dateStr+":</td> <td class='datafield'>"+m_highScores[ix].score+"</td></tr>";
						};
						m_output += "</table>";
					};
					$(p_targetTagID).innerHTML = m_output;
				}
		}).request();
	};

	
	MultiChoiceGame.prototype.GetHighScoreToday = function(p_game, p_targetTagID) {
		var m_url = "http://scores.studyjapanese.org/scores/"+p_game+"/?distinct=1&interval=24&count=5&";
		var m_msgNoScores = "<em>Be the first to score today!</em>";
		var m_highScores = null;

		new JsonP(m_url, {
		    onComplete: function(p_response){
				var m_output = "";
				m_highScores = p_response.data.scores;
				if(!$defined(m_highScores) || m_highScores.length==0) {
					m_output += m_msgNoScores;
				} else {
					m_output += "<table>";
					for(ix=0;ix<m_highScores.length;ix++) {
						var userlink = "<a href='/component/comprofiler/userprofile/"+m_highScores[ix].name+"' target='_blank' title='User profile'>"+m_highScores[ix].name+"</a>";
						 m_output +="<tr><td class='label'>"+userlink+":</td> <td class='datafield'>"+m_highScores[ix].score+"</td></tr>";
					};
					m_output += "</table>";
				};
				$(p_targetTagID).innerHTML = m_output;
			}
		}).request();
	};
	
	MultiChoiceGame.prototype.GetHighScoreAllTime = function(p_game, p_targetTagID) {
		var m_url = "http://scores.studyjapanese.org/scores/"+p_game+"/?distinct=1&count=5&";
		var m_msgNoScores = "<em>Be the first to make a high score!</em>";
		var m_highScores = null;

		new JsonP(m_url, {
		    onComplete: function(p_response){
				var m_output = "";
				m_highScores = p_response.data.scores;
				if(!$defined(m_highScores) || m_highScores.length==0) {
					m_output += m_msgNoScores;
				} else {
					m_output += "<table>";
					for(ix=0;ix<m_highScores.length;ix++) {
						var userlink = "<a href='/component/comprofiler/userprofile/"+m_highScores[ix].name+"' target='_blank' title='User profile'>"+m_highScores[ix].name+"</a>";
						 m_output +="<tr><td class='label'>"+userlink+":</td> <td class='datafield'>"+m_highScores[ix].score+"</td></tr>";
					};
					m_output += "</table>";
				};
				$(p_targetTagID).innerHTML = m_output;
			}
		}).request();
	};

	/**
	 * settingID: the setting parameter to toggle - this.settings.SETTINGID
	 * labelText : array of ["text when false", "text when true"]
	 * domOutputID : the domID for the element to print out the text in
	 */
	MultiChoiceGame.prototype.ToggleSetting = function(settingID,labelText,domOutputID) {
		if(this.settings[settingID]) {
			this.settings[settingID]=!this.settings[settingID];
			//$(domOutputID).innerHTML = labelText[0];
			graphutils.ReplaceInnerHtml(domOutputID,labelText[0]);
		} else {
			this.settings[settingID]=!this.settings[settingID];
			//$(domOutputID).innerHTML = labelText[1];
			graphutils.ReplaceInnerHtml(domOutputID,labelText[1]);
		}
	}

	MultiChoiceGame.prototype.PauseGame = function() {
		game.ToggleSetting('useCardTimer',['Off','On'],'timerToggle');	
	
		if(this.settings.useCardTimer) {
			this.ShowMessage("Timer resumed.");
			this.currentCardStartTS = new Date() - (this.currentCardPauseTS - this.currentCardStartTS);
			this.UpdateTime();
		}  else {
			this.ShowMessage("Timer paused.");
			this.currentCardPauseTS = new Date();		
			this.RedrawTime();
		}
	};

	MultiChoiceGame.prototype.UpdateTime = function() {
		var gameTime = new Date(new Date() - this.gameStartTS);
		var cardTime = new Date(new Date() - this.currentCardStartTS);
		var output = "";
		var cardTimeLeft = 0;

		if(!this.settings.useCardTimer) {
			return;
		}
		if(this.settings.cardTimeout>0 && this.timeCountAlive && this.settings.useCardTimer) {
			cardTimeLeft = this.settings.cardTimeout - (cardTime.getMinutes()*60 + cardTime.getSeconds() + cardTime.getMilliseconds()/1000);
			cardTimeLeft = (cardTimeLeft<=0)?0:cardTimeLeft;
			if(cardTimeLeft<=0) {
				// time out answer
				this.Answer(null);
			}
		}
		
		this.cardTimeLeftPct = Math.floor((cardTimeLeft/this.settings.cardTimeout)*100);
		cp.SetCompleteness(this.cardTimeLeftPct);
		
		this.RedrawTime();
		if(this.timeCountAlive) {
			var thisObj = this;
			window.setTimeout(function() { thisObj.UpdateTime(); }, this.timerInterval);		
		}
	};

	MultiChoiceGame.prototype.RedrawTime = function() {
		var gameTime = new Date(new Date() - this.gameStartTS);
		var cardTime = new Date(new Date() - this.currentCardStartTS);
		var output = "";
		var cardTimeLeft = 0;
	
		output +=   "<span class='label'>Time since start:</span> " + gameTime.getMinutes() + " m " + gameTime.getSeconds() + " s </br>\n";
	
		if(this.settings.cardTimeout>0 && this.timeCountAlive && this.settings.useCardTimer) {
			cardTimeLeft = this.settings.cardTimeout - (cardTime.getMinutes()*60 + cardTime.getSeconds() + cardTime.getMilliseconds()/1000);
			cardTimeLeft = (cardTimeLeft<=0)?0:cardTimeLeft;
			output +=   "<span class='label'>Time left on this card:</span> " 
						+ Math.floor((cardTimeLeft/this.settings.cardTimeout)*100) + " % </br></br>\n";

		}

		graphutils.ReplaceInnerHtml("timepanel",output);		
	};


	MultiChoiceGame.prototype.UpdateStats = function() {
		var output = "";
		var nroRight = this.answersCorrect.length;
		var nroWrong = this.answersWrong.length;
		var nroTotal = this.currentGame.originalSet.length;
		var wordsLeft = this.leftSet.length;
		var successRatio = nroWrong==0?100:Math.floor(nroRight/(nroRight+nroWrong)*100);
		var pctTaken = Math.floor((nroTotal-nroWrong)/nroTotal*100);

		$("nroRight").innerHTML = nroRight;
		$("nroWrong").innerHTML = nroWrong;
		$("wordsLeft").innerHTML = wordsLeft;		
		$("points").innerHTML = this.points;		
		$("endPoints").innerHTML = this.points;		

		//pb.SetCompleteness(successRatio);
	
		// Print stats	
		// TODO: print out TD even if field is empty...
		output += "<table style='width:95%'><tr>"
				+"<td style='width:50%;'><h4 style='color:#060;'>Correct</h4>";
		output += "<table>";
		for(i=0;i<this.answersCorrect.length;i++) {
			output += "<tr>";
			if(this.templateConfig.kanji&3 && this.answersCorrect[i].kanji) {
				output += "<td class='kanji'>"+this.answersCorrect[i].kanji + "</td>";
			}
			if(this.templateConfig.kana&3 && this.answersCorrect[i].kana) {
				output += "<td class='kana'>"+this.answersCorrect[i].kana+ "</td>";
			}
			if(this.templateConfig.roomaji&3 && this.answersCorrect[i].roomaji) {
				output += "<td class='roomaji'>"+this.answersCorrect[i].roomaji+ "</td>";
			}
			if(this.templateConfig.english&3 && this.answersCorrect[i].english) {
				output += "<td class='english'>"+this.answersCorrect[i].english+ "</td>";
			}			
			output += "</tr>";
		}
		output += "</table></td>";
		output += "<td style='width:50%;'><h4 style='color:#600;'>Wrong </h4>";
		output += "<table>";
		for(i=0;i<this.answersWrong.length;i++) {
			output += "<tr>";
			if(this.templateConfig.kanji&3 && this.answersWrong[i].kanji) {
				output += "<td class='kanji'>"+this.answersWrong[i].kanji + "</td>";
			}
			if(this.templateConfig.kana&3 && this.answersWrong[i].kana) {
				output += "<td class='kana'>"+this.answersWrong[i].kana+ "</td>";
			}
			if(this.templateConfig.roomaji&3 && this.answersWrong[i].roomaji) {
				output += "<td class='roomaji'>"+this.answersWrong[i].roomaji+ "</td>";
			}
			if(this.templateConfig.english&3 && this.answersWrong[i].english) {
				output += "<td class='english'>"+this.answersWrong[i].english+ "</td>";
			}			
			output += "</tr>";
		}
		output += "</table></td></tr></table>";
		graphutils.ReplaceInnerHtml("answerstats",output);
	};

	MultiChoiceGame.prototype.BuildQuestionaire = function() {
		var nroAlternatives = this.settings.alternatives;
		var fake = new Array();
		var taken = "";
	
		this.currentAnswer = this.leftSet.pop();
		this.currentAnswer.isAnswer = true;
	
		taken = ":"+this.currentAnswer.id+":";

		for(i=0;i<nroAlternatives && i+1<this.currentGame.originalSet.length;i++) {
			fake[i] = this.GetRandom(this.currentGame.originalSet);	
			while(taken.indexOf(":"+fake[i].id+":")>=0) {
				fake[i] = this.GetRandom(this.currentGame.originalSet);	
			}
			fake[i].isAnswer=false; // mark fake;
			taken += ":"+fake[i].id+":";
		
			//debugUtil.trace("this.originalSet.length:"+this.currentGame.originalSet.length);
		}

		// Add correct answer and fakes to alternatives
		alternatives = fake;
		alternatives.push(this.currentAnswer);

		// Randomize answers		
	  	jutils.FisherYates(alternatives);
  
	  	this.currentQuestions = alternatives;	  
	};

	MultiChoiceGame.prototype.ClearQuestionaire = function() {
		var o_answerList = document.getElementById('answerlist');
		o_answerList.innerHTML = "";
	};

	MultiChoiceGame.prototype.PrintOut = function() {
		var o_question = document.getElementById('question');
		var output = "";
		if(this.templateConfig.kanji&1 && this.currentAnswer.kanji) {
			output += "<span class='kanji'>"+this.currentAnswer.kanji + "</span>";
		}
		if(this.templateConfig.kana&1 && this.currentAnswer.kana) {
			output += "<span class='kana'>"+this.currentAnswer.kana+ "</span>";
		}
		if(this.templateConfig.roomaji&1 && this.currentAnswer.roomaji) {
			output += "<span class='roomaji'>"+this.currentAnswer.roomaji+ "</span>";
		}
		if(this.templateConfig.english&1 && this.currentAnswer.english) {
			output += "<span class='english'>"+this.currentAnswer.english+ "</span>";
		}
		if(this.templateConfig.image&1 && this.currentAnswer.image) {
			output += "img:<img src='"+this.currentAnswer.image+"'>";
		}
		if(this.templateConfig.examplej&1 && this.currentAnswer.examplej) {
			output += "<div class='example'><h3>Example</h3>";
			if(this.templateConfig.exampleimg & 1 && this.currentAnswer.exampleimg) {
				output += "<img src='"+this.currentAnswer.exampleimg+"'>";
			}
			output += "<span class='examplej'>"+this.currentAnswer.examplej + "</span>";
			if(this.templateConfig.examplee&1 && this.currentAnswer.examplee) {
				output += "<span class='examplee'>"+this.currentAnswer.examplee + "</span>";
			}
			output += "<div style='clear:both'></div></div>";
		}
		if(this.templateConfig.jsound&1 && this.currentAnswer.jsound) {
			output += "<div>Sound (not implemented): "+this.currentAnswer.jsound+"</div>";
		}
		if(this.templateConfig.comment&1 && this.currentAnswer.comment) {
			output += "<span class='comment'>"+this.currentAnswer.comment+"</span>";
		}
		if(this.templateConfig.sod&1 && this.currentAnswer.sod) {
			output += "<img src='"+this.currentAnswer.sod+"'>";
		}
		o_question.innerHTML = output;

		var o_answerList = document.getElementById('answerlist');
		var outpAnswer="";
	
		for(i=0;i<this.currentQuestions.length;i++) {
			output = "";
			if(this.templateConfig.kanji & 2 && this.currentQuestions[i].kanji) {
				output += this.currentQuestions[i].kanji;
			}
			if(this.templateConfig.kana & 2 && this.currentQuestions[i].kana) {
				output += this.currentQuestions[i].kana;
			}
			if(this.templateConfig.roomaji & 2 && this.currentQuestions[i].roomaji) {
				output += this.currentQuestions[i].roomaji;
			}
			if(this.templateConfig.english & 2 && this.currentQuestions[i].english) {
				output += this.currentQuestions[i].english;
			}
			if(this.templateConfig.image & 2 && this.currentQuestions[i].image) {
				output += "<br/><img src='"+this.currentQuestions[i].image+"'>";
			}
			if(this.templateConfig.jsound & 2 && this.currentQuestions[i].jsound) {
				output += this.currentQuestions[i].jsound;
			}
			if(this.templateConfig.sod&2 && this.currentQuestions[i].sod) {
				output += "<br/><img src='"+this.currentQuestions[i].sod+"'>";
			}

			outpAnswer += ""
				+"<a href='#' title='Keyboard shortcut: "+(i+1)+" key' id='alt_"+i+"' onclick='game.Answer("+i+");'>"
				+"<span style='font-size:7px;text-align:left;clear:both;margin-right:5px;'>"+(i+1)+"</span>"
				+ output
				+"</a>";
			//debugUtil.trace(outpAnswer);
		}

		o_answerList.innerHTML = outpAnswer;
	
	};

	MultiChoiceGame.prototype.GetRandom = function(arr) {
		var len = arr.length;
		var ranNum= Math.floor(Math.random()*len);
		return arr[ranNum];
	};

	MultiChoiceGame.prototype.RandomizeTemplate = function() {
		if(this.settings.randomizeTemplate) {
			var len = 2;
			var ranNum= Math.floor(Math.random()*len);
			switch(ranNum) {
				case 0:
					this.templateConfig=this.templateConfigExample.roomajiToKana;
					break;
				case 1:
					this.templateConfig=this.templateConfigExample.kanaToRoomaji;
					break;
			}
		}
	
	};

	 /** Take an index of the current question and evaluate if it is right */
	MultiChoiceGame.prototype.ShowMessage = function(p_msg,p_highlightColor) {
		graphutils.ReplaceInnerHtml("messagebox",p_msg);			
		if($defined(p_highlightColor))
			$("messagebox").highlight(p_highlightColor);
	};

	MultiChoiceGame.prototype.LogError = function(p_msg) {
		graphutils.ReplaceInnerHtml("messagebox",p_msg);									
	};

	MultiChoiceGame.prototype.LoadGame = function(p_url) {
		var hira_basic = new Array();
		var thisObj = this;
		
		// Format: [ kanji, kana, roomaji, english, image, jsound, examplej, examplee, exampleimg, comment]		
		thisObj.ShowMessage("Loading data...",'#66FF66');
		var items = null;
		var jsonRequest = new Request.JSON({
				url: p_url, 
				onComplete: function(p_response){
					items = p_response.cards;

					jutils.FisherYates(items);

					if($defined(p_response.limit)) {
						items = items.slice(0, Math.min(items.length, p_response.limit) );
					}
					
					thisObj.ShowMessage("Start!",'#66FF66');
					
					thisObj.currentGame.originalSet = items;
					thisObj.currentGame.gameID = p_response.id;
					thisObj.currentGame.gameName = p_response.name;
				},
				onFailure: function(err){
					thisObj.LogError(err);
				},
				async: false
			}).post({'data': 'empty'});	
	};

	/* Prototype to add to Elements */
	MultiChoiceGame.prototype.ToggleTemplate = function()
	{
			if(this.getStyle("display")!="none") {				
				//this._oldHeight = this.getStyle("height");
				//this.tween("height",0);
				this.setStyle("display","none");
			} else {			
				//this.tween("height",this._oldHeight)
				this.setStyle("display","block");
			} 
	}





