19.12.2012, 16:58
Ниже представлен скрипт ботов основаных на плагине CNPC, которые должны нападать на игрока когда тот окажется рядом с ними, но нападают не те боты кторые близко к игроку, а все 450 мать их! В чём тут может быть проблема?
pawn Код:
/*
* Created: 12.04.10
* Author: 009
* Last Modifed: 14.07.10
* Description: Citizens in SA:MP
*/
// --------------------------------------------------
// includes
// --------------------------------------------------
#include <a_samp>
#include <cnpc>
// --------------------------------------------------
// defines
// --------------------------------------------------
#define VERSION "0.2"
#define ONLY_LOS_SANTOS
#define for_npcs(%1) for(new %1 = 499;%1 >= 50;%1--)
#if !defined MAX_STRING
#define MAX_STRING 128
#endif
#define NODE_TYPE_PED 0
#define Z_CORRECTION 0.7
#define GetDistanceBetweenCoords(%1,%2,%3,%4,%5,%6) floatsqroot((%4 - %1)*(%4 - %1) + (%5 - %2)*(%5 - %2) + (%6 - %3)*(%6 - %3))
#pragma tabsize 0
forward JokeNPC();
// --------------------------------------------------
// enums
// --------------------------------------------------
enum NPCNodeDataInfo
{
nNodeId,
nPathType,
nPointId,
nLastPointId
};
enum {
NPC_STATUS_WAIT,
NPC_STATUS_WALK_TO_CLOSEST,
NPC_STATUS_RUN_TO_CLOSEST,
NPC_STATUS_SPRINT_TO_CLOSEST,
NPC_STATUS_LOOK_AT_CLOSEST,
NPC_STATUS_AIM_AT_CLOSEST,
NPC_STATUS_SHOT_AT_CLOSEST
};
// --------------------------------------------------
// news
// --------------------------------------------------
new badSkins[] = {3, 4, 5, 6, 8, 42, 65, 74, 86, 119, 149, 208, 273, 289},
strtmp[MAX_STRING],
Node:TrafficNodes[MAX_NODES],
TrafficNodesHeader[MAX_NODES][4],
NPCNodeData[MAX_NPCS][NPCNodeDataInfo],
Float:floattmp[3],
inttmp,
NPC_STATUS,
ZoneToArray[MAX_NODES] = {-1,...};
#if defined ALL_SAN_ANDREAS
new AllowedZones[64] =
{
0,1,2,...
};
#elseif defined ONLY_LOS_SANTOS
new AllowedZones[] =
{
5,6,7,12,13,14,15,20,21,22,23
};
#elseif defined ONLY_SAN_FIERRO
new AllowedZones[] =
{
17,24,25,26,32,33,34,40,41
};
#elseif defined ONLY_LAS_VENTURAS
new AllowedZones[] =
{
37,38,39,45,46,47,53,54,55,61,62,63
};
#endif
// --------------------------------------------------
// publics
// --------------------------------------------------
public OnFilterScriptInit()
{
// cnpc settings
ToogleVisualDeath(1);
// read nodes
for(new i = 0;i < sizeof(AllowedZones);i++)
{
format(strtmp,sizeof(strtmp),"Nodes/NODES%d.DAT",AllowedZones[i]);
if(!fexist(strtmp)) continue;
ZoneToArray[ AllowedZones[i] ] = i;
new j = AllowedZones[i];
TrafficNodes[j] = OpenNode(strtmp);
GetNodeHeader(TrafficNodes[j],TrafficNodesHeader[j][0],TrafficNodesHeader[j][1],TrafficNodesHeader[j][2],TrafficNodesHeader[j][3]);
printf("Node 'NODES%d' loaded.Data: %d,%d,%d,%d",AllowedZones[i],TrafficNodesHeader[j][0],TrafficNodesHeader[j][1],TrafficNodesHeader[j][2],TrafficNodesHeader[j][3]);
}
// create npcs
for_npcs(i)
{
// create npc
CreateNPC(i,"Citizen");
// randomize node
do NPCNodeData[i][nNodeId] = AllowedZones[ random(sizeof(AllowedZones)) ];
while(!TrafficNodes[ NPCNodeData[i][nNodeId] ]);
// randomize type of path
if(TrafficNodesHeader[ NPCNodeData[i][nNodeId] ][1] == 0) NPCNodeData[i][nPathType] = NODE_TYPE_PED;
else if(random(100) > 30) NPCNodeData[i][nPathType] = NODE_TYPE_PED;
// randomize point
rpoint:
switch(NPCNodeData[i][nPathType])
{
case NODE_TYPE_PED: NPCNodeData[i][nPointId] = TrafficNodesHeader[ NPCNodeData[i][nNodeId] ][1] + random(TrafficNodesHeader[ NPCNodeData[i][nNodeId] ][2] - 1) + 1;
}
// set point and get coords
SetNodePoint(TrafficNodes[ NPCNodeData[i][nNodeId] ],NPCNodeData[i][nPointId]);
GetNodePointPos(TrafficNodes[ NPCNodeData[i][nNodeId] ],floattmp[0],floattmp[1],floattmp[2]);
if(floattmp[2] > 800.0) // is coord for interior
{
goto rpoint;
}
floattmp[2] += Z_CORRECTION; // correction
// find valid skin
do inttmp = random(300);
while(!IsValidSkin(inttmp));
// spawn on this point
SetSpawnInfo(i,0,inttmp,floattmp[0],floattmp[1],floattmp[2],0.0,0,0,0,0,0,0);
SpawnNPC(i);
// vehicle
// get next point
new link = GetNodePointLinkId(TrafficNodes[ NPCNodeData[i][nNodeId] ]);
SetNodeLink(TrafficNodes[ NPCNodeData[i][nNodeId] ],link);
// save last point
NPCNodeData[i][nLastPointId] = NPCNodeData[i][nPointId];
// change point
NPCNodeData[i][nPointId] = GetNodeLinkNodeId(TrafficNodes[ NPCNodeData[i][nNodeId] ]);
NPCNodeData[i][nNodeId] = GetNodeLinkAreaId(TrafficNodes[ NPCNodeData[i][nNodeId] ]);
// check zone
if(ZoneToArray[ NPCNodeData[i][nNodeId] ] == -1)
{
goto rpoint;
}
// get coords
SetNodePoint(TrafficNodes[ NPCNodeData[i][nNodeId] ],NPCNodeData[i][nPointId]);
GetNodePointPos(TrafficNodes[ NPCNodeData[i][nNodeId] ],floattmp[0],floattmp[1],floattmp[2]);
floattmp[2] += Z_CORRECTION; // correction
// go to this point
switch(NPCNodeData[i][nPathType])
{
case NODE_TYPE_PED: NPC_WalkTo(i,floattmp[0],floattmp[1],floattmp[2],0);
}
//SetTimerEx("ZombieAttack",1000,1);
}
print("Citizens " VERSION " by 009 loaded.");
SetTimer("JokeNPC",1000,1);
return 1;
}
/*forward ZombieAttack();
public ZombieAttack()
{
new Float:Zpos[3],Float:Ppos[3];
for(new z = 0, p = 0;z < sizeof(AllowedZones),p<MAX_PLAYERS;z++,p++)
{
GetNPCPos(z,Zpos[0],Zpos[1],Zpos[2]);
GetPlayerPos(p,Ppos[0],Ppos[1],Ppos[2]);
if(PointInRangeOfPoint(10, Zpos[0], Zpos[1], Zpos[2], Ppos[0], Ppos[1], Ppos[2]))
{
NPC_SprintTo(z,Ppos[0],Ppos[1],Ppos[2],0);
NPC_LookAt(z,Ppos[0],Ppos[1],Ppos[2]);
NPC_AimAt(z,Ppos[0],Ppos[1],Ppos[2]);
NPC_ShotAt(z,Ppos[0],Ppos[1],Ppos[2]);
}
}
return 1;
}*/
public OnPlayerUpdate(playerid)
{
/*new Float:Zpos[3],Float:Ppos[3];
for(new z = 0, p = 0;z < sizeof(AllowedZones),p<MAX_PLAYERS;z++,p++)
{
for_npcs(z)
{
GetNPCPos(z,Zpos[0],Zpos[1],Zpos[2]);
}
GetPlayerPos(p,Ppos[0],Ppos[1],Ppos[2]);
if(PointInRangeOfPoint(10, Zpos[0], Zpos[1], Zpos[2], Ppos[0], Ppos[1], Ppos[2]))
{
NPC_SprintTo(z,Ppos[0],Ppos[1],Ppos[2],0);
NPC_LookAt(z,Ppos[0],Ppos[1],Ppos[2]);
NPC_AimAt(z,Ppos[0],Ppos[1],Ppos[2]);
NPC_ShotAt(z,Ppos[0],Ppos[1],Ppos[2]);
}
}*/
return 1;
}
public OnFilterScriptExit()
{
for_npcs(i)
{
if(!IsValidNPC(i)) continue;
DestroyNPC(i);
}
for(new i = 0;i < sizeof(TrafficNodes);i++)
{
if(ZoneToArray[i] != -1) CloseNode(TrafficNodes[i]);
}
print("Citizens " VERSION " by 009 unloaded.");
return 1;
}
/*
public OnGameModeInit()
{
print("Citizens loading...");
print("Citizens loaded.");
}
*/
public OnPlayerStreamIn(playerid, forplayerid)
{
if(!IsValidNPC(playerid)) return;
if(GetNPCState(playerid) == NPC_STATE_DEATH) ApplyAnimation(playerid,"PED","KO_skid_front",4.1,0,1,1,1,1);
}
// -----------------------------------------------------------------------------
// Plugin's callbacks
// -----------------------------------------------------------------------------
public OnNPCGetDamage(npcid,playerid,Float:health_loss,bodypart)
{
return 1;
}
public OnNPCSpawn(npcid)
{
SetPlayerColor(npcid,0xFFFFFF00);
return 1;
}
public OnNPCMovingComplete(npcid)
{
// set cuurent point for geting
SetNodePoint(TrafficNodes[ NPCNodeData[npcid][nNodeId] ],NPCNodeData[npcid][nPointId]);
// get next point
new link = GetNodePointLinkId(TrafficNodes[ NPCNodeData[npcid][nNodeId] ]);
new lc = GetNodePointLinkCount(TrafficNodes[ NPCNodeData[npcid][nNodeId] ]);
new try_count = 0;
// randomize link
randomize:
// get point
SetNodeLink(TrafficNodes[ NPCNodeData[npcid][nNodeId] ],(link + random(lc)));
// get tmp pid
inttmp = GetNodeLinkNodeId(TrafficNodes[ NPCNodeData[npcid][nNodeId] ]);
if((inttmp == NPCNodeData[npcid][nLastPointId]) && (lc > 1))
{
try_count++;
if(try_count < 10) goto randomize;
}
// check zone
new node = GetNodeLinkAreaId(TrafficNodes[ NPCNodeData[npcid][nNodeId] ]);
if(ZoneToArray[ node ] == -1) goto randomize;
// save last point
NPCNodeData[npcid][nLastPointId] = NPCNodeData[npcid][nPointId];
// change point
NPCNodeData[npcid][nPointId] = inttmp;
NPCNodeData[npcid][nNodeId] = node;
// get coords
SetNodePoint(TrafficNodes[ NPCNodeData[npcid][nNodeId] ],NPCNodeData[npcid][nPointId]);
GetNodePointPos(TrafficNodes[ NPCNodeData[npcid][nNodeId] ],floattmp[0],floattmp[1],floattmp[2]);
floattmp[2] += Z_CORRECTION; // correction
// go to this point
switch(NPCNodeData[npcid][nPathType])
{
case NODE_TYPE_PED: NPC_WalkTo(npcid,floattmp[0],floattmp[1],floattmp[2],0);
}
return 1;
}
public OnNPCDeath(npcid,killerid,reason)
{
ApplyAnimation(npcid,"PED","KO_skid_front",4.1,0,1,1,1,1);
return 1;
}
public JokeNPC()
{
new Float:pos[3];
/*new Float:Zpos[3],Float:Ppos[3];
for_npcs(i)
{
GetNPCPos(i,Zpos[0],Zpos[1],Zpos[2]);
}
for(new i=0;i<MAX_PLAYERS;i++)
{
GetPlayerPos(i,Ppos[0],Ppos[1],Ppos[2]);
}
if(PointInRangeOfPoint(10, Ppos[0], Ppos[1], Ppos[2], Zpos[0], Zpos[1], Zpos[2]))
{
for_npcs(i)
{
NPC_WalkTo(i,Ppos[0],Ppos[1],Ppos[2],0);
NPC_SprintTo(i,Ppos[0],Ppos[1],Ppos[2],0);
NPC_LookAt(i,Ppos[0],Ppos[1],Ppos[2]);
NPC_AimAt(i,Ppos[0],Ppos[1],Ppos[2]);
NPC_ShotAt(i,Ppos[0],Ppos[1],Ppos[2]);
}
}*/
/*switch(NPC_STATUS)
{
case NPC_STATUS_WAIT: return;
case NPC_STATUS_WALK_TO_CLOSEST:
{*/
for_npcs(i)
{
for(new p=0;p<MAX_PLAYERS;p++)
{
if(IsPlayersNear(p,i,25))
{
/* GetPlayerPos(GetPlayerClosestPlayer(i),pos[0],pos[1],pos[2]);
NPC_WalkTo(i,(random(5) - random(5) + pos[0]),(random(5) - random(5) + pos[1]),pos[2],0);
}
return;
}
case NPC_STATUS_RUN_TO_CLOSEST:
{
for_npcs(i)
{*/
GetPlayerPos(GetPlayerClosestPlayer(i),pos[0],pos[1],pos[2]);
NPC_RunTo(i,(random(5) - random(5) + pos[0]),(random(5) - random(5) + pos[1]),pos[2],0);
/* }
return;
}
case NPC_STATUS_SPRINT_TO_CLOSEST:
{
for_npcs(i)
{
GetPlayerPos(GetPlayerClosestPlayer(i),pos[0],pos[1],pos[2]);
NPC_SprintTo(i,(random(5) - random(5) + pos[0]),(random(5) - random(5) + pos[1]),pos[2],0);
}
return;
}
case NPC_STATUS_LOOK_AT_CLOSEST:
{
for_npcs(i)
{
GetPlayerPos(GetPlayerClosestPlayer(i),pos[0],pos[1],pos[2]);
NPC_LookAt(i,pos[0],pos[1],pos[2]);
}
return;
}
case NPC_STATUS_AIM_AT_CLOSEST:
{
for_npcs(i)
{
GetPlayerPos(GetPlayerClosestPlayer(i),pos[0],pos[1],pos[2]);
NPC_AimAt(i,pos[0],pos[1],pos[2]);
}
return;
}
case NPC_STATUS_SHOT_AT_CLOSEST:
{
for_npcs(i)
{*/
GetPlayerPos(GetPlayerClosestPlayer(i),pos[0],pos[1],pos[2]);
NPC_ShotAt(i,pos[0],pos[1],pos[2]);
/*}
return;
}*/
}
}
}
}
stock IsPlayersNear(playerid,targetid,Float:range)
{
new Float:pos[3];
GetPlayerPos(targetid,pos[0],pos[1],pos[2]);
if(IsPlayerInRangeOfPoint(playerid,range,pos[0],pos[1],pos[2]))return true;
return false;
}
// --------------------------------------------------
// stocks
// --------------------------------------------------
stock IsValidSkin(skinid)
{
if(skinid < 0 || skinid > 299) return false;
for (new i = 0; i < sizeof(badSkins); i++)
{
if (skinid == badSkins[i]) return false;
}
return true;
}
stock PointInRangeOfPoint(Float:range, Float:x, Float:y, Float:z, Float:X, Float:Y, Float:Z)
{
X -= x;
Y -= y;
Z -= z;
return ((X * X) + (Y * Y) + (Z * Z)) < (range * range);
}
stock GetPlayerClosestPlayer(playerid)
{
new pid = INVALID_PLAYER_ID,
//Float:distance = 10,
Float:tmp[6];
GetNPCPos(playerid,tmp[0],tmp[1],tmp[2]);
for(new i = 0;i < MAX_PLAYERS;i++)
{
if(i == playerid) continue;
if(!IsPlayerConnected(i)) continue;
if(IsPlayerNPC(i)) continue;
GetPlayerPos(i,tmp[3],tmp[4],tmp[5]);
//tmp[6] = GetDistanceBetweenCoords(tmp[0],tmp[1],tmp[2],tmp[3],tmp[4],tmp[5]);
//if(tmp[6] < distance )
if(PointInRangeOfPoint(0, tmp[0], tmp[1], tmp[2], tmp[3], tmp[4], tmp[5]))continue;
//distance = tmp[6];
pid = i;
}
return pid;
}
/*stock GetDistanceBetweenCoords(Float:distance,Float:x1,Float:x2,Float:x3,Float:x4,Float:x5,Float:x6)
{
distance = floatsqroot((x4 - x1)*(x4 - x1) + (x5 - x2)*(x5 - x2) + (x6 - x3)*(x6 - x3));
return 1;
}*/