/********************************************************************************************
 * plugin_pager  v6.11
 *
 * This plugin will display a custom message to a specific client or clients
 * as they connect, in effect "paging" them.
 *
 * Much of the code for the file parsing and the admin_pager_add functions was
 * borrowed from plugin_sank_sounds, by Luke Sankey <sank@spu.edu>
 *
 * Thanks to Surfdevil for posting on the AdminMod forums about a typo of mine!
 *
 * Several major changes are noted below, by version:
 *
 * v6.11 Note:
 *  Minor tweaks, better compatibility for AdminMod 2.50.58 and later
 *
 * v6.10 Note:
 *  Updated for Steam & AdminMod 2.50.58
 *
 * v6.01 Note:
 *  ALL sounds are now "spoken", which means all sounds (both internal and external) must be
 *  defined in the config file with a forward slash "/" instead of a backslash "\"
 *
 * v5.0 Note:
 *  "Spoken" sound messages no longer require the additional "speak" command or the quotation
 *  marks; see the example below in Setup or see Sample Config file
 *
 * v3.0 Note:
 *  This version features some documentation corrections, as well as bug fixes.  The most
 *  important documentation correction is in regards to the search_type.  The original version
 *  incorrectly said a search_type of 3 is for AuthID and 4 is for IP Address... it should be
 *  the other way around.  This means some of you may have to make some changes to your config
 *  files if you have not already done so.
 *
 * Setup:
 * 1) Setup a file named PAGER.CFG with the following info:
 * 2) Choose a PAGER_MODE to use
 *     -- MODE 1 = display PAGER_MESSAGE
 *     -- MODE 2 = don't display it
 * 3) Specify a PAGER_MESSAGE to be displayed when delivering messages
 * 4) Specify a PAGER_SOUND to be played when delivering messages
       -- A blank entry will play one of 6 random default messages
       -- Either specify an external .wav file relative to your mod's "sound" folder...
       -- Or specify an internal wav file (see ReadMe.txt for more info)
 * 5) Specify a <search_type> from 1 to 4: 1=Full Name, 2=Partial Name, 3=IP Address, 4=AuthID
 * 6) Specify a client's Name, Partial name, IP Address, or AuthID followed by a ;
 * 7) Enter a custom message for that person following their Name/AuthID/IP
 * 8) Enter as many as 40 messages
 * 9) File should follow this format:
 *       PAGER_MODE;<1 or 2>
 *       PAGER_MESSAGE;You have a message!!
 *       PAGER_SOUND;misc/pg_subspsig.wav
 *        or
 *       PAGER_SOUND;you have a message
 *       <search_type>;<target>;<message1>
 *       <search_type>;<target>;<message2>
 *       <search_type>;<target>;<message3>
 *
 *
 * Functions included:
 *  admin_pager_reload
 *  admin_pager_resend [target]
 *  admin_pager_off
 *  admin_pager_on
 *  admin_pager_add "<search_type>;<target>;<message>"
 *
 * February 10, 2002 Added
 *  admin_pager_list
 *  admin_pager_delete [index]
 *
 * June 2, 2002 Added
 *  admin_pager_mode
 *  admin_pager_msg
 *  admin_pager_sound
 *
 *
 * Bill Bateman aka "HunteR"
 * http://thepit.shacknet.nu
 * huntercc@hotmail.com
 ********************************************************************************************/
 
 
#include <core>
#include <console>
#include <string>
#include <admin>
#include <adminlib>
#include <plugin>
 
 
#define ACCESS_PAGER 64+512 // levels 64 + 512 give access to special pager commands
#define MAX_LINES 40
#define MAX_IPADDRESS 15+1  // xxx.xxx.xxx.xxx = 15 characters + null character
#define NUM_TO_LIST 8       // number of messages to list at a time for admin_pager_list
#define LIST_CHARS 10       // max number of characters to show of Message in admin_pager_list
 
#define DEBUG 0  // set to 1 for extra logging of data
 
 
new STRING_VERSION[MAX_DATA_LENGTH] = "2.50.58, Pager v6.11";
new FILENAME[MAX_DATA_LENGTH] = "addons\adminmod\config\PAGER.CFG";  // name of file to be parsed
new sMatchMethod[MAX_DATA_LENGTH];  // temporary string for MatchMethod
new ContentsChanged = 0;   // flag used in deletion of messages
 
// determines how to identify the target:
// 1=Name, 2=Partial Name, 3=IP Address, 4=AuthID
new MatchMethod[MAX_LINES];
 
