/* SDAL-TIMELEFT
(c) by Sir Drink a lot (17.04.04)
 
DESCRIPTION:
- calculates the time left on map.
- reacts on chat message "timeleft" or admin_timeleft. It displays the time left on map to all 
  and speaks the time left on map only to client.
- sets mp_timeleft in seconds
 
INSTALLATION:
- LogD must be installed.
- if you use plugin_sdal_allowsounds, clients can decide with ".stop" or ".play", if they want to
  hear customsounds e.g. the speak-output of time left on map.
- this plugin must be initialized before plugin_chat.
- after "Game_Commencing" or "Restart_Round" it works 100 % 
 
*/
 
#include <core>
#include <console>
#include <string>
#include <admin>
#include <adminlib>
 
#define ACCESS_CONSOLE 131072
 
new AM_VERSION_STRING[] = "2.50.58_v01";
 
/////////////////////////
// KEY FOR ALLOWSOUNDS //
/////////////////////////
 
new Key[]="am_sound";
 
////////////////////
// TIME-VARIABLES //
////////////////////
new g_timelimit;
new g_checktime;
 
//////////////////
// SPEAK-OUTPUT //
//////////////////
static OnesLib[10][] = { 
	"", "one ", "two ", "three ", "four ", "five ", "six ", "seven ", "eight ", "nine " 
};
static TensLib[10][] = {
	"", "ten ", "twenty ", "thirty ", "fourty ", "fifty ", "sixty ", "seventy ", "eighty ", "ninety " 
};
static TeensLib[10][] = {
	"", "eleven ", "twelve ", "thirteen ", "fourteen ", "fifteen ", "sixteen ", "seventeen "
	, "eighteen ", "nineteen " 
};
static HundredsLib[10][] = { 
	"", "one hundred ", "two hundred ", "three hundred ", "four hundred ", "five hundred ", 
	"six hundred ", "seven hundred ", "eight hundred ", "nine hundred " 
};
static GroupNamesLib[5][] = {
	"", "thousand ", "million ", "billion ", "trillion " 
};
 
public plugin_init() {
	plugin_registerinfo("SDAL-Timeleft","Displays and speaks time left on map",AM_VERSION_STRING);
	plugin_registercmd("admin_timeleft","admin_timeleft",ACCESS_ALL,"admin_timeleft: Shows the time left");
	plugin_registercmd("say","HSay",ACCESS_ALL,"say time: Shows the time left");
	plugin_registercmd("mn_world","mn_world",ACCESS_CONSOLE);
	exec( "logd_reg 62 admin_command mn_world" );
	g_timelimit = getvar("mp_timelimit")*60+2;
	g_checktime = systemtime();
	time_change("");
	return PLUGIN_CONTINUE;
}
 
public admin_timeleft(HLCommand,HLData,HLUserName,UserIndex){
	new User[MAX_NAME_LENGTH];
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
	time_change(User);
	return PLUGIN_HANDLED;
}
 
public HSay(HLCommand,HLData,HLUserName,UserIndex){
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
   	convert_string(HLData,Data,MAX_DATA_LENGTH);
   	strstripquotes(Data);
   	if(strcmp(Data,"timeleft")==0){
   		/*override for plugin_chat*/
   		snprintf(Data,MAX_DATA_LENGTH,"%s : timeleft",User);
   		say(Data);
   		time_change(User);
   		return PLUGIN_HANDLED;
   	}
   	return PLUGIN_CONTINUE;
}  		
 
public mn_world(HLCommand,HLData,HLUserName,UserIndex){
	new Data[MAX_NAME_LENGTH];
   	convert_string(HLData,Data,MAX_NAME_LENGTH); 
    	if(Data[0]=='G' || Data[8]=='R'){
    		g_checktime=systemtime();
    	}
    	time_change("");
        return PLUGIN_CONTINUE;
}
 
