All pastes #208200 Raw Edit

YSS_messages.pwn

public text v1 · immutable
#208200 ·published 2006-10-18 13:57 UTC
rendered paste body
/*

Alex "Y_Less" Cole's server system

 - auto messages system (inc MOTD)

Messaging system, periodically sends messages to all server members
as well as specific ones on connect or spawn (MOTD style)
Based on previous messaging systems I have produced but much improved.

Features:

Messages read from file

Commands:

*/

#include <a_samp>
#include "YSScommon.pwn"

#define YS_MESSAGES_ON  // Always on
//#define YS_MESSAGES_SEL // INI defined

#define SEND_MESSAGE_ALL(%1) if (gMessages[d][MS_TEXT_%1][0]) CallRemoteFunction("SendFormattedMessageToAll", "is", c, gMessages[d][MS_TEXT_%1]);
#define SEND_MESSAGE(%1) if (gMessages[d][MS_TEXT_%1][0]) CallRemoteFunction("SendFormattedMessage", "iis", playerid, c, gMessages[d][MS_TEXT_%1]);

#define YS_MAX_MESSAGES 16

#define MS_BITS_MOTD		0x000000FF
#define MS_BITS_COUNT		0x0000FF00
#define MS_BITS_MOTD_SPAWN	0x01000000
#define MS_BITS_MOTD_CONN	0x02000000
#define MS_BITS_MOTD_INC	0x04000000
#define MS_BITS_USE			0x08000000

new gMessageDat = 0xFFFFFFFF;
//new gLastMessage;
new gMessageDelay = 1500; // 5 mins
//new gMessageCount = 0;

#define MS_TYPE_IGNORE 0x00010000

#define __NONE__				group = 0;
#define YS_INI_MESSAGES			1
#define YS_INI_MEMBERLEVELS		2
#define YS_INI_COMMANDLEVELS	3
#define YS_INI_ALTNAMES			4
#define YS_INI_SETTINGS			5
#define YS_INI_IGNORECOMMANDS	6
#define YS_INI_FILTERCOMMANDS	7
#define YS_INI_LOGGING			8

enum YS_MESSAGE_DAT
{
	MS_TYPE, // 0xFFFF0000 - info, 0x0000FFFF - type
	MS_INFO, // Color or display time depending on MS_TYPE
	MS_TEXT_0[MAX_INI_LINE],
	MS_TEXT_1[MAX_INI_LINE],
	MS_TEXT_2[MAX_INI_LINE],
	MS_TEXT_3[MAX_INI_LINE],
	MS_TEXT_4[MAX_INI_LINE]
}

new gMessages[YS_MAX_MESSAGES][YS_MESSAGE_DAT];

forward YSProcess();
forward ReadINI(update);

public OnFilterScriptInit()
{
	ADD_MODULE("messages", "YSS messages module v0.1 (c) Alex \"Y_Less\" Cole")
	READINI

	return 1;
}

public OnFilterScriptExit()
{
	REMOVE_MODULE("messages")
	return 1;
}

public OnPlayerSpawn(playerid)
{
	if (gMessageDat & MS_BITS_MOTD_SPAWN)
	{
		if ((gMessageDat & MS_BITS_MOTD) != 0xFF)
		{
			DisplayMessage(playerid, (gMessageDat & MS_BITS_MOTD));
		}
	}
}

public OnPlayerConnect(playerid)
{
	if (gMessageDat & MS_BITS_MOTD_CONN)
	{
		if ((gMessageDat & MS_BITS_MOTD) != 0xFF)
		{
			DisplayMessage(playerid, (gMessageDat & MS_BITS_MOTD));
		}
	}
}

public YSProcess()
{
	PRIORITY(gMessageDelay)
	{
		#if !defined YS_MESSAGES_ON
			if (gMessageDat & MS_BITS_USE)
			{
		#endif
				DisplayMessage();
		#if !defined YS_MESSAGES_ON
			}
		#endif
	}
}

DisplayMessage(playerid = INVALID_PLAYER_ID, d = 255)
{
	if (d == 255)
	{
		do
		{
			d = random((gMessageDat & MS_BITS_COUNT) >>> 8);
		}
		while (/*d == 255 || */((gMessageDat & MS_BITS_MOTD) == d && !(gMessageDat & MS_BITS_MOTD_INC)) || (MS_TYPE_IGNORE & gMessages[d][MS_TYPE]));
	}
	if (playerid == INVALID_PLAYER_ID)
	{
		if (gMessages[d][MS_TYPE] & 0xFFFF)
		{
			CallRemoteFunction("GameFormattedMessageToAll", "sii", gMessages[d][MS_TEXT_0], gMessages[d][MS_INFO] * 1000, gMessages[d][MS_TYPE] & 0xFFFF);
		}
		else
		{
			new c = gMessages[d][MS_INFO];
			SEND_MESSAGE_ALL(0)
			SEND_MESSAGE_ALL(1)
			SEND_MESSAGE_ALL(2)
			SEND_MESSAGE_ALL(3)
			SEND_MESSAGE_ALL(4)
		}
	}
	else
	{
		if (gMessages[d][MS_TYPE] & 0xFFFF)
		{
			CallRemoteFunction("GameFormattedMessage", "isii", playerid, gMessages[d][MS_TEXT_0], gMessages[d][MS_INFO] * 1000, gMessages[d][MS_TYPE] & 0xFFFF);
		}
		else
		{
			new c = gMessages[d][MS_INFO];
			SEND_MESSAGE(0)
			SEND_MESSAGE(1)
			SEND_MESSAGE(2)
			SEND_MESSAGE(3)
			SEND_MESSAGE(4)
		}
	}
}

