/* A plugin for enabling limited teleporting abilities. */
/* Telefun mode, which can be turned on by administrators, allows 
 * everyone to access to limited teleport commands, admin_teleset1 & admin_teleset2
 * which set teleport points, and admin_telego1 & admin_telego2 which allow them to
 * teleport back to these points.  Administrators with level 8192 access can always
 * access these commands, as well as admin_telesend1 & admin_telesend2, which enables
 * them to send people to the points they set. Based off code I got from PetitMorte
 * and [WHO]Them, and inspired by [WHO]Them's script.*/
/* $Id: plugin_telefun.sma,v 1.1 2001/04/04 yensid $ */
 
#include <core>
#include <console>
#include <string>
#include <admin>
#include <adminlib>
 
#define ACCESS_FUN 8192
#define ACCESS_VOTE_FUN 8192
 
#define TELE_INVALID 0
 
new STRING_VERSION[MAX_DATA_LENGTH] = "2.50.0";
 
new Telefuntime = 0;
new UserX1[MAX_PLAYERS] = {TELE_INVALID,...};
new UserX2[MAX_PLAYERS] = {TELE_INVALID,...};
new UserY1[MAX_PLAYERS] = {TELE_INVALID,...};
new UserY2[MAX_PLAYERS] = {TELE_INVALID,...};
new UserZ1[MAX_PLAYERS] = {TELE_INVALID,...};
new UserZ2[MAX_PLAYERS] = {TELE_INVALID,...};
 
public admin_fun(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
	if(check_param(Data)==1) {
		execute_command(User,Command,"admin_fun_mode","1");
	} else {
		execute_command(User,Command,"admin_fun_mode","0");
	}
	return PLUGIN_HANDLED;
}
 
