More updates

This commit is contained in:
Jackz 2023-05-02 09:05:27 -05:00
parent 98ec7a34fa
commit a52f053082
No known key found for this signature in database
GPG key ID: E0BBD94CF657F603
8 changed files with 305 additions and 156 deletions

Binary file not shown.

Binary file not shown.

Binary file not shown.

View file

@ -40,7 +40,7 @@ int g_iLaserIndex;
static char FORBIDDEN_CLASSNAMES[MAX_FORBIDDEN_CLASSNAMES][] = { static char FORBIDDEN_CLASSNAMES[MAX_FORBIDDEN_CLASSNAMES][] = {
// "env_physics_blocker", // "env_physics_blocker",
// "env_player_blocker", // "env_player_blocker",
// "func_brush", "func_brush",
"func_simpleladder", "func_simpleladder",
"func_button", "func_button",
"func_elevator", "func_elevator",
@ -48,10 +48,10 @@ static char FORBIDDEN_CLASSNAMES[MAX_FORBIDDEN_CLASSNAMES][] = {
// "func_movelinear", // "func_movelinear",
// "infected", // "infected",
"func_lod", "func_lod",
"func_door",
"prop_ragdoll" "prop_ragdoll"
}; };
#define MAX_HIGHLIGHTED_CLASSNAMES 3 #define MAX_HIGHLIGHTED_CLASSNAMES 3
static char HIGHLIGHTED_CLASSNAMES[MAX_HIGHLIGHTED_CLASSNAMES][] = { static char HIGHLIGHTED_CLASSNAMES[MAX_HIGHLIGHTED_CLASSNAMES][] = {
"env_physics_blocker", "env_physics_blocker",
@ -59,6 +59,7 @@ static char HIGHLIGHTED_CLASSNAMES[MAX_HIGHLIGHTED_CLASSNAMES][] = {
"func_brush" "func_brush"
} }
public void OnPluginStart() public void OnPluginStart()
{ {
RegAdminCmd("sm_grabent_freeze", Cmd_ReleaseFreeze, ADMFLAG_CHEATS, "<0/1> - Toggle entity freeze/unfreeze on release."); RegAdminCmd("sm_grabent_freeze", Cmd_ReleaseFreeze, ADMFLAG_CHEATS, "<0/1> - Toggle entity freeze/unfreeze on release.");
@ -139,6 +140,12 @@ public Action Cmd_Grab(client, args) {
if (ent == -1 || !IsValidEntity(ent)) if (ent == -1 || !IsValidEntity(ent))
return Plugin_Handled; //<-- timer to allow search for entity?? return Plugin_Handled; //<-- timer to allow search for entity??
// Grab the parent
int parent = GetEntPropEnt(ent, Prop_Data, "m_hParent");
if(parent > 0) {
ent = parent;
}
float entOrigin[3], playerGrabOrigin[3]; float entOrigin[3], playerGrabOrigin[3];
GetEntPropVector(ent, Prop_Send, "m_vecOrigin", entOrigin); GetEntPropVector(ent, Prop_Send, "m_vecOrigin", entOrigin);
GetClientEyePosition(client, playerGrabOrigin); GetClientEyePosition(client, playerGrabOrigin);
@ -238,7 +245,7 @@ public Action Timer_UpdateGrab(Handle timer, DataPack pack) {
char targetname[64]; char targetname[64];
GetEntPropString(g_pGrabbedEnt[client], Prop_Data, "m_iName", targetname, sizeof(targetname)); GetEntPropString(g_pGrabbedEnt[client], Prop_Data, "m_iName", targetname, sizeof(targetname));
PrintCenterText(client, "%s", targetname); PrintCenterText(client, "%s", targetname);
GlowEntity(g_pGrabbedEnt[client]); GlowEntity(client, g_pGrabbedEnt[client]);
} }
// *** Enable/Disable Rotation Mode // *** Enable/Disable Rotation Mode
@ -525,13 +532,13 @@ stock void CreateRing(int client, float ang[3], float pos[3], float diameter, in
} }
} }
void GlowEntity(int entity) { void GlowEntity(int client, int entity) {
float pos[3], mins[3], maxs[3], angles[3]; float pos[3], mins[3], maxs[3], angles[3];
GetEntPropVector(entity, Prop_Send, "m_angRotation", angles); GetEntPropVector(entity, Prop_Send, "m_angRotation", angles);
GetEntPropVector(entity, Prop_Send, "m_vecOrigin", pos); GetEntPropVector(entity, Prop_Send, "m_vecOrigin", pos);
GetEntPropVector(entity, Prop_Send, "m_vecMins", mins); GetEntPropVector(entity, Prop_Send, "m_vecMins", mins);
GetEntPropVector(entity, Prop_Send, "m_vecMaxs", maxs); GetEntPropVector(entity, Prop_Send, "m_vecMaxs", maxs);
Effect_DrawBeamBoxRotatableToAll(pos, mins, maxs, angles, g_iLaserIndex, 0, 0, 30, 0.1, 0.4, 0.4, 0, 0.1, { 0, 255, 0, 235 }, 0); Effect_DrawBeamBoxRotatableToClient(client, pos, mins, maxs, angles, g_iLaserIndex, 0, 0, 30, 0.1, 0.4, 0.4, 0, 0.1, { 0, 255, 0, 235 }, 0);
} }
//============================================================================ //============================================================================

View file

@ -739,3 +739,33 @@ stock void HSVToRGBInt(const float vec[3], int out[3]) {
out[1] = RoundToFloor(view_as<float>(out[1])); out[1] = RoundToFloor(view_as<float>(out[1]));
out[2] = RoundToFloor(view_as<float>(out[2])); out[2] = RoundToFloor(view_as<float>(out[2]));
} }
// Gets a position from where the cursor is upto distance away (basically <= distance, going against walls)
stock bool GetCursorLimited(int client, float distance, float endPos[3], TraceEntityFilter filter)
{
if (client > 0 && client <= MaxClients && IsClientInGame(client)) {
float clientEye[3], clientAngle[3], direction[3];
GetClientEyePosition(client, clientEye);
GetClientEyeAngles(client, clientAngle);
GetAngleVectors(clientAngle, direction, NULL_VECTOR, NULL_VECTOR);
ScaleVector(direction, distance);
AddVectors(clientEye, direction, endPos);
TR_TraceRayFilter(clientEye, endPos, MASK_OPAQUE, RayType_EndPoint, filter, client);
if (TR_DidHit(INVALID_HANDLE)) {
TR_GetEndPosition(endPos);
}
return true;
}
return false;
}
stock void SetWeaponDelay(int client, float delay) {
int pWeapon = GetEntPropEnt(client, Prop_Send, "m_hActiveWeapon");
if (pWeapon > -1) {
SetEntPropFloat(pWeapon, Prop_Send, "m_flNextPrimaryAttack", GetGameTime() + delay);
SetEntPropFloat(pWeapon, Prop_Send, "m_flNextSecondaryAttack", GetGameTime() + delay);
}
}