new Messages[MAX_LINES][MAX_DATA_LENGTH];      // contains list of messages to be delievered, from FILENAME
new StoredUser[MAX_LINES][MAX_NAME_LENGTH];    // contains users to be paged, in the form of Name, AuthID, or IP Address, from FILENAME
new MsgTimer[MAX_PLAYERS+1];                   // timer to delay the retrieval of the target's AuthID
new MyWholeIP[MAX_PLAYERS+1][MAX_IPADDRESS+7]; // IP of current player, with the port number
new PagerEnabled = 1;                          // 1 = enabled, 0 = disabled
new NumOfMessages = 0;                         // total number of messages parsed from config file
new ConnHandled[MAX_PLAYERS+1] = {0,...};      // connection status of each player
new bResend[MAX_PLAYERS+1] = {0,...};          // used only in admin_pager_resend
 
new PAGER_MODE = 1;                            // Mode 1 = display the pager notify message, Mode 2 = don't
new PAGER_MESSAGE[MAX_TEXT_LENGTH];            // First message to be displayed when a client has a page
new PAGER_SOUND[MAX_DATA_LENGTH];              // Sound to be played to notify the user of a page; blank means use default
 
 
public plugin_init()
{
	plugin_registerinfo("HunteR's Client Pager Plugin", "Displays customized messages to specific players after they connect.", STRING_VERSION);
	plugin_registercmd("specmode",		"HandleSpecMode",	ACCESS_ALL);
	plugin_registercmd("admin_pager_resend","admin_pager_resend",	ACCESS_ALL,	"admin_pager_resend [target]: Re-sends a user's messages; admins may also specify a target.");
	plugin_registercmd("admin_pager_delete","admin_pager_delete",	ACCESS_ALL,	"admin_pager_delete [index]: Deletes your messages; [index] is from ^"admin_pager_list^"");
	plugin_registercmd("admin_pager_on",	"admin_pager_on",	ACCESS_PAGER,	"admin_pager_on: Enables the pager plugin.");
	plugin_registercmd("admin_pager_off",	"admin_pager_off",	ACCESS_PAGER,	"admin_pager_off: Disables the pager plugin.");
	plugin_registercmd("admin_pager_reload","admin_pager_reload",	ACCESS_PAGER,	"admin_pager_reload: Reloads config file.");
	plugin_registercmd("admin_pager_add",	"admin_pager_add",	ACCESS_PAGER,	"admin_pager_add ^"<search_type>;<target>;<message>^": Adds a message to the pager config file.");
	plugin_registercmd("admin_pager_list",	"admin_pager_list",	ACCESS_PAGER,	"admin_pager_list: Displays indexed list of people who have messages waiting.");
	plugin_registercmd("admin_pager_mode",	"admin_pager_mode",	ACCESS_PAGER,	"admin_pager_mode <1 or 2>: 1 = Display PAGER_MESSAGE, 2 = Don't.");
	plugin_registercmd("admin_pager_msg",	"admin_pager_msg",	ACCESS_PAGER,	"admin_pager_msg <PAGER_MESSAGE or ^"default^">: Text to show when delivering messages.");
	plugin_registercmd("admin_pager_sound",	"admin_pager_sound",	ACCESS_PAGER,	"admin_pager_sound <PAGER_SOUND or ^"default^">: Sound to play when delivering messages.");
 
	new i;
	for(i = 0; i < MAX_PLAYERS; i++)
		MsgTimer[i] = 0;
 
	snprintf(PAGER_MESSAGE, MAX_TEXT_LENGTH, "You have a message waiting for you!!!");
	parse_file(FILENAME);
 
	return PLUGIN_CONTINUE;
}
 