public admin_telebind(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new TargetName[MAX_NAME_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new User[MAX_NAME_LENGTH];
 
	convert_string(HLCommand,Command,MAX_COMMAND_LENGTH);
	convert_string(HLData,Data,MAX_DATA_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
	if (check_user(Data) == 1) { 
		get_username(Data,TargetName,MAX_NAME_LENGTH);
		execclient(TargetName, "bind HOME admin_teleset1");
		execclient(TargetName, "bind PGUP admin_teleset2");
		execclient(TargetName, "bind END admin_telego1");
		execclient(TargetName, "bind PGDN admin_telego2");
		snprintf(Text, MAX_TEXT_LENGTH, "Binding teleport keys for %s.", TargetName);
		selfmessage(Text);
		messageex(TargetName, "Home and PgUp can be used to set teleport points.", print_chat);
		messageex(TargetName, "End and PgDn can be used to teleport to these points.", print_chat);
	} else {
		selfmessage("Unrecognized player: ");
		selfmessage(Data);
	}
	log_command(User,Command,Data);
	return PLUGIN_HANDLED;
}
 
public admin_telebindall(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new TargetName[MAX_NAME_LENGTH];
	new User[MAX_NAME_LENGTH];
	new i;
	new maxplayers = maxplayercount();
	new SessionID;
	new Team;
	new WONID;
 
	for(i=1; i<=maxplayers; i++) {
		strinit(TargetName);
		SessionID = 0;
		if(playerinfo(i,TargetName,MAX_NAME_LENGTH,SessionID,WONID,Team)==1) {
			if (check_user(TargetName)==1) { 
				execclient(TargetName, "bind HOME admin_teleset1");
				execclient(TargetName, "bind PGUP admin_teleset2");
				execclient(TargetName, "bind END admin_telego1");
				execclient(TargetName, "bind PGDN admin_telego2");
				messageex(TargetName, "Home and PgUp can be used to set teleport points.", print_chat);
				messageex(TargetName, "End and PgDn can be used to teleport to these points.", print_chat);
			}
		}
	}
	log_command(User,Command,Data);
	return PLUGIN_HANDLED;
}
 
public admin_telebindme(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
 
	execclient(User, "bind HOME admin_teleset1");
	execclient(User, "bind PGUP admin_teleset2");
	execclient(User, "bind END admin_telego1");
	execclient(User, "bind PGDN admin_telego2");
	messageex(User, "Home and PgUp can be used to set teleport points.", print_chat);
	messageex(User, "End and PgDn can be used to teleport to these points.", print_chat);
	log_command(User,Command,Data);
	return PLUGIN_HANDLED;
}
 
public admin_telefun(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
	if (getvar("admin_fun_mode")==0) {
		selfmessage("Telefun mode can only be turned on if admin_fun_mode is 1.");
		return PLUGIN_HANDLED;
	}
	if(check_param(Data)==1) {
		if (Telefuntime==1) {
			selfmessage("Telefun time is already enabled.");
		} else {
			Telefuntime = 1;
			centersay("Telefun time is now enabled!^nUse admin_telebindme to setup your teleporting keys.^nTeleporting keys: HOME and PGUP set teleport points^nEND and PGDN teleport to these points.",20,0,255,0);
		}
	} else {
		if (Telefuntime==1) {
			Telefuntime = 0;
			centersay("Telefun time is now disabled.  Hope you enjoyed it!",15,0,255,0);
		} else {
			selfmessage("Telefun time is already enabled.");
		}
	}
	log_command(User,Command,Data);
	return PLUGIN_HANDLED;
}
 
public admin_telego1(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
	if (Telefuntime==0) {
		if (check_auth(ACCESS_FUN)==0) {
			selfmessage("You can't use this while telefun time is off.");
			return PLUGIN_HANDLED;
		}
	}
	if(teleport(User,UserX1[UserIndex],UserY1[UserIndex],UserZ1[UserIndex])==1) {
		selfmessage("Go To 1 Succeeded.");
	} else {
		selfmessage("Go to 1 failed.");
	}
	return PLUGIN_HANDLED;
}
 
public admin_telego2(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
	if (Telefuntime==0) {
		if (check_auth(ACCESS_FUN)==0) {
			selfmessage("You can't use this while telefun time is off.");
			return PLUGIN_HANDLED;
		}
	}
	if(teleport(User,UserX2[UserIndex],UserY2[UserIndex],UserZ2[UserIndex])==1) {
		selfmessage("Go To 2 Succeeded.");
	} else {
		selfmessage("Go to 2 failed.");
	}
	return PLUGIN_HANDLED;
}
 
public admin_telehelp(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
	if (Telefuntime==1) {
		centersay("Telefun time is enabled!^nUse admin_telebindme to setup your teleporting keys.^nTeleporting keys: HOME and PGUP set teleport points^nEND and PGDN teleport to these points.",20,0,255,0);
	} else {
		selfmessage("Telefun time is not enabled.  Use 'admin_telefun on' to start fun time.");
	}
	return PLUGIN_HANDLED;
}
 
public admin_telesend1(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
	new Text[MAX_TEXT_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
 
	if (check_user(Data) == 1) {
		new TargetName[MAX_NAME_LENGTH];
		get_username(Data,TargetName,MAX_NAME_LENGTH);
		if(teleport(TargetName,UserX1[UserIndex],UserY1[UserIndex],UserZ1[UserIndex])==1) {
			snprintf(Text, MAX_TEXT_LENGTH, "%s teleported to setpoint 1.", TargetName);
			selfmessage(Text);
		} else {
			selfmessage("Failed telesend1.");
		}
	} else {
		selfmessage("Unrecognized user name ");
		selfmessage(Data);
	}
	return PLUGIN_HANDLED;
}
 
public admin_telesend2(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
	new Text[MAX_TEXT_LENGTH];
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
 
	if (check_user(Data) == 1) {
		new TargetName[MAX_NAME_LENGTH];
		get_username(Data,TargetName,MAX_NAME_LENGTH);
		if(teleport(TargetName,UserX2[UserIndex],UserY2[UserIndex],UserZ2[UserIndex])==1) {
			snprintf(Text, MAX_TEXT_LENGTH, "%s teleported to setpoint 2.", TargetName);
			selfmessage(Text);
		} else {
			selfmessage("Failed telesend2.");
		}
	} else {
		selfmessage("Unrecognized user name ");
		selfmessage(Data);
	}
	return PLUGIN_HANDLED;
}
 
public admin_teleset1(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new strNumber[MAX_NUMBER_LENGTH];
	new x=0;
	new y=0;
	new z=0;
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
 
	if (Telefuntime==0) {
		if (check_auth(ACCESS_FUN)==0) {
			selfmessage("You can't use this while telefun time is off.");
			return PLUGIN_HANDLED;
		}
	}
	if (get_userorigin(User, x, y, z)==1) {
		numtostr(x, strNumber);
		numtostr(y, strNumber);
		numtostr(z, strNumber);
		snprintf(Text, MAX_TEXT_LENGTH, "Coord1 Set: X:%s Y:%t Z:%u", x, y, z);
		UserX1[UserIndex] = x;
		UserY1[UserIndex] = y;
		UserZ1[UserIndex] = z;		
	} else {
		selfmessage("Failed teleset1.");
	}
	return PLUGIN_HANDLED;
}
 
public admin_teleset2(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new strNumber[MAX_NUMBER_LENGTH];
	new x=0;
	new y=0;
	new z=0;
 
	convert_string(HLCommand,Command,MAX_NAME_LENGTH);
	convert_string(HLData,Data,MAX_NAME_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
 
	if (Telefuntime==0) {
		if (check_auth(ACCESS_FUN)==0) {
			selfmessage("You can't use this while telefun time is off.");
			return PLUGIN_HANDLED;
		}
	}
	if (get_userorigin(User, x, y, z)==1) {
		numtostr(x, strNumber);
		numtostr(y, strNumber);
		numtostr(z, strNumber);
		snprintf(Text, MAX_TEXT_LENGTH, "Coord2 Set: X:%s Y:%t Z:%u", x, y, z);
		UserX2[UserIndex] = x;
		UserY2[UserIndex] = y;
		UserZ2[UserIndex] = z;		
	} else {
		selfmessage("Failed teleset2.");
	}
	return PLUGIN_HANDLED;
}
 
public admin_vote_telefun(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
	if (getvar("admin_fun_mode")==0) {
		selfmessage("A vote for Telefun mode can only occur if admin_fun_mode is 1.");
		return PLUGIN_HANDLED;
	}
	if (vote_allowed()!=1) {
		selfmessage( "Vote not allowed at this time.");
		return PLUGIN_HANDLED;
	}
 
	convert_string(HLCommand,Command,MAX_COMMAND_LENGTH);
	convert_string(HLData,Data,MAX_DATA_LENGTH);
	convert_string(HLUserName,User,MAX_NAME_LENGTH);
 
	new Text[MAX_DATA_LENGTH] = "Enable telefun mode, allowing teleporting?";
	log(Text);
	vote(Text,"On","Off","HandleTelefunVote",Data);
	return PLUGIN_HANDLED;
}
 
/* Handle a telefun vote's results. */
public HandleTelefunVote(WinningOption,funuser,VoteCount,UserCount) {
	new strNumber[MAX_NUMBER_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new Ratio = 50;
 
	if (WinningOption == 1) {
		if (VoteCount >= Ratio*UserCount/100) {
			Telefuntime = 1; 
			centersay("Telefun time is now enabled!^nUse admin_telebindme to setup your teleporting keys.^nTeleporting keys: HOME and PGUP set teleport points^nEND and PGDN teleport to these points.",20,0,255,0);
		} else {
			numtostr(Ratio*UserCount/100,strNumber);
			snprintf(Text, MAX_TEXT_LENGTH, "Vote to turn on Telefun succeeded, but not enough votes for change (needed %s)", strNumber);
			say(Text);
		}
	} else {
		if (VoteCount >= Ratio*UserCount/100) {
			Telefuntime = 0; 
			centersay("Telefunun time is now disabled!",15,0,255,0);
		} else {
			numtostr(Ratio*UserCount/100,strNumber);
			snprintf(Text, MAX_TEXT_LENGTH, "Vote to turn off Telefun succeeded, but not enough votes for change (needed %s)", strNumber);
			say(Text);
		}
	}
}
 
public plugin_connect(HLUserName, HLIP, UserIndex) {
	if (UserIndex >= 1 && UserIndex <= MAX_PLAYERS) {
		UserX1[UserIndex] = TELE_INVALID;
		UserX2[UserIndex] = TELE_INVALID;
		UserY1[UserIndex] = TELE_INVALID;
		UserY2[UserIndex] = TELE_INVALID;
		UserZ1[UserIndex] = TELE_INVALID;
		UserZ2[UserIndex] = TELE_INVALID;
	}
	return PLUGIN_CONTINUE;
}
 
public plugin_disconnect(HLUserName, UserIndex) {
	if (UserIndex >= 1 && UserIndex <= MAX_PLAYERS) {
		UserX1[UserIndex] = TELE_INVALID;
		UserX2[UserIndex] = TELE_INVALID;
		UserY1[UserIndex] = TELE_INVALID;
		UserY2[UserIndex] = TELE_INVALID;
		UserZ1[UserIndex] = TELE_INVALID;
		UserZ2[UserIndex] = TELE_INVALID;
	}
	return PLUGIN_CONTINUE;
}
 
public plugin_init() {
	plugin_registerinfo("TeleFun Plugin","Gives limited teleporting abilities.",STRING_VERSION);
 
	plugin_registercmd("admin_fun","admin_fun",ACCESS_FUN,"admin_fun <^"on^" | ^"off^">: Turns fun mode on or off.");	
	plugin_registercmd("admin_telebind","admin_telebind",ACCESS_FUN,"admin_telebind <target>: On target's system, binds HOME & PGUP to teleset1 & 2, and END & PGDN to telego1 & 2.");
	plugin_registercmd("admin_telebindall","admin_telebindall",ACCESS_FUN,"admin_telebindall: On everyone's systems, binds HOME & PGUP to teleset1 & 2, and END & PGDN to telego1 & 2.");
	plugin_registercmd("admin_telebindme","admin_telebindme",ACCESS_ALL,"admin_telebindme: On users's system, binds HOME & PGUP to teleset1 & 2, and END & PGDN to telego1 & 2.");	
	plugin_registercmd("admin_telefun","admin_telefun",ACCESS_FUN,"admin_telefun <^"on^" | ^"off^">: Turns telefun mode, allowing limited teleporting, on or off.");	
	plugin_registercmd("admin_telego1","admin_telego1",ACCESS_ALL,"admin_telego1: Teleports user to waypoint 1.");	
	plugin_registercmd("admin_telego2","admin_telego2",ACCESS_ALL,"admin_telego2: Teleports user to waypoint 2.");	
	plugin_registercmd("admin_telehelp","admin_telehelp",ACCESS_FUN,"admin_telehelp: Displays help for telefun mode in a centersay.");	
	plugin_registercmd("admin_telesend1","admin_telesend1",ACCESS_FUN,"admin_telesend1 <target>: Teleports target to users waypoint 1.");	
	plugin_registercmd("admin_telesend2","admin_telesend2",ACCESS_FUN,"admin_telesend2<target>: Teleports target to users waypoint 2.");	
	plugin_registercmd("admin_teleset1","admin_teleset1",ACCESS_ALL,"admin_teleset1: Sets user's teleporting waypoint 1.");	
	plugin_registercmd("admin_teleset2","admin_teleset2",ACCESS_ALL,"admin_teleset2: Sets user's teleporting waypoint 2.");	
	plugin_registercmd("admin_vote_telefun","admin_vote_telefun",ACCESS_FUN,"admin_vote_telefun: Begins vote for whether to have telefun mode enabled.");	
 
	return PLUGIN_CONTINUE;
}