time_change(User[]){
	new Text[MAX_TEXT_LENGTH];
	new Minutes[MAX_NUMBER_LENGTH];
	new Seconds[MAX_NUMBER_LENGTH];
	new iTime;
	new minutes;
	new seconds;
	if (getvar("mp_timelimit")*60+2 != g_timelimit){
		g_timelimit=getvar("mp_timelimit")*60+2;
        }
	iTime= g_timelimit - (systemtime() - g_checktime);
	minutes = iTime/60;
        seconds=iTime%60;
 
        snprintf(Text,MAX_TEXT_LENGTH,"%i",iTime);
        setstrvar("mp_timeleft",Text);
 
        if(strlen(User)!=0){
	        snprintf(Minutes,MAX_NUMBER_LENGTH,"%i",minutes);
	        if(seconds<10){
	        	snprintf(Seconds,MAX_NUMBER_LENGTH,"0%i",seconds);
	        }else{
	        	snprintf(Seconds,MAX_NUMBER_LENGTH,"%i",seconds);
	        }
	        snprintf(Text,MAX_TEXT_LENGTH,"Time Remaining: %s:%s minutes",Minutes,Seconds);
	        say(Text);
	        speak_timeleft(minutes,seconds,User);
		/*DEBUG
		execclient(User,"timeleft");
		*/
	}
}
 
speak_timeleft(minutes,seconds,User[]){
	new Text[MAX_TEXT_LENGTH];
	new Minutes[MAX_NUMBER_LENGTH];
	new Seconds[MAX_NUMBER_LENGTH];
	if(allowsound(User)){
		numtoword(minutes,Minutes,MAX_NUMBER_LENGTH);
	        numtoword(seconds,Seconds,MAX_NUMBER_LENGTH);
	        snprintf(Text,MAX_DATA_LENGTH,"fvox/%s minutes %s seconds remaining",Minutes,Seconds ); 
		speakto(User,Text);
	}
}
 
//////////////////////////////
// SOUND AND MESSAGE OUTPUT //
//////////////////////////////
 
allowsound(User[]){
	new Info[MAX_NUMBER_LENGTH];
	new iInfo;
	new Authid[MAX_AUTHID_LENGTH];
	get_userAuthID(User,Authid,MAX_AUTHID_LENGTH);
	if(strcmp(Authid,"BOT")!=0){
		get_userinfo(User,Key,Info,MAX_NUMBER_LENGTH);
		iInfo=strtonum(Info);
		if(strlen(Info)==0 || iInfo > 0){/*damit wird automatisch immer der Sound auf 1 gesetzt,wenn kein setinfo vorhanden, bis 'stop' eingegeben wird*/
			return 1;
		}
	}
	return 0;
}
 
/*Big THX to SR71GOKU for this code!*/
stock do_numtoword(iNum,str[],iLevel,iLength) {
 
	/* If there is more than one group of 3, then take care of the others first. */
	if(iNum >= 1000) do_numtoword(iNum / 1000,str,iLevel + 1,iLength);
 
	/* Grab the the first 3 digits only */
	iNum %= 1000;	
 
	/* Isolate each digit */
	new _hundreds = iNum / 100;
	new _tens = (iNum / 10) % 10;
	new _ones = iNum % 10;
 
	/* Take care of the teen numbers */
	if(_tens == 1 && _ones != 0) {
		snprintf(str,iLength,"%s%s%s%s",str,HundredsLib[_hundreds],TeensLib[_ones],GroupNamesLib[iLevel]);
	} else {
		snprintf(str,iLength,"%s%s%s%s%s",str,HundredsLib[_hundreds], TensLib[_tens], OnesLib[_ones],GroupNamesLib[iLevel]);
	}
 
	if(iLevel==0) str[strlen(str)-1] = 0; /* Gets rid of the trailing space*/
	return 1;
}
 
stock numtoword(iNum,str[],iLength) {
	/* Empties the first char of the string */
	str[0] = 0;
	str[iLength-1] = 0;
	if(iNum == 0) {
		snprintf(str,iLength,"zero");
		return 1;
	}
	if(iNum < 0) {
		iNum *= -1;
		snprintf(str,iLength,"negative ");
	}
 
	return do_numtoword(iNum,str,0,iLength); 
}