public ReadINI(update)
{
	new File:inifile;
	if (fexist(INI_NAME))
	{
		inifile = fopen(INI_NAME, io_read);
		if (inifile)
		{
			new mc = 0;
			new intext = 0;
			new str[MAX_INI_LINE];
			new group = 0;
			new timed = 0;
			while (fread(inifile, str))
			{
				// Read line first
				if (str[0] == '[')
				{
					StripNL(str);
					INI_GROUP(MESSAGES)
					else INI_GROUP(SETTINGS)
					else __NONE__
				}
				else
				{
					switch (group)
					{
						case YS_INI_MESSAGES:
						{
							//INIT // Do multiply
							if (!intext)
							{
								if (mc < YS_MAX_MESSAGES)
								{
									INI_GET_B(Ignore, MS_TYPE_IGNORE, 6, gMessages[mc][MS_TYPE])
									else if (strcmp(str, "Type", true, 4) == 0)
									{
										gMessages[mc][MS_TYPE] &= 0xFFFF0000;
										gMessages[mc][MS_TYPE] += strval(ReturnINIValue(str[4]));
									}
									else INI_GET_H(Color, gMessages[mc][MS_INFO], 5)
									else INI_GET_I(Time, gMessages[mc][MS_INFO], 4)
									else INI_GET_B(Spawn, MS_BITS_MOTD_SPAWN, 5, gMessageDat)
									else INI_GET_B(Connect, MS_BITS_MOTD_CONN, 7, gMessageDat)
									//else if (strcmp(str, "Connect", true, 7) == 0) { if (strval(ReturnINIValue(str[7]))) { gMessageDat &= -1 ^ MS_BITS_MOTD_TYPE; } else { gMessageDat |= MS_BITS_MOTD_TYPE; } }
									//else if (strcmp(str, "Spawn", true, 5) == 0) { if (strval(ReturnINIValue(str[7]))) { gMessageDat |= MS_BITS_MOTD_TYPE; } else { gMessageDat &= -1 ^ MS_BITS_MOTD_TYPE; } }
									else INI_GET_B(Include, MS_BITS_MOTD_INC, 7, gMessageDat)
									else if (strcmp(str, "Motd", true, 4) == 0)
									{
										gMessageDat &= 0xFFFFFF00;
										if (strval(ReturnINIValue(str[4])))
										{
											gMessageDat |= mc & 0xFF;
										}
										else
										{
											gMessageDat |= 0xFF;
										}
									}
									else if (strcmp(str, "Text", true, 4) == 0)
									{
										intext = 1;
									}
								}
								else
								{
									print("YSS warning: Max messages reached");
									intext = -1;
								}
							}
							else if (intext > 0)
							{
								if (str[0] > 0x20)
								{
									StripNL(str);
									switch (intext)
									{
										case 1:
										{
											format(gMessages[mc][MS_TEXT_0], MAX_INI_LINE, "%s", str);
										}
										case 2:
										{
											format(gMessages[mc][MS_TEXT_1], MAX_INI_LINE, "%s", str);
										}
										case 3:
										{
											format(gMessages[mc][MS_TEXT_2], MAX_INI_LINE, "%s", str);
										}
										case 4:
										{
											format(gMessages[mc][MS_TEXT_3], MAX_INI_LINE, "%s", str);
										}
										case 5:
										{
											format(gMessages[mc][MS_TEXT_4], MAX_INI_LINE, "%s", str);
										}
										default:
										{
											intext = -1;
										}
									}
									intext++;
								}
								else
								{
									intext = 0;
									mc++;
								}
							}
						}
						case YS_INI_SETTINGS:
						{
							INIT
							INI_GET_B(UseMessages, MS_BITS_USE, 11, gMessageDat)
							else if (strcmp(str, "MessageDelay", true, 12) == 0)
							{
								gMessageDelay = strval(ReturnINIValue(str[12]));
								timed = 1;
							}
						}
					}
				}
			}
			gMessageDat &= 0xFFFF00FF;
			new c;
			for (new i = 0; i < YS_MAX_MESSAGES; i++)
			{
				if (gMessages[i][MS_TEXT_0][0] != 0)
				{
					c++;
				}
			}
			gMessageDat |= (c << 8) & MS_BITS_COUNT;
			if (timed)
			{
				gMessageDelay /= PROCESS_LOOP_DELAY; // Account for the calling frequency
			}
		}
		else
		{
			print("YSS warning: Could not read ini file, default settings loaded");
		}
	}
	else
	{
	    print("YSS warning: Could not find ini file, default settings loaded");
	}
}

hexval(string[])
{
	new m = 0;
	if (string[0] == '0' && string[1] == 'x') m = 2;
	new ret = 0;
	for (new i = m, j = 28; i < 8 + m; i++, j -= 4)
	{
		new k = string[i];
		if (k >= '0' && k <= '9')
		{
		    ret += (k - 0x30) << j;
		}
		else if (k >= 'A' && k <= 'F')
		{
		    ret += (k - 0x37) << j;
		}
		else if (k >= 'a' && k <= 'f')
		{
		    ret += (k - 0x57) << j;
		}
		else
		{
		    return 0;
		}
	}
	return ret;
}