public admin_pager_sound(HLCommand,HLData,HLUserName,UserIndex) {
	new Data[MAX_DATA_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	convert_string(HLData, Data, MAX_DATA_LENGTH);
 
	if ( strlen(Data) == 0 )
	{
		selfmessage("[ADMIN] PAGER_SOUND is currently:");
		snprintf(Text, MAX_TEXT_LENGTH, "[ADMIN]   ^"%s^"", PAGER_SOUND);
		selfmessage(Text);
	}
	else if ( !strcasecmp(Data,"default") )
	{
		strinit(PAGER_SOUND);
		selfmessage("[ADMIN] Pager Plugin will now use one of six random default sounds.");
		write_list();
	}
	else
	{
		strcpy(PAGER_SOUND, Data, MAX_DATA_LENGTH);
		selfmessage("[ADMIN] PAGER_SOUND is currently:");
		snprintf(Text, MAX_TEXT_LENGTH, "[ADMIN]   %s", PAGER_SOUND);
		selfmessage(Text);
		write_list();
	}
 
	return PLUGIN_HANDLED;
}
 
public admin_pager_msg(HLCommand,HLData,HLUserName,UserIndex) {
	new Data[MAX_DATA_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	convert_string(HLData, Data, MAX_DATA_LENGTH);
 
	if ( strlen(Data) == 0 )
	{
		selfmessage("[ADMIN] PAGER_MESSAGE is currently:");
		snprintf(Text, MAX_TEXT_LENGTH, "[ADMIN]   ^"%s^"", PAGER_MESSAGE);
		selfmessage(Text);
	}
	else if ( !strcasecmp(Data,"default") )
	{
		snprintf(PAGER_MESSAGE, MAX_TEXT_LENGTH, "You have a message waiting for you!!!");
		selfmessage("[ADMIN] PAGER_MESSAGE is currently:");
		selfmessage(PAGER_MESSAGE);
		write_list();
	}
	else
	{
		strcpy(PAGER_MESSAGE, Data, MAX_TEXT_LENGTH);
		selfmessage("[ADMIN] PAGER_MESSAGE is currently:");
		snprintf(Text, MAX_TEXT_LENGTH, "[ADMIN]   ^"%s^"", PAGER_MESSAGE);
		selfmessage(Text);
		write_list();
	}
 
	return PLUGIN_HANDLED;
}
 
public admin_pager_mode(HLCommand,HLData,HLUserName,UserIndex) {
	new Data[MAX_DATA_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	convert_string(HLData, Data, MAX_DATA_LENGTH);
 
	if ( strlen(Data) == 0 )
	{
		snprintf(Text, MAX_TEXT_LENGTH, "[ADMIN] Current PAGER_MODE = %d", PAGER_MODE);
		selfmessage(Text);
		selfmessage("[ADMIN]  Mode 1 = Display PAGER_MESSAGE.");
		selfmessage("[ADMIN]  Mode 2 = Don't.");
	}
	else if ( strtonum(Data) == 1 )
	{
		PAGER_MODE = 1;
		selfmessage("[ADMIN] Pager Plugin will display PAGER_MESSAGE to all recipients.");
		write_list();
	}
	else
	{
		PAGER_MODE = 2;
		selfmessage("[ADMIN] Pager Plugin will no longer display PAGER_MESSAGE.");
		write_list();
	}
 
	return PLUGIN_HANDLED;
}
 
public admin_pager_list(HLCommand,HLData,HLUserName,UserIndex) {
	new Data[MAX_DATA_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new sTemp[MAX_TEXT_LENGTH];
	convert_string(HLData, Data, MAX_DATA_LENGTH);
 
	if ( NumOfMessages < 1 )
	{
		selfmessage("[PAGER] No messages to list.");
		return PLUGIN_HANDLED;
	}
 
	if ( strlen(Data) == 0 ) Data = "0";
	new msgIndex = strtonum(Data);
	if ( msgIndex < 0 || msgIndex >= NumOfMessages) {
		snprintf(Text, MAX_TEXT_LENGTH, "[PAGER] Index is out of range.  Index must be from 0 to %i", NumOfMessages-1);
		selfmessage(Text);
	} else {
		selfmessage("[Index] - [MatchType] : [User]");
		new i;
		new Range = msgIndex + NUM_TO_LIST;
		if ( Range > NumOfMessages ) Range = NumOfMessages;
		for ( i=msgIndex; i<Range; i++ )
		{
			strcpy(sTemp, Messages[i], LIST_CHARS);
			if ( MatchMethod[i] == 1 ) {
				snprintf(Text, MAX_TEXT_LENGTH, "%i - Exact Name :^t%s - %s", i, StoredUser[i], sTemp);
				selfmessage(Text);
			} else if ( MatchMethod[i] == 2 ) {
				snprintf(Text, MAX_TEXT_LENGTH, "%i - Partial Name :^t%s - %s", i, StoredUser[i], sTemp);
				selfmessage(Text);
			} else if ( MatchMethod[i] == 3 ) {
				snprintf(Text, MAX_TEXT_LENGTH, "%i - IP Address :^t%s - %s", i, StoredUser[i], sTemp);
				selfmessage(Text);
			} else if ( MatchMethod[i] == 4 ) {
				snprintf(Text, MAX_TEXT_LENGTH, "%i - AuthID : ^t%s - %s", i, StoredUser[i], sTemp);
				selfmessage(Text);
			}
		}
		if ( (msgIndex+NUM_TO_LIST) < NumOfMessages ) {
			snprintf(Text, MAX_TEXT_LENGTH, "  Type admin_pager_list %i for more", Range+1);
			selfmessage(Text);
		}
	}
 
	return PLUGIN_HANDLED;
}
 
// Deletes all messages for user; admins may also specify a target
public admin_pager_delete(HLCommand,HLData,HLUserName,UserIndex) {
	new Command[MAX_COMMAND_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new Data[MAX_DATA_LENGTH];
	new MyName[MAX_NAME_LENGTH];                    // Name of current player
	new MyAuthID[MAX_DATA_LENGTH];                  // AuthID of current player
	new MyIP[MAX_IPADDRESS];                        // IP of current player, w/o the port number
 
	if ( NumOfMessages < 1 )
	{
		selfmessage("[PAGER] No messages to delete.");
		return PLUGIN_HANDLED;
	}
 
 	convert_string(HLCommand,Command,MAX_COMMAND_LENGTH);
	convert_string(HLUserName, MyName, MAX_NAME_LENGTH);
	convert_string(HLData, Data, MAX_DATA_LENGTH);
	get_userAuthID(MyName, MyAuthID);
 
	// This chunk of code handles deletion of messages from the list by an admin
	if ( (strlen(Data) != 0) ) {
		if( !access(ACCESS_PAGER, "") ) {
			selfmessage("[PAGER] You do not have access to specify a message to be deleted.");
			return PLUGIN_HANDLED;
		}
 
		new msgIndex = strtonum(Data);
 
		if ( msgIndex < 0 || msgIndex >= NumOfMessages) {
			snprintf(Text, MAX_TEXT_LENGTH, "[PAGER] Index is out of range.  Index must be from 0 to %i", NumOfMessages-1);
			selfmessage(Text);
		} else {
			snprintf(Text, MAX_TEXT_LENGTH, "[PAGER] Message number %i now being deleted.", msgIndex);
			selfmessage(Text);
#if DEBUG
			log(Text);
			snprintf(Text, MAX_TEXT_LENGTH, "[PAGER] Message: ^"%s^"", Messages[msgIndex]);
			log(Text);
#endif
			Messages[msgIndex] = "";
			write_list();
#if DEBUG
			snprintf(Text, MAX_TEXT_LENGTH, "[PAGER] Message after deletion: ^"%s^"", Messages[msgIndex]);
			log(Text);
#endif
		}
		log_command(MyName,Command,Data);
		return PLUGIN_HANDLED;
	}
 
	// if this chunk is executed from the HLDS console, it will clear the file, which we dont want:
	if ( UserIndex ) {
		strtok(MyWholeIP[UserIndex], ":", MyIP, MAX_IPADDRESS);  // strip the port number from the IP
		selfmessage("All messages specifically for you are now being deleted.");
 
		// search for exact matches: Exact Name, IP, or AuthID
		new searchIndex = 0;
		for ( searchIndex=0; searchIndex<NumOfMessages; searchIndex++ )
		{
			// delete any messages that match current user, and are not substring matches
			if ( ( MatchMethod[searchIndex] != 2 ) && ( (strcasecmp(MyName,StoredUser[searchIndex]) == 0) || (streq(MyIP,StoredUser[searchIndex]) == 1) ) ) {
				Messages[searchIndex] = "";
				ContentsChanged = 1;
			}
			else if ( MatchMethod[searchIndex] != 2 && (streq(MyAuthID,StoredUser[searchIndex]) == 1) ) {
				Messages[searchIndex] = "";
				ContentsChanged = 1;
			}
		}
 
		if ( !ContentsChanged ) {
			selfmessage("[PAGER] Error deleting message or none to delete.");
			log("[PAGER] Error deleting message or none to delete.");
			return PLUGIN_HANDLED;
		}
 
		snprintf(Text, MAX_TEXT_LENGTH, "Pager Plugin >> Messages for ^"%s^" were deleted.", MyName);
		selfmessage(Text);
		log(Text);
		write_list();
	} else {
		selfmessage("[ADMIN] You must be a client to use this command, or you must specify a target.");
	}
 
	return PLUGIN_HANDLED;
}
 
write_list() {
	// Write everything to the default file:
	new Text[MAX_TEXT_LENGTH];
	new saveIndex = 0;
	new TimeStamp[MAX_TEXT_LENGTH];
	servertime(TimeStamp, MAX_TEXT_LENGTH);
 
	resetfile(FILENAME);
	writefile(FILENAME, "# Config File for Pager Plugin, by HunteR <huntercc@hotmail.com>");
	writefile(FILENAME, "# Last modified:");
	snprintf(Text, MAX_TEXT_LENGTH, "# %s", TimeStamp);
	writefile(FILENAME, Text);
	writefile(FILENAME, "#");
	writefile(FILENAME, "# Mode 1 = display PAGER_MESSAGE");
	writefile(FILENAME, "# Mode 2 = don't display it");
	snprintf(Text, MAX_TEXT_LENGTH, "PAGER_MODE;%i", PAGER_MODE);
	writefile(FILENAME, Text);
	snprintf(Text, MAX_TEXT_LENGTH, "PAGER_MESSAGE;%s", PAGER_MESSAGE);
	writefile(FILENAME, Text);
	snprintf(Text, MAX_TEXT_LENGTH, "PAGER_SOUND;%s", PAGER_SOUND);
	writefile(FILENAME, Text);
	writefile(FILENAME, "#");
	writefile(FILENAME, "# 1=Exact Name, 2=Partial Name, 3=IP Address, 4=AuthID");
 
	for ( saveIndex=0; saveIndex<NumOfMessages; saveIndex++ )
	{
		// write non-blank lines to the default file
		if ( strlen(Messages[saveIndex]) != 0 ) {
			snprintf(Text, MAX_TEXT_LENGTH, "%i;%s;%s", MatchMethod[saveIndex], StoredUser[saveIndex], Messages[saveIndex]);
			writefile(FILENAME, Text);
#if DEBUG
			log(Text);
#endif
		}
	}
 
	ContentsChanged = 1;
	parse_file(FILENAME);
	ContentsChanged = 0;
 
	return 1;
}
 
// Disables the pager plugin
public admin_pager_off(HLCommand,HLData,HLUserName,UserIndex) {
	PagerEnabled = 0;
	say("HunteR's Client Pager Plugin has been disabled!");
	playsoundall("fvox/communications_on(e70) deactivated");
 
	return PLUGIN_HANDLED;
}
 
// Enables the pager plugin if already disabled
public admin_pager_on(HLCommand,HLData,HLUserName,UserIndex) {
	PagerEnabled = 1;
	say("HunteR's Client Pager Plugin has been enabled!");
	playsoundall("fvox/communications_on");
 
	return PLUGIN_HANDLED;
}
 
// USAGE:  admin_pager_add "<search_type>;<target>;<message>"
public admin_pager_add(HLCommand, HLData, HLUserName, UserIndex) {
	new Data[MAX_DATA_LENGTH];
	new User[MAX_NAME_LENGTH];
	new sMethod[MAX_DATA_LENGTH];
	new Method;
	new Target[MAX_DATA_LENGTH];
	new Msg[MAX_DATA_LENGTH];
	new Text[MAX_TEXT_LENGTH];
 
	if ( NumOfMessages >= MAX_LINES )
	{
		selfmessage("No room for new messages. Either increase MAX_LINES or remove old messages.");
		return PLUGIN_HANDLED;
	}
 
	// See if file_access_write is on or off:
	if ( getvar("file_access_write") == 0 )
	{
		snprintf(Text, MAX_TEXT_LENGTH, "Pager Plugin >> Cannot write to %s", FILENAME);
		selfmessage(Text);
		selfmessage("Pager Plugin >> file_access_write must be set to 1.");
 
		return PLUGIN_HANDLED;
	}
 
	convert_string(HLData, Data, MAX_DATA_LENGTH);
	convert_string(HLUserName, User, MAX_NAME_LENGTH);
 
	strstripquotes(Data);
	strsplit(Data, ";", sMethod, MAX_DATA_LENGTH, Target, MAX_DATA_LENGTH, Msg, MAX_DATA_LENGTH);
	Method = strtonum(sMethod);
 
	// Check if the parameters are valid or not:
	if( Method < 1 || Method > 4 || strlen(Target) == 0 || strlen(Msg) == 0 )
	{
		selfmessage("Invalid format.");
		selfmessage("USAGE: admin_pager_add ^"<search_type>;<target>;<message>^"");
		selfmessage("where <search_type> is 1 through 4: 1=Exact Name, 2=Partial Name, 3=IP Address, 4=AuthID");
		return PLUGIN_HANDLED;
	}
 
	new TimeStamp[MAX_TEXT_LENGTH];
	servertime(TimeStamp, MAX_TEXT_LENGTH);
 
	snprintf(Text, MAX_TEXT_LENGTH, "# %s: Message added by ^"%s^"", TimeStamp, User);
	writefile(FILENAME, Text);
	snprintf(Text, MAX_TEXT_LENGTH, "%i;%s;%s", Method, Target, Msg);
	writefile(FILENAME, Text);
 
	switch (Method)
	{
		case 1: strcpy(sMethod, "Exact Name", MAX_TEXT_LENGTH);
		case 2: strcpy(sMethod, "Partial Name", MAX_TEXT_LENGTH);
		case 3: strcpy(sMethod, "IP Address", MAX_TEXT_LENGTH);
		case 4: strcpy(sMethod, "AuthID", MAX_TEXT_LENGTH);
	}
 
	snprintf(Text, MAX_TEXT_LENGTH, " >> Search type:^t^"%i^"  (%s)", Method, sMethod);
	selfmessage(Text);
	snprintf(Text, MAX_TEXT_LENGTH, " >> Target user:^t^"%s^"", Target);
	selfmessage(Text);
	snprintf(Text, MAX_TEXT_LENGTH, " >> Message added:^t^"%s^"", Msg);
	selfmessage(Text);
	snprintf(Text, MAX_TEXT_LENGTH, "New message successfully added to ^"%s^" file.", FILENAME);
 
	NumOfMessages++;
	parse_file(FILENAME);
 
	return PLUGIN_HANDLED;
}
 
public admin_pager_resend(HLCommand,HLData,HLUserName,UserIndex) {
	new TargetIndex;
	new TargetName[MAX_NAME_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new User[MAX_NAME_LENGTH];
	new Data[MAX_DATA_LENGTH];
	convert_string(HLUserName, User, MAX_NAME_LENGTH);
	convert_string(HLData, Data, MAX_DATA_LENGTH);
 
	if ( (strlen(Data) != 0) )
	{
		if ( check_auth(ACCESS_PAGER) )
		{
			if ( check_user(Data) )
			{
				get_userindex(Data, TargetIndex);
				playerinfo(TargetIndex,TargetName,MAX_NAME_LENGTH);
				snprintf(Text, MAX_TEXT_LENGTH, "^"%s^" used command admin_pager_resend %s", User, TargetName);
				selfmessage(Text);
				log(Text);
				bResend[TargetIndex] = 1;
				MsgTimer[TargetIndex] = set_timer("MsgTrigger",1,0,TargetName);
			} else {
				snprintf(Text, MAX_TEXT_LENGTH, "Error: ^"%s^" is not a valid player on this server.", Data);
				selfmessage(Text);
			}
		} else {
			selfmessage("You do not have access to extend this command.");
		}
	}
	else {
		selfmessage("If you have any messages waiting, they will now be delivered.");
		bResend[UserIndex] = 1;
		MsgTimer[UserIndex] = set_timer("MsgTrigger",1,0,User);
	}
 
	return PLUGIN_HANDLED;
}
 
// Re-parses the config file
public admin_pager_reload(HLCommand,HLData,HLUserName,UserIndex) {
	parse_file(FILENAME);
	return PLUGIN_HANDLED;
}
 
 
//*************************************************************************
// Parses the sound file specified by loadfile. If loadfile is empty, then
// it parses the default FILENAME.
//
// Returns 0 if parsing was successful
// Returns 1 if parsing failed
// Returns -1 otherwise
//************************************************************************/
parse_file(loadfile[] = "") {
	new GotLine;
	new iLineNum = 0;
	new strLineBuf[MAX_TEXT_LENGTH];
	new ListIndex = 0;
	new Text[MAX_TEXT_LENGTH];
	NumOfMessages = 0; // reset the count before we parse again
 
	if (strlen(loadfile) == 0)
		strcpy(loadfile, FILENAME, MAX_TEXT_LENGTH);
 
	if (fileexists(loadfile) > 0)
	{
		GotLine = readfile(loadfile, strLineBuf, iLineNum, MAX_TEXT_LENGTH);
		if (GotLine <= 0)
		{
			// If file access is already set correctly...
			if (getvar("file_access_read") == 1)
				snprintf(Text, MAX_TEXT_LENGTH, "Pager Plugin >> Unable to read from %s file.", loadfile);
			else
				snprintf(Text, MAX_TEXT_LENGTH, "Pager Plugin >> CVAR file_access_read is set incorrectly.");
			log(Text);
			return -1;
		}
 
		new clearIndex = 0;
		for ( clearIndex=0; clearIndex<MAX_LINES; clearIndex++ ) {
			MatchMethod[clearIndex] = 0;
			StoredUser[clearIndex] = "";
			Messages[clearIndex] = "";
		}
 
		while (GotLine)
		{
			if (ListIndex >= MAX_LINES)
			{
				log("Pager Plugin >> Pager list truncated. Increase MAX_LINES and recompile.");
				printf("Pager Plugin >> Error - stopped parsing %s file.^n", loadfile);
				break;
			}
 
			// As long as the line isn't commented out, and isn't blank, then process it.
			if ( (strncmp(strLineBuf, "#", 1) != 0) && (strncmp(strLineBuf, "//", 2) != 0) && (strlen(strLineBuf) != 0) )
			{
				strsep(strLineBuf, ";", sMatchMethod, MAX_DATA_LENGTH, strLineBuf, MAX_TEXT_LENGTH);
				strtrim(sMatchMethod, "^t");
				strtrim(strLineBuf, "^t");
 
				if( !strcasecmp(sMatchMethod, "PAGER_MODE") )
					PAGER_MODE = strtonum(strLineBuf);
				else if( !strcasecmp(sMatchMethod, "PAGER_MESSAGE") && strlen(strLineBuf) )
					strcpy(PAGER_MESSAGE, strLineBuf, MAX_TEXT_LENGTH);
				else if( !strcasecmp(sMatchMethod, "PAGER_SOUND") )
					strcpy(PAGER_SOUND, strLineBuf, MAX_TEXT_LENGTH);
				else
				{
					strsplit(strLineBuf, ";", StoredUser[ListIndex], MAX_DATA_LENGTH, Messages[ListIndex], MAX_DATA_LENGTH);
					MatchMethod[ListIndex] = strtonum(sMatchMethod);
 
					if( MatchMethod[ListIndex] > 0 && MatchMethod[ListIndex] < 5 )
					{
						ListIndex++;
						NumOfMessages++;
					} else {
						snprintf(Text, MAX_TEXT_LENGTH, "Pager Plugin >> Line %i skipped in file %s for invalid format", iLineNum, FILENAME);
						log(Text);
					}
				}
			}
 
			// Read in the next line from the file
			GotLine = readfile(loadfile, strLineBuf, ++iLineNum, MAX_TEXT_LENGTH);
		}
	}
	else // file exists returned false, meaning the file didn't exist
	{
		snprintf(Text, MAX_TEXT_LENGTH, "[ADMIN] Pager Plugin >> Cannot find %s file.", loadfile);
		selfmessage(Text);
		return 1;
	}
 
	if ( !ContentsChanged ) {
		snprintf(Text, MAX_TEXT_LENGTH, "[ADMIN] Pager Plugin >> %s successfully loaded.", loadfile);
		selfmessage(Text);
	}
	else ContentsChanged = 0;
 
	return 0;
}
 
welcome_user(User[]) {
	new Text[MAX_TEXT_LENGTH];
 
	if( PAGER_MODE == 1 )
	{
		plugin_message(PAGER_MESSAGE);
		snprintf(Text, MAX_TEXT_LENGTH, "HunteR's Client Pager Plugin: %s", PAGER_MESSAGE);
		messageex(User, Text, print_chat);
	}
 
	new dummy1[MAX_TEXT_LENGTH];
	new sExt[MAX_TEXT_LENGTH];
	strsep(PAGER_SOUND, ".", dummy1, MAX_TEXT_LENGTH, sExt, MAX_TEXT_LENGTH);
 
	if ( !strlen(PAGER_SOUND) )
	{
		new rand;
		new Num = 6;  // Total number of sounds (defined below in switch statement)
		rand = random(Num);
 
		if ( rand > (Num-1) ) {
			// shouldn't ever get here, but just in case:
			log("Pager Plugin >> Random number too big, setting to maximum value.");
			rand = (Num-1);
		}
 
		switch(rand)
		{
			case 0: execclient(User, "speak ^"fvox/safe_day^"");
			case 1: execclient(User, "speak ^"tride/c0a0_tr_gmorn(e56)^"");
			case 2: execclient(User, "speak ^"scientist/goodtoseeyou(e65)^"");
			case 3: execclient(User, "speak ^"scientist/greetings(e55)^"");
			case 4: execclient(User, "speak ^"scientist/greetings2(e38)^"");
			case 5: execclient(User, "speak ^"scientist/hellothere^"");
		}
	}
	else if ( strcasecmp(sExt,"wav") != 0 )  // if it does NOT end in ".wav" then "speak" the sound
	{
		snprintf(Text, MAX_TEXT_LENGTH, "speak ^"%s^"", PAGER_SOUND);
		execclient(User, Text);
	}
	else
		playsound(User, PAGER_SOUND);
}
 
public  MsgTrigger(Timer,WaitCount,RepeatCount,User) {
	new MyAuthID[MAX_DATA_LENGTH];
	new MyIP[MAX_IPADDRESS];       // IP of current player, w/o the port number
	new searchIndex = 0;
	new Text[MAX_TEXT_LENGTH];
	new UserIndex;
	new MyName[MAX_NAME_LENGTH];
	new MatchFound = 0;
 
	convert_string(User, MyName, MAX_NAME_LENGTH);
	get_userindex(MyName, UserIndex);
	get_userAuthID(MyName, MyAuthID);
 
	strtok(MyWholeIP[UserIndex], ":", MyIP, MAX_IPADDRESS);  // strip the port number from the IP
 
	for ( searchIndex=0; searchIndex<MAX_LINES; searchIndex++ )
	{
		if (MatchMethod[searchIndex]<1 || MatchMethod[searchIndex]>4 || strlen(StoredUser[searchIndex])==0 )
			break;
 
		if ( MatchMethod[searchIndex] == 1 && strcasecmp(MyName,StoredUser[searchIndex]) == 0 )
		{
			if ( !MatchFound ) {    // only call welcome_user one time per user
				welcome_user(MyName);
				MatchFound = 1;
			}
			snprintf(Text, MAX_TEXT_LENGTH, "--Message for %s >> %s", StoredUser[searchIndex], Messages[searchIndex]);
			messageex(MyName,Text,print_chat);
#if DEBUG
			log(Text);
#endif
		}
 
		if ( MatchMethod[searchIndex] == 2 && strcasestr(MyName,StoredUser[searchIndex]) != -1 )
		{
			if ( !MatchFound ) {    // only call welcome_user one time per user
				welcome_user(MyName);
				MatchFound = 1;
			}
			snprintf(Text, MAX_TEXT_LENGTH, "--Message for %s >> %s", StoredUser[searchIndex], Messages[searchIndex]);
			messageex(MyName,Text,print_chat);
#if DEBUG
			log(Text);
#endif
		}
 
		if ( MatchMethod[searchIndex] == 3 && streq(MyIP,StoredUser[searchIndex]) == 1 )
		{
			if ( !MatchFound ) {    // only call welcome_user one time per user
				welcome_user(MyName);
				MatchFound = 1;
			}
			snprintf(Text, MAX_TEXT_LENGTH, "--Message for %s >> %s", StoredUser[searchIndex], Messages[searchIndex]);
			messageex(MyName,Text,print_chat);
#if DEBUG
			log(Text);
#endif
		}
 
		if ( MatchMethod[searchIndex] == 4 && streq(MyAuthID,StoredUser[searchIndex]) == 1 )
		{
			if ( !MatchFound ) {    // only call welcome_user one time per user
				welcome_user(MyName);
				MatchFound = 1;
			}
			snprintf(Text, MAX_TEXT_LENGTH, "--Message for %s >> %s", StoredUser[searchIndex], Messages[searchIndex]);
			messageex(MyName,Text,print_chat);
#if DEBUG
			log(Text);
#endif
		}
	}
	if ( !MatchFound ) {
		if ( bResend[UserIndex] == 1 ) {
			messageex(MyName, "Pager Plugin >> You have no messages.", print_chat);
			bResend[UserIndex] = 0;
		}
#if DEBUG
		snprintf(Text, MAX_TEXT_LENGTH, "No message found for %s", MyName);
		log(Text);
#endif
	}
}
 
public plugin_connect(HLUserName, HLIP, UserIndex)
{
	convert_string(HLIP, MyWholeIP[UserIndex], MAX_IPADDRESS+6);
	ConnHandled[UserIndex] = 0;
#if DEBUG
	new Text[MAX_TEXT_LENGTH];
	snprintf(Text, MAX_TEXT_LENGTH, "Connecting IP address: %s", MyWholeIP[UserIndex]);
	log(Text);
#endif
 
	return PLUGIN_CONTINUE;
}
 
public plugin_disconnect(HLUserName, UserIndex)
{
	if ( UserIndex >= 1 && UserIndex <= MAX_PLAYERS )
	{
		strinit(MyWholeIP[UserIndex]);
		ConnHandled[UserIndex] = 0;
	}
 
	return PLUGIN_CONTINUE;
}
 
public HandleSpecMode(HLCommand, HLData, HLUserName, UserIndex)
{
	new MyUserName[MAX_NAME_LENGTH];
	convert_string(HLUserName, MyUserName, MAX_NAME_LENGTH);
 
	if ( (UserIndex >= 1) && (UserIndex <= MAX_PLAYERS) && (PagerEnabled == 1) && (!ConnHandled[UserIndex]) ) {
		MsgTimer[UserIndex] = set_timer("MsgTrigger",20,0,MyUserName);
		ConnHandled[UserIndex] = 1;
#if DEBUG
		log("MsgTrigger called for 20 seconds.");
#endif
		return PLUGIN_CONTINUE;
	}
#if DEBUG
	log("No MsgTrigger called.");
#endif
 
	return PLUGIN_CONTINUE;
}
 
 
 
//////////////////////////////////////////////////////
// Originally from plugin_sank_sounds, by Luke Sankey
// Modified March 30, 2003 by HunteR
// to "speak" instead of "play"
////////////////////////////////////
playsoundall(sound[], IfDead = -1)
{
	new maxplayers = maxplayercount();
	new Name[MAX_NAME_LENGTH];
	new Text[MAX_TEXT_LENGTH];
	new i;
 
	strstripquotes(sound);
	strtrim(sound," ^t");
 
	snprintf(Text, MAX_TEXT_LENGTH, "speak ^"%s^"", sound);
	for(i=1; i<=maxplayers; i++)
	{
		new iDead;
		new dummy;
		if (playerinfo(i, Name, MAX_NAME_LENGTH, dummy, dummy, dummy, iDead) == 1)
		{
			if (IfDead == -1)
				execclient(Name, Text);
			else if (IfDead == iDead)
				execclient(Name, Text);
		}
	}
}