View file

@ -0,0 +1,13 @@
#if defined _player_notes_included_
#endinput
#endif
#define _player_notes_included_
void AddNote(int noteCreator, int noteTarget, const char[] message) {
char steamidCreator[32], steamidTarget[32];
GetClientAuthId(noteCreator, AuthId_Steam2, steamidCreator, sizeof(steamidCreator));
GetClientAuthId(noteTarget, AuthId_Steam2, steamidTarget, sizeof(steamidTarget));
AddNoteIdentity(steamidCreator, steamidTarget, message);
}
native void AddNoteIdentity(const char noteCreator[32], const char noteTarget[32], const char[] message);

View file

@ -57,6 +57,7 @@ enum hatFeatures {
HatData hatData[MAXPLAYERS+1]; HatData hatData[MAXPLAYERS+1];
int lastHatRequestTime[MAXPLAYERS+1], g_iLaserIndex; int lastHatRequestTime[MAXPLAYERS+1], g_iLaserIndex;
bool tempGod[MAXPLAYERS+1]; bool tempGod[MAXPLAYERS+1];
bool inSaferoom[MAXPLAYERS+1];
static float cmdThrottle[MAXPLAYERS+1]; static float cmdThrottle[MAXPLAYERS+1];
static bool onLadder[MAXPLAYERS+1]; static bool onLadder[MAXPLAYERS+1];
@ -116,36 +117,37 @@ enum struct WallBuilderData {
int snapAngle; int snapAngle;
int movetype; int movetype;
int moveSpeed; int moveSpeed;
float movedistance; float moveDistance;
int entity; int entity;
bool canScale;
void Reset() { void Reset() {
this.size[0] = this.size[1] = this.size[2] = 5.0; this.size[0] = this.size[1] = this.size[2] = 5.0;
this.angles[0] = this.angles[1] = this.angles[2] = 0.0; this.angles[0] = this.angles[1] = this.angles[2] = 0.0;
this.axis = 0; this.axis = 0;
this.movetype = 0; this.movetype = 0;
this.movedistance = 100.0; this.canScale = true;
this.moveDistance = 100.0;
this.moveSpeed = 1; this.moveSpeed = 1;
this.snapAngle = 30; this.snapAngle = 30;
this.entity = INVALID_ENT_REFERENCE; this.entity = INVALID_ENT_REFERENCE;
this.CalculateMinMax(); this.CalculateMins();
this.SetMode(INACTIVE); this.SetMode(INACTIVE);
} }
void CalculateMinMax() { void CalculateMins() {
this.mins[0] = -this.size[0]; this.mins[0] = -this.size[0];
this.mins[1] = -this.size[1]; this.mins[1] = -this.size[1];
this.mins[2] = -this.size[2]; this.mins[2] = -this.size[2];
} }
void Draw(int color[4], float lifetime, float amplitude = 0.1) { void Draw(int color[4], float lifetime, float amplitude = 0.1) {
Effect_DrawAxisOfRotationToAll(this.origin, this.angles, ORIGIN_SIZE, g_iLaserIndex, 0, 0, 30, 0.2, 0.1, 0.1, 0, 0.0, 0); if(!this.canScale && this.entity != INVALID_ENT_REFERENCE) {
Effect_DrawBeamBoxRotatableToAll(this.origin, this.mins, this.size, this.angles, g_iLaserIndex, 0, 0, 30, lifetime, 0.4, 0.4, 0, amplitude, color, 0);
if(this.entity != INVALID_ENT_REFERENCE) {
TeleportEntity(this.entity, this.origin, this.angles, NULL_VECTOR); TeleportEntity(this.entity, this.origin, this.angles, NULL_VECTOR);
SetEntPropVector(this.entity, Prop_Send, "m_vecMins", this.mins); } else {
SetEntPropVector(this.entity, Prop_Send, "m_vecMaxs", this.size); Effect_DrawBeamBoxRotatableToAll(this.origin, this.mins, this.size, this.angles, g_iLaserIndex, 0, 0, 30, lifetime, 0.4, 0.4, 0, amplitude, color, 0);
} }
Effect_DrawAxisOfRotationToAll(this.origin, this.angles, ORIGIN_SIZE, g_iLaserIndex, 0, 0, 30, 0.2, 0.1, 0.1, 0, 0.0, 0);
} }
bool IsActive() { bool IsActive() {
@ -156,8 +158,10 @@ enum struct WallBuilderData {
this.mode = mode; this.mode = mode;
} }
void CycleMode(int client, float tick, bool moveForward = true) { void CycleMode(int client, float tick) {
if(tick - cmdThrottle[client] <= 0.25) return; if(tick - cmdThrottle[client] <= 0.25) return;
int flags = GetEntityFlags(client) & ~FL_FROZEN;
SetEntityFlags(client, flags);
switch(this.mode) { switch(this.mode) {
// MODES: // MODES:
// - MOVE (cursor point) // - MOVE (cursor point)
@ -165,7 +169,7 @@ enum struct WallBuilderData {
// - SCALE // - SCALE
// - FREECAM // - FREECAM
case MOVE_ORIGIN: { case MOVE_ORIGIN: {
if(moveForward) { if(this.canScale) {
this.mode = SCALE; this.mode = SCALE;
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Scale\x01"); PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Scale\x01");
} else { } else {
@ -174,34 +178,13 @@ enum struct WallBuilderData {
} }
} }
case SCALE: { case SCALE: {
if(moveForward) { this.mode = FREELOOK;
this.mode = ROTATE; PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Freelook\x01");
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Rotate\x01");
} else {
this.mode = MOVE_ORIGIN;
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Move\x01");
PrintToChat(client, "Controls: \x05RELOAD\x01 to change mode");
}
}
case ROTATE: {
if(moveForward) {
this.mode = FREELOOK;
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Freelook\x01");
} else {
this.mode = SCALE;
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Scale\x01");
}
} }
case FREELOOK: { case FREELOOK: {
if(moveForward) { this.mode = MOVE_ORIGIN;
this.mode = MOVE_ORIGIN; PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Move & Rotate\x01");
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Move Origin\x01"); // PrintToChat(client, "Controls: \x05RELOAD\x01 to change mode");
PrintToChat(client, "Controls: \x05RELOAD\x01 to change mode");
} else {
this.mode = ROTATE;
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Rotate\x01");
PrintToChat(client, "Controls: \x05RELOAD\x01 to change axis");
}
} }
} }
cmdThrottle[client] = tick; cmdThrottle[client] = tick;
@ -271,6 +254,10 @@ enum struct WallBuilderData {
} }
int Build() { int Build() {
if(!this.canScale) {
this.Reset();
return -3;
}
// Don't need to build a new one if we editing: // Don't need to build a new one if we editing:
int blocker = this.entity; int blocker = this.entity;
bool isEdit = true; bool isEdit = true;
@ -301,9 +288,12 @@ enum struct WallBuilderData {
enteffects |= 32; //EF_NODRAW enteffects |= 32; //EF_NODRAW
SetEntProp(blocker, Prop_Send, "m_fEffects", enteffects); SetEntProp(blocker, Prop_Send, "m_fEffects", enteffects);
AcceptEntityInput(blocker, "Enable"); AcceptEntityInput(blocker, "Enable");
} else {
TeleportEntity(this.entity, this.origin, this.angles, NULL_VECTOR);
SetEntPropVector(this.entity, Prop_Send, "m_vecMins", this.mins);
SetEntPropVector(this.entity, Prop_Send, "m_vecMaxs", this.size);
} }
this.Draw(WALL_COLOR, 5.0, 1.0); this.Draw(WALL_COLOR, 5.0, 1.0);
this.Reset(); this.Reset();
return isEdit ? -2 : createdWalls.Push(EntIndexToEntRef(blocker)); return isEdit ? -2 : createdWalls.Push(EntIndexToEntRef(blocker));
@ -322,9 +312,6 @@ enum struct WallBuilderData {
} }
} }
stock float SnapTo(const float value, const float degree) {
return float(RoundFloat(value / degree)) * degree;
}
WallBuilderData WallBuilder[MAXPLAYERS+1]; WallBuilderData WallBuilder[MAXPLAYERS+1];
public Plugin myinfo = public Plugin myinfo =
@ -348,6 +335,7 @@ public void OnPluginStart() {
LoadTranslations("common.phrases"); LoadTranslations("common.phrases");
HookEvent("player_entered_checkpoint", OnEnterSaferoom); HookEvent("player_entered_checkpoint", OnEnterSaferoom);
HookEvent("player_left_checkpoint", OnLeaveSaferoom);
HookEvent("player_bot_replace", Event_PlayerOutOfIdle ); HookEvent("player_bot_replace", Event_PlayerOutOfIdle );
HookEvent("bot_player_replace", Event_PlayerToIdle); HookEvent("bot_player_replace", Event_PlayerToIdle);
@ -355,6 +343,9 @@ public void OnPluginStart() {
RegAdminCmd("sm_wall", Command_MakeWall, ADMFLAG_CHEATS); RegAdminCmd("sm_wall", Command_MakeWall, ADMFLAG_CHEATS);
RegAdminCmd("sm_walls", Command_ManageWalls, ADMFLAG_CHEATS); RegAdminCmd("sm_walls", Command_ManageWalls, ADMFLAG_CHEATS);
AddCommandListener(Command_ScrollWheelUp, "invnext");
AddCommandListener(Command_ScrollWheelDown, "invprev");
cvar_sm_hats_blacklist_enabled = CreateConVar("sm_hats_blacklist_enabled", "1", "Is the prop blacklist enabled", FCVAR_NONE, true, 0.0, true, 1.0); cvar_sm_hats_blacklist_enabled = CreateConVar("sm_hats_blacklist_enabled", "1", "Is the prop blacklist enabled", FCVAR_NONE, true, 0.0, true, 1.0);
cvar_sm_hats_enabled = CreateConVar("sm_hats_enabled", "1.0", "Enable hats.\n0=OFF, 1=Admins Only, 2=Any", FCVAR_NONE, true, 0.0, true, 2.0); cvar_sm_hats_enabled = CreateConVar("sm_hats_enabled", "1.0", "Enable hats.\n0=OFF, 1=Admins Only, 2=Any", FCVAR_NONE, true, 0.0, true, 2.0);
cvar_sm_hats_enabled.AddChangeHook(Event_HatsEnableChanged); cvar_sm_hats_enabled.AddChangeHook(Event_HatsEnableChanged);
@ -460,7 +451,8 @@ public Action Command_DoAHat(int client, int args) {
SetEntProp(entity, Prop_Send, "m_CollisionGroup", hatData[client].collisionGroup); SetEntProp(entity, Prop_Send, "m_CollisionGroup", hatData[client].collisionGroup);
SetEntProp(entity, Prop_Send, "m_nSolidType", hatData[client].solidType); SetEntProp(entity, Prop_Send, "m_nSolidType", hatData[client].solidType);
int flags = ~GetEntityFlags(entity) & FL_FROZEN;
SetEntityFlags(entity, flags);
int visibleEntity = EntRefToEntIndex(hatData[client].visibleEntity); int visibleEntity = EntRefToEntIndex(hatData[client].visibleEntity);
SDKUnhook(entity, SDKHook_SetTransmit, OnRealTransmit); SDKUnhook(entity, SDKHook_SetTransmit, OnRealTransmit);
if(visibleEntity > 0) { if(visibleEntity > 0) {
@ -517,8 +509,8 @@ public Action Command_DoAHat(int client, int args) {
hatData[client].visibleEntity = INVALID_ENT_REFERENCE; hatData[client].visibleEntity = INVALID_ENT_REFERENCE;
hatData[client].entity = INVALID_ENT_REFERENCE; hatData[client].entity = INVALID_ENT_REFERENCE;
} */ else { } */ else {
GetHorizontalPositionFromClient(client, 10.0, hatData[client].orgPos); GetHorizontalPositionFromClient(client, 80.0, hatData[client].orgPos);
hatData[client].orgPos[2] += 5.0; hatData[client].orgPos[2] += 35.0;
TeleportEntity(entity, hatData[client].orgPos, hatData[client].orgAng, vel); TeleportEntity(entity, hatData[client].orgPos, hatData[client].orgAng, vel);
CreateTimer(6.0, Timer_PropSleep, hatData[client].entity); CreateTimer(6.0, Timer_PropSleep, hatData[client].entity);
} }
@ -559,7 +551,13 @@ public Action Command_DoAHat(int client, int args) {
TeleportEntity(entity, hatData[client].orgPos, hatData[client].orgAng, NULL_VECTOR); TeleportEntity(entity, hatData[client].orgPos, hatData[client].orgAng, NULL_VECTOR);
// hatData[client].orgPos[2] = mins[2]; // hatData[client].orgPos[2] = mins[2];
PrintToChat(client, "[Hats] Placed hat in front of you."); PrintToChat(client, "[Hats] Placed hat in front of you.");
} else { } else if(arg[0] == 'd') {
WallBuilder[client].Reset();
WallBuilder[client].entity = EntIndexToEntRef(entity);
WallBuilder[client].canScale = false;
WallBuilder[client].SetMode(SCALE);
PrintToChat(client, "\x04[Walls] \x01Beta Prop Mover active for \x04%d", entity);
} else {
PrintToChat(client, "[Hats] Restored hat to its original position."); PrintToChat(client, "[Hats] Restored hat to its original position.");
} }
@ -571,7 +569,7 @@ public Action Command_DoAHat(int client, int args) {
hatData[client].entity = INVALID_ENT_REFERENCE; hatData[client].entity = INVALID_ENT_REFERENCE;
} else { } else {
int flags = 0; int flags = 0;
entity = GetLookingEntity(client, Filter_IgnorePlayer); //GetClientAimTarget(client, false); entity = GetLookingEntity(client, Filter_ValidHats); //GetClientAimTarget(client, false);
if(entity <= 0) { if(entity <= 0) {
PrintCenterText(client, "[Hats] No entity found"); PrintCenterText(client, "[Hats] No entity found");
} else { } else {
@ -590,6 +588,12 @@ public Action Command_DoAHat(int client, int args) {
if(GetClientTeam(entity) != 2 && ~cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_InfectedHats)) { if(GetClientTeam(entity) != 2 && ~cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_InfectedHats)) {
PrintToChat(client, "[Hats] Cannot make enemy a hat... it's dangerous"); PrintToChat(client, "[Hats] Cannot make enemy a hat... it's dangerous");
return Plugin_Handled; return Plugin_Handled;
} else if(entity == EntRefToEntIndex(WallBuilder[client].entity)) {
PrintToChat(client, "[Hats] You are currently editing this entity");
return Plugin_Handled;
} else if(inSaferoom[client] && cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_NoSaferoomHats)) {
PrintToChat(client, "[Hats] Hats are not allowed in the saferoom");
return Plugin_Handled;
} else if(!IsPlayerAlive(entity) || GetEntProp(entity, Prop_Send, "m_isHangingFromLedge") || L4D_IsPlayerCapped(entity)) { } else if(!IsPlayerAlive(entity) || GetEntProp(entity, Prop_Send, "m_isHangingFromLedge") || L4D_IsPlayerCapped(entity)) {
PrintToChat(client, "[Hats] Player is either dead, hanging or in the process of dying."); PrintToChat(client, "[Hats] Player is either dead, hanging or in the process of dying.");
return Plugin_Handled; return Plugin_Handled;
@ -669,11 +673,15 @@ public Action Command_MakeWall(int client, int args) {
char arg1[16]; char arg1[16];
GetCmdArg(1, arg1, sizeof(arg1)); GetCmdArg(1, arg1, sizeof(arg1));
if(StrEqual(arg1, "build", false)) { if(StrEqual(arg1, "build", false)) {
int flags = GetEntityFlags(client) & ~FL_FROZEN;
SetEntityFlags(client, flags);
int id = WallBuilder[client].Build(); int id = WallBuilder[client].Build();
if(id == -1) { if(id == -1) {
PrintToChat(client, "\x04[Walls]\x01 Wall Creation: \x04Error\x01"); PrintToChat(client, "\x04[Walls]\x01 Wall Creation: \x04Error\x01");
} else if(id == -2) { } else if(id == -2) {
PrintToChat(client, "\x04[Walls]\x01 Wall Edit: \x04Complete\x01"); PrintToChat(client, "\x04[Walls]\x01 Wall Edit: \x04Complete\x01");
} else if(id == -3) {
PrintToChat(client, "\x04[Walls]\x01 Entity Edit: \x04Complete\x01");
} else { } else {
PrintToChat(client, "\x04[Walls]\x01 Wall Creation: \x05Wall #%d Created\x01", id + 1); PrintToChat(client, "\x04[Walls]\x01 Wall Creation: \x05Wall #%d Created\x01", id + 1);
} }
@ -685,6 +693,8 @@ public Action Command_MakeWall(int client, int args) {
PrintToChat(client, "\t\"size\" \"%.2f %.2f %.2f\"", WallBuilder[client].size[0], WallBuilder[client].size[1], WallBuilder[client].size[2]); PrintToChat(client, "\t\"size\" \"%.2f %.2f %.2f\"", WallBuilder[client].size[0], WallBuilder[client].size[1], WallBuilder[client].size[2]);
PrintToChat(client, "}"); PrintToChat(client, "}");
} else if(StrEqual(arg1, "cancel")) { } else if(StrEqual(arg1, "cancel")) {
int flags = GetEntityFlags(client) & ~FL_FROZEN;
SetEntityFlags(client, flags);
WallBuilder[client].SetMode(INACTIVE); WallBuilder[client].SetMode(INACTIVE);
PrintToChat(client, "\x04[Walls]\x01 Wall Creation: \x04Cancelled\x01"); PrintToChat(client, "\x04[Walls]\x01 Wall Creation: \x04Cancelled\x01");
} }
@ -695,6 +705,8 @@ public Action Command_MakeWall(int client, int args) {
} else { } else {
WallBuilder[client].Reset(); WallBuilder[client].Reset();
if(args > 0) { if(args > 0) {
// TODO: Determine axis
char arg2[8]; char arg2[8];
for(int i = 0; i < 3; i++) { for(int i = 0; i < 3; i++) {
GetCmdArg(i + 1, arg2, sizeof(arg2)); GetCmdArg(i + 1, arg2, sizeof(arg2));
@ -704,10 +716,19 @@ public Action Command_MakeWall(int client, int args) {
} }
WallBuilder[client].size[i] = value; WallBuilder[client].size[i] = value;
} }
WallBuilder[client].CalculateMinMax();
float rot[3];
GetClientEyeAngles(client, rot);
if(rot[2] > 45 && rot[2] < 135 || rot[2] > -135 && rot[2] < -45) {
float temp = WallBuilder[client].size[0];
WallBuilder[client].size[0] = WallBuilder[client].size[1];
WallBuilder[client].size[1] = temp;
}
WallBuilder[client].CalculateMins();
} }
WallBuilder[client].SetMode(SCALE); WallBuilder[client].SetMode(SCALE);
GetCursorLocationLimited(client, 100.0, WallBuilder[client].origin); GetCursorLimited(client, 100.0, WallBuilder[client].origin, Filter_IgnorePlayer);
PrintToChat(client, "\x04[Walls]\x01 New Wall Started. End with \x05/wall build\x01 or \x04/wall cancel\x01"); PrintToChat(client, "\x04[Walls]\x01 New Wall Started. End with \x05/wall build\x01 or \x04/wall cancel\x01");
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Scale\x01"); PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Scale\x01");
} }
@ -718,7 +739,7 @@ public Action Command_ManageWalls(int client, int args) {
if(args == 0) { if(args == 0) {
PrintToChat(client, "\x04[Walls]\x01 Created Walls: \x05%d\x01", createdWalls.Length); PrintToChat(client, "\x04[Walls]\x01 Created Walls: \x05%d\x01", createdWalls.Length);
for(int i = 1; i <= createdWalls.Length; i++) { for(int i = 1; i <= createdWalls.Length; i++) {
GlowWall(i, 10.0); GlowWall(i, 20.0);
} }
return Plugin_Handled; return Plugin_Handled;
} }
@ -747,6 +768,7 @@ public Action Command_ManageWalls(int client, int args) {
for(int i = 1; i <= createdWalls.Length; i++) { for(int i = 1; i <= createdWalls.Length; i++) {
int entity = GetWallEntity(i); int entity = GetWallEntity(i);
AcceptEntityInput(entity, "Toggle"); AcceptEntityInput(entity, "Toggle");
GlowWall(i);
} }
PrintToChat(client, "\x04[Walls]\x01 Toggled \x05%d\x01 walls", walls); PrintToChat(client, "\x04[Walls]\x01 Toggled \x05%d\x01 walls", walls);
} else { } else {
@ -754,6 +776,7 @@ public Action Command_ManageWalls(int client, int args) {
if(id > -1) { if(id > -1) {
int entity = GetWallEntity(id); int entity = GetWallEntity(id);
AcceptEntityInput(entity, "Toggle"); AcceptEntityInput(entity, "Toggle");
GlowWall(id);
PrintToChat(client, "\x04[Walls]\x01 Toggled Wall: \x05#%d\x01", id); PrintToChat(client, "\x04[Walls]\x01 Toggled Wall: \x05#%d\x01", id);
} }
} }
@ -796,7 +819,7 @@ public Action Command_ManageWalls(int client, int args) {
if(id > -1) { if(id > -1) {
int entity = GetWallEntity(id); int entity = GetWallEntity(id);
WallBuilder[client].Import(entity, true); WallBuilder[client].Import(entity, true);
GetCursorLocationLimited(client, 100.0, WallBuilder[client].origin); GetCursorLimited(client, 100.0, WallBuilder[client].origin, Filter_IgnorePlayer);
PrintToChat(client, "\x04[Walls]\x01 Editing copy of wall \x05%d\x01. End with \x05/wall build\x01 or \x04/wall cancel\x01", id); PrintToChat(client, "\x04[Walls]\x01 Editing copy of wall \x05%d\x01. End with \x05/wall build\x01 or \x04/wall cancel\x01", id);
PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Scale\x01"); PrintToChat(client, "\x04[Walls]\x01 Mode: \x05Scale\x01");
} }
@ -809,6 +832,21 @@ public Action Command_ManageWalls(int client, int args) {
return Plugin_Handled; return Plugin_Handled;
} }
public Action Command_ScrollWheelUp(int client, const char[] command, int args) {
if(WallBuilder[client].IsActive()) {
WallBuilder[client].moveDistance++;
return Plugin_Handled;
}
return Plugin_Continue;
}
public Action Command_ScrollWheelDown(int client, const char[] command, int args) {
if(WallBuilder[client].IsActive()) {
WallBuilder[client].moveDistance--;
return Plugin_Handled;
}
return Plugin_Continue;
}
int GetWallId(int client, const char[] arg) { int GetWallId(int client, const char[] arg) {
int id; int id;
if(StringToIntEx(arg, id) > 0 && id > 0 && id <= createdWalls.Length) { if(StringToIntEx(arg, id) > 0 && id > 0 && id <= createdWalls.Length) {
@ -873,25 +911,36 @@ public void Event_ItemPickup(Event event, const char[] name, bool dontBroadcast)
} }
} }
// TODO: Possibly detect instead the hat itself entering saferoom // TODO: Possibly detect instead the hat itself entering saferoom
public void OnEnterSaferoom(Event event, const char[] name, bool dontBroadcast) { public void OnEnterSaferoom(Event event, const char[] name, bool dontBroadcast) {
int userid = event.GetInt("userid"); int userid = event.GetInt("userid");
int client = GetClientOfUserId(userid); int client = GetClientOfUserId(userid);
if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_NoSaferoomHats) && client > 0 && client <= MaxClients && IsValidClient(client) && GetClientTeam(client) == 2) { if(client > 0 && client <= MaxClients && IsValidClient(client) && GetClientTeam(client) == 2) {
if(HasHat(client)) { inSaferoom[client] = true;
if(!IsHatAllowed(client)) { if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_NoSaferoomHats)) {
PrintToChat(client, "[Hats] Hat is not allowed in the saferoom and has been returned"); if(HasHat(client)) {
ClearHat(client, true); if(!IsHatAllowed(client)) {
} else { PrintToChat(client, "[Hats] Hat is not allowed in the saferoom and has been returned");
CreateTimer(2.0, Timer_PlaceHat, userid); ClearHat(client, true);
// float maxflow = L4D2Direct_GetMapMaxFlowDistance() } else {
// L4D_GetNavArea_SpawnAttributes CreateTimer(2.0, Timer_PlaceHat, userid);
// L4D_GetNavAreaPos // float maxflow = L4D2Direct_GetMapMaxFlowDistance()
// L4D_GetNavArea_SpawnAttributes
// L4D_GetNavAreaPos
}
} }
} }
} }
} }
public void OnLeaveSaferoom(Event event, const char[] name, bool dontBroadcast) {
int userid = event.GetInt("userid");
int client = GetClientOfUserId(userid);
if(client > 0 && client <= MaxClients && IsValidClient(client) && GetClientTeam(client) == 2) {
inSaferoom[client] = false;
}
}
public void EntityOutput_OnStartTouchSaferoom(const char[] output, int caller, int client, float time) { public void EntityOutput_OnStartTouchSaferoom(const char[] output, int caller, int client, float time) {
if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_NoSaferoomHats) && client > 0 && client <= MaxClients && IsValidClient(client) && GetClientTeam(client) == 2) { if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_NoSaferoomHats) && client > 0 && client <= MaxClients && IsValidClient(client) && GetClientTeam(client) == 2) {
@ -981,20 +1030,6 @@ stock bool GetCursorLocation(int client, float outPos[3]) {
} }
} }
stock bool GetCursorLocationLimited(int client, float maxLength, float outPos[3]) {
float start[3], angle[3];
GetClientEyePosition(client, start);
GetClientEyeAngles(client, angle);
GetHorizontalPositionFromOrigin(start, angle, maxLength, outPos);
TR_TraceRayFilter(start, outPos, MASK_SOLID, RayType_EndPoint, Filter_NoPlayers, client);
if(TR_DidHit()) {
TR_GetEndPosition(outPos);
return true;
} else {
return false;
}
}
Action Timer_RemountHats(Handle h) { Action Timer_RemountHats(Handle h) {
float p1[3], p2[3]; float p1[3], p2[3];
for(int i = 1; i <= MaxClients; i++) { for(int i = 1; i <= MaxClients; i++) {
@ -1035,6 +1070,8 @@ void Frame_Remount(int i) {
} }
} }
// TODO: toggle highlight
// pick a diff model
Action Timer_PropSleep(Handle h, int ref) { Action Timer_PropSleep(Handle h, int ref) {
if(IsValidEntity(ref)) { if(IsValidEntity(ref)) {
if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_DeleteThrownHats)) { if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_DeleteThrownHats)) {
@ -1291,20 +1328,48 @@ public Action OnPlayerRunCmd(int client, int& buttons, int& impulse, float vel[3
///#WALL BUILDER PROCESS ///#WALL BUILDER PROCESS
if(WallBuilder[client].IsActive()) { if(WallBuilder[client].IsActive()) {
bool allowMove = true; bool allowMove = true;
SetWeaponDelay(client, 0.5);
switch(WallBuilder[client].mode) { switch(WallBuilder[client].mode) {
case MOVE_ORIGIN: { case MOVE_ORIGIN: {
SetWeaponDelay(client, 0.5);
switch(buttons) { switch(buttons) {
case IN_RELOAD: WallBuilder[client].CycleMoveMode(client, tick); case IN_SCORE: WallBuilder[client].CycleMoveMode(client, tick);
case IN_USE: WallBuilder[client].CycleSpeed(client, tick); case IN_ZOOM: WallBuilder[client].CycleSpeed(client, tick);
} }
if(WallBuilder[client].movetype == 0) { if(WallBuilder[client].movetype == 0) {
switch(buttons) { bool isRotate;
case IN_FORWARD: WallBuilder[client].movedistance++; int flags = GetEntityFlags(client);
case IN_BACK: WallBuilder[client].movedistance--; if(buttons & IN_USE) {
PrintCenterText(client, "%d %d", mouse[0], mouse[1]);
isRotate = true;
SetEntityFlags(client, flags |= FL_FROZEN);
if(buttons & IN_ATTACK) WallBuilder[client].CycleAxis(client, tick);
else if(buttons & IN_ATTACK2) WallBuilder[client].CycleSnapAngle(client, tick);
if(tick - cmdThrottle[client] > 0.25) {
if(WallBuilder[client].axis == 0) {
if(mouse[1] > 10) WallBuilder[client].angles[0] += WallBuilder[client].snapAngle;
else if(mouse[1] < -10) WallBuilder[client].angles[0] -= WallBuilder[client].snapAngle;
} else if(WallBuilder[client].axis == 1) {
if(mouse[0] > 10) WallBuilder[client].angles[1] += WallBuilder[client].snapAngle;
else if(mouse[0] < -10) WallBuilder[client].angles[1] -= WallBuilder[client].snapAngle;
}
cmdThrottle[client] = tick;
}
} else {
switch(buttons) {
case IN_ATTACK: WallBuilder[client].moveDistance++;
case IN_ATTACK2: WallBuilder[client].moveDistance--;
case IN_WALK: WallBuilder[client].CycleSnapAngle(client, tick);
}
} }
GetCursorLocationLimited(client, WallBuilder[client].movedistance, WallBuilder[client].origin); if(!isRotate && flags & FL_FROZEN) {
flags = ~flags & FL_FROZEN;
SetEntityFlags(client, flags);
}
GetCursorLimited(client, WallBuilder[client].moveDistance, WallBuilder[client].origin, Filter_IgnorePlayerAndWall);
// GetCursorLocationLimited(client, WallBuilder[client].moveDistance, WallBuilder[client].origin);
} else if(WallBuilder[client].movetype == 1) { } else if(WallBuilder[client].movetype == 1) {
switch(buttons) { switch(buttons) {
case IN_FORWARD: WallBuilder[client].origin[0] += WallBuilder[client].moveSpeed; case IN_FORWARD: WallBuilder[client].origin[0] += WallBuilder[client].moveSpeed;
@ -1320,6 +1385,7 @@ public Action OnPlayerRunCmd(int client, int& buttons, int& impulse, float vel[3
} }
} }
case SCALE: { case SCALE: {
SetWeaponDelay(client, 0.5);
allowMove = false; allowMove = false;
bool sizeChanged = false; bool sizeChanged = false;
switch(buttons) { switch(buttons) {
@ -1348,31 +1414,13 @@ public Action OnPlayerRunCmd(int client, int& buttons, int& impulse, float vel[3
case IN_USE: WallBuilder[client].CycleSpeed(client, tick); case IN_USE: WallBuilder[client].CycleSpeed(client, tick);
} }
if(sizeChanged) { if(sizeChanged) {
WallBuilder[client].CalculateMinMax(); WallBuilder[client].CalculateMins();
// PrintToChat(client, "origin %f %f %f", WallBuilder[client].origin[0], WallBuilder[client].origin[1], WallBuilder[client].origin[2]);
// PrintToChat(client, "mins %f %f %f", WallBuilder[client].mins[0], WallBuilder[client].mins[1], WallBuilder[client].mins[2]);
// PrintToChat(client, "maxs %f %f %f", WallBuilder[client].maxs[0], WallBuilder[client].maxs[1], WallBuilder[client].maxs[2]);
}
}
case ROTATE: {
switch(buttons) {
case IN_RELOAD: WallBuilder[client].CycleAxis(client, tick);
case IN_USE: WallBuilder[client].CycleSnapAngle(client, tick);
}
if(WallBuilder[client].axis == 0) {
if(mouse[1] > 0) WallBuilder[client].angles[0] += WallBuilder[client].snapAngle;
else if(mouse[1] < 0) WallBuilder[client].angles[0] -= WallBuilder[client].snapAngle;
} else if(WallBuilder[client].axis == 1) {
if(mouse[0] > 0) WallBuilder[client].angles[1] += WallBuilder[client].snapAngle;
else if(mouse[0] < 0) WallBuilder[client].angles[1] -= WallBuilder[client].snapAngle;
} }
} }
} }
switch(buttons) { switch(buttons) {
case IN_ATTACK: WallBuilder[client].CycleMode(client, tick); case IN_RELOAD: WallBuilder[client].CycleMode(client, tick); // R: Cycle forward
case IN_ATTACK2: WallBuilder[client].CycleMode(client, tick, false);
} }
WallBuilder[client].Draw(BUILDER_COLOR, 0.1, 0.1); WallBuilder[client].Draw(BUILDER_COLOR, 0.1, 0.1);
@ -1459,6 +1507,12 @@ public void OnMapEnd() {
} }
public void OnPluginEnd() { public void OnPluginEnd() {
ClearHats(); ClearHats();
for(int i = 1; i <= MaxClients; i++) {
if(IsClientConnected(i) && IsClientInGame(i)) {
int flags = GetEntityFlags(i) & ~FL_FROZEN;
SetEntityFlags(i, flags);
}
}
} }
public bool TraceEntityFilterPlayer(int entity, int contentsMask, any data) { public bool TraceEntityFilterPlayer(int entity, int contentsMask, any data) {
@ -1491,7 +1545,14 @@ stock bool Filter_NoPlayers(int entity, int mask, int data) {
return entity > MaxClients && entity != data; return entity > MaxClients && entity != data;
} }
stock bool Filter_IgnorePlayerAndWall(int entity, int mask, int data) {
return entity > 0 && entity != data && EntRefToEntIndex(WallBuilder[data].entity) != entity;
}
bool Filter_IgnorePlayer(int entity, int mask, int data) { bool Filter_IgnorePlayer(int entity, int mask, int data) {
return entity > 0 && entity != data;
}
bool Filter_ValidHats(int entity, int mask, int data) {
if(entity == data) return false; if(entity == data) return false;
if(entity <= MaxClients) { if(entity <= MaxClients) {
int client = GetRealClient(data); int client = GetRealClient(data);
@ -1536,6 +1597,8 @@ void ClearHat(int i, bool restore = false) {
return; return;
} }
int flags = ~GetEntityFlags(entity) & FL_FROZEN;
SetEntityFlags(entity, flags);
// if(HasEntProp(entity, Prop_Send, "m_flModelScale")) // if(HasEntProp(entity, Prop_Send, "m_flModelScale"))
// SetEntPropFloat(entity, Prop_Send, "m_flModelScale", 1.0); // SetEntPropFloat(entity, Prop_Send, "m_flModelScale", 1.0);
SetEntProp(modifyEntity, Prop_Send, "m_CollisionGroup", hatData[i].collisionGroup); SetEntProp(modifyEntity, Prop_Send, "m_CollisionGroup", hatData[i].collisionGroup);
@ -1670,11 +1733,24 @@ void EquipHat(int client, int entity, const char[] classname = "", int flags = H
if(entity <= MaxClients && !IsFakeClient(entity)) { if(entity <= MaxClients && !IsFakeClient(entity)) {
PrintToChat(entity, "[Hats] %N has hatted you, type /hat to dismount at any time", client); PrintToChat(entity, "[Hats] %N has hatted you, type /hat to dismount at any time", client);
} }
// Reset things: // Reset things:
hatData[client].flags = 0; hatData[client].flags = 0;
hatData[client].offset[0] = hatData[client].offset[1] = hatData[client].offset[2] = 0.0; hatData[client].offset[0] = hatData[client].offset[1] = hatData[client].offset[2] = 0.0;
hatData[client].angles[0] = hatData[client].angles[1] = hatData[client].angles[2] = 0.0; hatData[client].angles[0] = hatData[client].angles[1] = hatData[client].angles[2] = 0.0;
if(modifyEntity <= MaxClients) {
if(HasFlag(client, HAT_REVERSED)) {
hatData[client].offset[2] += 7.2;
} else {
hatData[client].offset[2] += 4.2;
}
} else {
float mins[3];
GetEntPropVector(modifyEntity, Prop_Send, "m_vecMins", mins);
hatData[client].offset[2] += mins[2];
}
if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_ReversedHats) && flags & view_as<int>(HAT_REVERSED)) { if(cvar_sm_hats_flags.IntValue & view_as<int>(HatConfig_ReversedHats) && flags & view_as<int>(HAT_REVERSED)) {
SetFlag(client, HAT_REVERSED); SetFlag(client, HAT_REVERSED);
if(StrEqual(classname, "infected") || (entity <= MaxClients && IsFakeClient(entity))) { if(StrEqual(classname, "infected") || (entity <= MaxClients && IsFakeClient(entity))) {
@ -1686,6 +1762,11 @@ void EquipHat(int client, int entity, const char[] classname = "", int flags = H
PrintToChat(entity, "[Hats] %N has set themselves as your hat", client); PrintToChat(entity, "[Hats] %N has set themselves as your hat", client);
} }
} else { } else {
if(StrEqual(classname, "infected")) {
int eflags = GetEntityFlags(entity) | FL_FROZEN;
SetEntityFlags(entity, eflags);
hatData[client].offset[2] = 36.0;
}
if(entity <= MaxClients) if(entity <= MaxClients)
PrintToChat(client, "[Hats] Set %N (%d) as a hat", entity, entity); PrintToChat(client, "[Hats] Set %N (%d) as a hat", entity, entity);
else else
@ -1696,17 +1777,7 @@ void EquipHat(int client, int entity, const char[] classname = "", int flags = H
LogAction(client, -1, "\"%L\" picked up %s as a hat (%d, %d)", client, classname, entity, visibleEntity); LogAction(client, -1, "\"%L\" picked up %s as a hat (%d, %d)", client, classname, entity, visibleEntity);
} }
hatData[client].scale = -1.0; hatData[client].scale = -1.0;
if(modifyEntity <= MaxClients) {
if(HasFlag(client, HAT_REVERSED)) {
hatData[client].offset[2] += 7.2;
} else {
hatData[client].offset[2] += 4.2;
}
} else {
float mins[3];
GetEntPropVector(modifyEntity, Prop_Send, "m_vecMins", mins);
hatData[client].offset[2] += mins[2];
}
} }
AcceptEntityInput(modifyEntity, "DisableMotion"); AcceptEntityInput(modifyEntity, "DisableMotion");
@ -1781,6 +1852,7 @@ void GlowWall(int id, float lifetime = 5.0) {
Effect_DrawBeamBoxRotatableToAll(pos, mins, maxs, angles, g_iLaserIndex, 0, 0, 30, lifetime, 0.4, 0.4, 0, 1.0, WALL_COLOR, 0); Effect_DrawBeamBoxRotatableToAll(pos, mins, maxs, angles, g_iLaserIndex, 0, 0, 30, lifetime, 0.4, 0.4, 0, 1.0, WALL_COLOR, 0);
} }
void DeleteWall(int id) { void DeleteWall(int id) {
GlowWall(id);
int ref = GetWallEntity(id); int ref = GetWallEntity(id);
if(IsValidEntity(ref)) { if(IsValidEntity(ref)) {
AcceptEntityInput(ref, "Kill"); AcceptEntityInput(ref, "Kill");
@ -1788,14 +1860,7 @@ void DeleteWall(int id) {
createdWalls.Erase(id - 1); createdWalls.Erase(id - 1);
} }
stock void SetWeaponDelay(int client, float delay)
{
int pWeapon = GetEntPropEnt(client, Prop_Send, "m_hActiveWeapon");
if (pWeapon > -1) {
SetEntPropFloat(pWeapon, Prop_Send, "m_flNextPrimaryAttack", GetGameTime() + delay);
SetEntPropFloat(pWeapon, Prop_Send, "m_flNextSecondaryAttack", GetGameTime() + delay);
}
}
stock bool FindGround(const float start[3], float end[3]) { stock bool FindGround(const float start[3], float end[3]) {
float angle[3]; float angle[3];
angle[0] = 90.0; angle[0] = 90.0;
@ -1836,3 +1901,7 @@ stock void LookAtPoint(int entity, const float destination[3]){
angles[1] -= 180; angles[1] -= 180;
TeleportEntity(entity, NULL_VECTOR, angles, NULL_VECTOR); TeleportEntity(entity, NULL_VECTOR, angles, NULL_VECTOR);
} }
stock float SnapTo(const float value, const float degree) {
return float(RoundFloat(value / degree)) * degree;
}

View file

@ -38,6 +38,12 @@ enum struct PlayerData {
static ArrayList lastPlayers; static ArrayList lastPlayers;
public APLRes AskPluginLoad2(Handle myself, bool late, char[] error, int err_max)
{
CreateNative("AddNoteIdentity", Native_AddNoteIdentity);
return APLRes_Success;
}
public void OnPluginStart() { public void OnPluginStart() {
if(!SQL_CheckConfig(DATABASE_CONFIG_NAME)) { if(!SQL_CheckConfig(DATABASE_CONFIG_NAME)) {
SetFailState("No database entry for %s; no database to connect to.", DATABASE_CONFIG_NAME); SetFailState("No database entry for %s; no database to connect to.", DATABASE_CONFIG_NAME);
@ -197,8 +203,7 @@ void ApplyRep(int client, int target, int rep) {
char activatorId[32], targetId[32]; char activatorId[32], targetId[32];
GetClientAuthId(client, AuthId_Steam2, activatorId, sizeof(activatorId)); GetClientAuthId(client, AuthId_Steam2, activatorId, sizeof(activatorId));
GetClientAuthId(target, AuthId_Steam2, targetId, sizeof(targetId)); GetClientAuthId(target, AuthId_Steam2, targetId, sizeof(targetId));
DB.Format(query, sizeof(query), "INSERT INTO `notes` (steamid, markedBy, content) VALUES ('%s', '%s', '%s')", targetId, activatorId, msg); AddNoteIdentity(activatorId, targetId, msg);
DB.Query(DB_AddNote, query);
} }
public Action Command_AddNoteDisconnected(int client, int args) { public Action Command_AddNoteDisconnected(int client, int args) {
@ -348,20 +353,20 @@ public Action Command_ListNotes(int client, int args) {
} }
bool ConnectDB() { bool ConnectDB() {
char error[255]; char error[255];
DB = SQL_Connect(DATABASE_CONFIG_NAME, true, error, sizeof(error)); DB = SQL_Connect(DATABASE_CONFIG_NAME, true, error, sizeof(error));
if (DB== null) { if (DB== null) {
LogError("Database error %s", error); LogError("Database error %s", error);
delete DB; delete DB;
return false; return false;
} else { } else {
PrintToServer("Connected to database %s", DATABASE_CONFIG_NAME); PrintToServer("Connected to database %s", DATABASE_CONFIG_NAME);
SQL_LockDatabase(DB); SQL_LockDatabase(DB);
SQL_FastQuery(DB, "SET NAMES \"UTF8mb4\""); SQL_FastQuery(DB, "SET NAMES \"UTF8mb4\"");
SQL_UnlockDatabase(DB); SQL_UnlockDatabase(DB);
DB.SetCharset("utf8mb4"); DB.SetCharset("utf8mb4");
return true; return true;
} }
} }
public void Event_FirstSpawn(Event event, const char[] name, bool dontBroadcast) { public void Event_FirstSpawn(Event event, const char[] name, bool dontBroadcast) {
@ -369,7 +374,7 @@ public void Event_FirstSpawn(Event event, const char[] name, bool dontBroadcast)
if(client > 0 && client <= MaxClients && !IsFakeClient(client)) { if(client > 0 && client <= MaxClients && !IsFakeClient(client)) {
static char auth[32]; static char auth[32];
GetClientAuthId(client, AuthId_Steam2, auth, sizeof(auth)); GetClientAuthId(client, AuthId_Steam2, auth, sizeof(auth));
DB.Format(query, sizeof(query), "SELECT notes.content, stats_users.last_alias FROM `notes` JOIN stats_users ON markedBy = stats_users.steamid WHERE notes.`steamid` = '%s'", auth); DB.Format(query, sizeof(query), "SELECT notes.content, stats_users.last_alias, markedBy FROM `notes` JOIN stats_users ON markedBy = stats_users.steamid WHERE notes.`steamid` = '%s'", auth);
DB.Query(DB_FindNotes, query, GetClientUserId(client)); DB.Query(DB_FindNotes, query, GetClientUserId(client));
} }
} }
@ -402,9 +407,9 @@ bool IsPlayerInHistory(const char[] id) {
public void DB_FindNotes(Database db, DBResultSet results, const char[] error, any data) { public void DB_FindNotes(Database db, DBResultSet results, const char[] error, any data) {
if(db == null || results == null) { if(db == null || results == null) {
LogError("DB_FindNotes returned error: %s", error); LogError("DB_FindNotes returned error: %s", error);
return; return;
} }
//initialize variables //initialize variables
int client = GetClientOfUserId(data); int client = GetClientOfUserId(data);
if(client > 0 && results.RowCount > 0) { if(client > 0 && results.RowCount > 0) {
@ -413,8 +418,13 @@ public void DB_FindNotes(Database db, DBResultSet results, const char[] error, a
int actions = 0; int actions = 0;
int repP = 0, repN = 0; int repP = 0, repN = 0;
while(results.FetchRow()) { while(results.FetchRow()) {
DBResult result;
results.FetchString(0, reason, sizeof(reason)); results.FetchString(0, reason, sizeof(reason));
results.FetchString(1, noteCreator, sizeof(noteCreator)); results.FetchString(1, noteCreator, sizeof(noteCreator), result);
if(result == DBVal_Null) {
// No name for admin, get the raw id:
results.FetchString(2, noteCreator, sizeof(noteCreator), result);
}
TrimString(reason); TrimString(reason);
if(ParseActions(data, reason)) { if(ParseActions(data, reason)) {
actions++; actions++;
@ -525,9 +535,9 @@ Action Timer_SlapPlayer(Handle h, int userid) {
public void DB_ListNotesForPlayer(Database db, DBResultSet results, const char[] error, DataPack pack) { public void DB_ListNotesForPlayer(Database db, DBResultSet results, const char[] error, DataPack pack) {
if(db == null || results == null) { if(db == null || results == null) {
LogError("DB_ListNotesForPlayer returned error: %s", error); LogError("DB_ListNotesForPlayer returned error: %s", error);
return; return;
} }
//initialize variables //initialize variables
static char auth[32]; static char auth[32];
pack.Reset(); pack.Reset();
@ -556,9 +566,9 @@ public void DB_ListNotesForPlayer(Database db, DBResultSet results, const char[]
public void DB_AddNote(Database db, DBResultSet results, const char[] error, any data) { public void DB_AddNote(Database db, DBResultSet results, const char[] error, any data) {
if(db == null || results == null) { if(db == null || results == null) {
LogError("DB_AddNote returned error: %s", error); LogError("DB_AddNote returned error: %s", error);
return; return;
} }
} }
stock void PrintChatToAdmins(const char[] format, any ...) { stock void PrintChatToAdmins(const char[] format, any ...) {
@ -588,3 +598,23 @@ stock void CPrintChatToAdmins(const char[] format, any ...) {
} }
CPrintToServer("%s", buffer); CPrintToServer("%s", buffer);
} }
any Native_AddNoteIdentity(Handle plugin, int numParams) {
char noteCreator[32];
char noteTarget[32];
int length;
GetNativeStringLength(3, length);
char[] message = new char[length + 1];
GetNativeString(1, noteCreator, sizeof(noteCreator));
GetNativeString(2, noteTarget, sizeof(noteTarget));
GetNativeString(3, message, length);
AddNoteIdentity(noteCreator, noteTarget, message);
return 0;
}
void AddNoteIdentity(const char noteCreator[32], const char noteTarget[32], const char[] message) {
// messaege length + steamids (32 + 32 + null term)
// char[] query = new char[strlen(message) + 65];
DB.Format(query, sizeof(query), "INSERT INTO `notes` (steamid, markedBy, content) VALUES ('%s', '%s', '%s')", noteCreator, noteTarget, message);
DB.Query(DB_AddNote, query);
}