Raised This Month: $319 Target: $400
 79%   Almost there!

[SNIPPET] NPC DeathMSG


Post New Thread Reply   
 
Thread Tools Display Modes
Author Message
Natsheh
Veteran Member
Join Date: Sep 2012
Old 05-09-2021 , 14:25   [SNIPPET] NPC DeathMSG
Reply With Quote #1

I've found a way to make an npc fake deathmsg, i thought i'd share since i had never found something similar on the web.

PHP Code:
#include <fakemeta>

enum any:DEATHMSG_DATA (+=1) {
    
DEATHMSG_VICTIM_ID 0,
    
DEATHMSG_KILLER_ID,
    
DEATHMSG_bHEADSHOT,
    
DEATHMSG_WEAPON_NAME[24]
}

public 
fw_NPC_KILLED(idkiller)
{
    if(!
pev_valid(id)) return HAM_IGNORED;
    
    
pev(idpev_globalnameszZMnamecharsmax(szZMname))
    if(!
szZMname[0]) copy(szZMnamecharsmax(szZMname), "Unnamed");

    static 
szParam[10], Array:xArrayiNPC_DeathMSG_Data[DEATHMSG_DATA];
    
iNPC_DeathMSG_Data[DEATHMSG_VICTIM_ID] = id;
    
iNPC_DeathMSG_Data[DEATHMSG_KILLER_ID] = killer;
    
iNPC_DeathMSG_Data[DEATHMSG_bHEADSHOT] = false;
    
copy(iNPC_DeathMSG_Data[DEATHMSG_WEAPON_NAME], charsmax(iNPC_DeathMSG_Data[DEATHMSG_WEAPON_NAME]), "knife");
    
copy(iNPC_DeathMSG_Data[DEATHMSG_VIC_NAME], charsmax(iNPC_DeathMSG_Data[DEATHMSG_VIC_NAME]), szZMname);

    if(
IsPlayer(killer))
    {
        
get_user_name(killeriNPC_DeathMSG_Data[DEATHMSG_KILLER_NAME], charsmax(iNPC_DeathMSG_Data[DEATHMSG_KILLER_NAME]))
    }
    else if(
killer && pev(killerPEV_IDENTITY) == ZOMBIE_PET_ID) {
        
pev(killerpev_globalnameszZMnamecharsmax(szZMname));
        if(!
szZMname[0]) copy(szZMnamecharsmax(szZMname), "Unnamed");
        
copy(iNPC_DeathMSG_Data[DEATHMSG_KILLER_NAME], charsmax(iNPC_DeathMSG_Data[DEATHMSG_KILLER_NAME]), szZMname);
    }

    
ArrayPushArray((xArray ArrayCreate(DEATHMSG_DATA1)), iNPC_DeathMSG_Data);
    
num_to_str(_:xArrayszParamcharsmax(szParam));

    static const 
Float:fInterval_len 1.0;
    static 
Float:finterval 0.0;

    if(
finterval >= get_gametime())
        
finterval += fInterval_len;
    else 
        
finterval get_gametime() + fInterval_len;

    
set_task((finterval get_gametime()), "task_interval_NPC_DEATHMSG"idszParamcharsmax(szParam));
    return 
HAM_SUPERCEDE;
}

public 
task_interval_NPC_DEATHMSG(const param[], taskid)
{
    static Array:
xArrayiNPC_DeathMSG_Data[DEATHMSG_DATA];
    
xArray any:str_to_num(param);
    
ArrayGetArray(xArray0iNPC_DeathMSG_Data);
    
ArrayDestroy(xArray);
    
Make_NPC_DeathMsg(iNPC_DeathMSG_Data[DEATHMSG_VICTIM_ID], iNPC_DeathMSG_Data[DEATHMSG_KILLER_ID],
        
iNPC_DeathMSG_Data[DEATHMSG_VIC_NAME], iNPC_DeathMSG_Data[DEATHMSG_KILLER_NAME],
        
iNPC_DeathMSG_Data[DEATHMSG_bHEADSHOT], iNPC_DeathMSG_Data[DEATHMSG_WEAPON_NAME]);
}

Make_NPC_DeathMsg(idkiller, const vicName[32], const killerName[32], const bool:bHeadshot, const weapon[24])
{
    static 
iMsg_TeamInfo 0;
    if(!
iMsg_TeamInfoiMsg_TeamInfo get_user_msgid("TeamInfo");
    
    
enum (+=1) {
        
VICTIM_ID 0,
        
KILLER_ID
    
}

    new 
iTargets[2];
    
iTargets[VICTIM_ID] = id;
    
iTargets[KILLER_ID] = killer;

    static 
szRejectReason[128], szName[2][32];

    
copy(szName[VICTIM_ID], charsmax(szName[]), vicName);
    
copy(szName[KILLER_ID], charsmax(szName[]), killerName);

    for(new 
iiTarget2i++)
    {
        
iTarget iTargets[i];
        if( 
IsPlayer(iTarget) && get_user_index(szName[i]) || !iTarget || (KILLER_ID == && iTargets[i] == iTargets[VICTIM_ID]))
            continue;

        
iTarget engfunc(EngFunc_CreateFakeClientszName[i]);

        if(!
iTarget)
            continue;
        
        
engfunc(EngFunc_FreeEntPrivateDataiTarget);

        
dllfunc(DLLFunc_ClientConnectiTarget szName[i], "127.0.0.1"szRejectReason);
        
        if( !
is_user_connected(iTarget) ) 
            continue;

        
dllfunc(DLLFunc_ClientPutInServeriTarget);
        
set_pev(iTargetpev_flagspev(iTarget,pev_flags) | FL_FAKECLIENT);

        
message_begin(MSG_ALLiMsg_TeamInfo, {0,0,0}, 0);
        
write_byte(iTarget);
        
write_string("TERRORIST");
        
message_end();

        
set_rendering(iTargetkRenderFxNone000kRenderTransAlpha);

        
iTargets[i] = iTarget;
    }

    new 
szParam[10], Array:xArrayiNPC_DeathMSG_Data[DEATHMSG_DATA];
    
iNPC_DeathMSG_Data[DEATHMSG_VICTIM_ID] = iTargets[VICTIM_ID];
    
iNPC_DeathMSG_Data[DEATHMSG_KILLER_ID] = iTargets[KILLER_ID];
    
iNPC_DeathMSG_Data[DEATHMSG_bHEADSHOT] = _:bHeadshot;
    
copy(iNPC_DeathMSG_Data[DEATHMSG_WEAPON_NAME], charsmax(iNPC_DeathMSG_Data[DEATHMSG_WEAPON_NAME]), weapon);
    
copy(iNPC_DeathMSG_Data[DEATHMSG_KILLER_NAME], charsmax(iNPC_DeathMSG_Data[DEATHMSG_KILLER_NAME]), killerName);
    
copy(iNPC_DeathMSG_Data[DEATHMSG_VIC_NAME], charsmax(iNPC_DeathMSG_Data[DEATHMSG_VIC_NAME]), vicName);
    
ArrayPushArray((xArray ArrayCreate(DEATHMSG_DATA1)), iNPC_DeathMSG_Data);
    
num_to_str(_:xArrayszParamcharsmax(szParam));
    
set_task(0.1"declare_npc_deathmsg"idszParamcharsmax(szParam))
}

public 
declare_npc_deathmsg(const param[], const taskid)
{
    new Array:
xArray any:str_to_num(param), iNPC_DeathMSG_Data[DEATHMSG_DATA];
    
ArrayGetArray(xArray0iNPC_DeathMSG_Data);
    
ArrayDestroy(xArray);

    
make_deathmsg(iNPC_DeathMSG_Data[DEATHMSG_KILLER_ID], iNPC_DeathMSG_Data[DEATHMSG_VICTIM_ID],
         
iNPC_DeathMSG_Data[DEATHMSG_bHEADSHOT], iNPC_DeathMSG_Data[DEATHMSG_WEAPON_NAME]);

    if(
iNPC_DeathMSG_Data[DEATHMSG_KILLER_ID] > && pev(iNPC_DeathMSG_Data[DEATHMSG_KILLER_ID], pev_flags) & FL_FAKECLIENT)
    {
        
server_cmd("kick #%d;"get_user_userid(iNPC_DeathMSG_Data[DEATHMSG_KILLER_ID]));
    }
    
    if(
iNPC_DeathMSG_Data[DEATHMSG_VICTIM_ID] > && pev(iNPC_DeathMSG_Data[DEATHMSG_VICTIM_ID], pev_flags) & FL_FAKECLIENT)
    {
        
server_cmd("kick #%d;"get_user_userid(iNPC_DeathMSG_Data[DEATHMSG_VICTIM_ID]));
    }


basically what this function do is it creates a bot if an npc entity id was passed into either the killer or id ( victim ) parameters or both, and it kicks the bot/s once the fake deathmsg is sent.

NPC entity name must be set into globalname keyvalue, or you can change that if you're using one npc name for all.

Adding a delay of 1.0 second to Make_NPC_DeathMsg is recommended if you're going to call it many times per second.
__________________
@Jailbreak Main Mod v2.6.6 100%
@User Tag Prefix 100% done !
@Mystery Box 100% done !
@VIP System 100% done !


Last edited by Natsheh; 05-09-2021 at 20:23.
Natsheh is offline
Send a message via MSN to Natsheh Send a message via Skype™ to Natsheh
DJEarthQuake
Veteran Member
Join Date: Jan 2014
Location: Astral planes
Old 06-18-2021 , 04:43   Re: [SNIPPET] NPC DeathMSG
Reply With Quote #2

When you refer to Non-Player Character you mean Artificial Intelligence? As it stands this is non-functional. I started to clean it up but still missing some pieces and got too much other work to do. Are you up for sharing a non-fragmented script please? When I first looked at this I had found a way to do this with way less code yet then I scrolled down to see a lot more code. I just wanted to see what this can do beforehand.
__________________
"It's not the actual programming that's interesting. But it's what you can accomplish with the end results that are important." -Dennis Ritchie
"Mathematics, rightly viewed, possesses not only truth, but supreme beauty a beauty cold and austere, like that of sculpture..." -Bertrand Russell
DJEarthQuake is offline
DJEarthQuake
Veteran Member
Join Date: Jan 2014
Location: Astral planes
Old 10-03-2021 , 09:48   Re: [SNIPPET] NPC DeathMSG
Reply With Quote #3

I've made a dumbed down version of this as I was curious. Could respectively use some help optimizing it as some unoptimized maps this plugin is a source of instability. You can see I have tried but now would appreciate some help. This is a working plugin.

PHP Code:
#include amxmodx
#include amxmisc
#include engine
#include engine_stocks
#include fakemeta
#include fakemeta_util
#include hamsandwich

#define MAX_PLAYERS                32

#define MAX_RESOURCE_PATH_LENGTH   64

#define MAX_MENU_LENGTH            512

#define MAX_NAME_LENGTH            32

#define MAX_AUTHID_LENGTH          64

#define MAX_IP_LENGTH              16

#define MAX_USER_INFO_LENGTH       256

#define charsmin                  -1

new g_SzMonster_class[MAX_NAME_LENGTH]
new 
g_getakill
new npc_entg_npc_entnpc_ent_bind[MAX_NAME_LENGTH]
new 
ClientName[MAX_PLAYERS+1][MAX_NAME_LENGTH+1]


new const 
ents_with_health[][]={"func_breakable""func_pushable""func_door""func_door_rotating""momentary_door""monster_scientist"}

/*
new const the_monster_list[][]={
    "item_airtank",
    "monster_alien_controller",
    "monster_alien_grunt",
    "monster_alien_slave",
    "monster_apache",
    "monster_barnacle",
    "monster_babycrab",
    "monster_barney",
    "monster_bigmomma",
    "monster_bullchicken",
    "monster_cockroach",
    "monster_gargantua",
    "monster_gman",
    "monster_grunt_repel",
    "monster_human_grunt_ally",
    "monster_headcrab",
    "monster_houndeye",
    "monster_human_assassin",
    "monster_human_grunt",
    "monster_human_grunt_ally",
    "monster_human_medic_ally",
    "monster_human_torch_ally",
    "monster_ichthyosaur",
    "monster_leech",
    "monster_miniturret",
    "monster_nihilanth",
    "monster_osprey",
    "monster_scientist",
    "monster_sentry",
    "monster_sitting_scientist",
    "monster_tentacle",
    "monster_turret",
    "monster_zombie",
    "monster_blkop_apache",
    "monster_blkop_osprey",
    "monster_shockroach",
    "monster_shocktrooper",
    "monster_pitdrone",
    "monster_gonome"
}
*/

new const REPLACE[][] = {"monster_""func_""item_"}


public 
plugin_init()
{
    
register_plugin("monsters' hitpoints","1.1","SPiNX");
    
g_npc_ent register_cvar("npc_type""parachute")

    
#if AMXX_VERSION_NUM == 182;
    
get_pcvar_string(g_npc_ent,npc_ent_bindcharsmax(npc_ent_bind))
    
#else
    
bind_pcvar_string(g_npc_ent,npc_ent_bindcharsmax(npc_ent_bind))
    
#endif
    
npc_ent find_ent(charsmin,npc_ent_bind)
    
#if AMXX_VERSION_NUM == 182;
    
RegisterHamFromEntity(Ham_TakeDamage,npc_ent,"Ham_TakeDamage_player"//cvar to test random classes
    #else
    
RegisterHamFromEntity(Ham_TakeDamage,npc_ent,"Ham_TakeDamage_player"1//cvar to test random classes
    #endif
    
register_event("Damage","@event_damage","b"//standard player hp reading

    
for(new list; list < sizeof ents_with_health; ++list)
        
#if AMXX_VERSION_NUM == 182;
        
RegisterHam(Ham_TakeDamage,ents_with_health[list],"Ham_TakeDamage_player"1//array of breakables from skeleton key of destruction plugin
        #else
        
RegisterHam(Ham_TakeDamage,ents_with_health[list],"Ham_TakeDamage_player"1true//array of breakables from skeleton key of destruction plugin
        #endif


    //if (find_ent(charsmin,"monstermaker") > 0)
    
new few[][]={"monstermaker","monster_apache","monster_tentacle"}
    for(new 
ofthemofthem sizeof few; ++ofthem)
    if (
find_ent(charsmin,few[ofthem]) > 0)
    {
        new const 
monster_list1[][]=
        {
            
"item_airtank",
            
"monster_alien_controller",
            
"monster_alien_grunt",
            
"monster_alien_slave",
            
"monster_apache",
            
"monster_barnacle",
            
"monster_babycrab",
            
"monster_barney",
            
"monster_bigmomma",
            
"monster_bullchicken",
            
"monster_cockroach"
        
}

        new const 
monster_list2[][]=
        {
            
"monster_gargantua",
            
"monster_gman",
            
"monster_grunt_repel",
            
"monster_human_grunt_ally",
            
"monster_headcrab",
            
"monster_houndeye",
            
"monster_human_assassin",
            
"monster_human_grunt",
            
"monster_human_grunt_ally",
            
"monster_human_medic_ally",
            
"monster_human_torch_ally",
            
"monster_ichthyosaur",
            
"monster_leech",
            
"monster_miniturret",
            
"monster_nihilanth",
            
"monster_osprey"
        
}

        new const 
monster_list3[][]=
        {
            
"monster_scientist",
            
"monster_sentry",
            
"monster_sitting_scientist",
            
"monster_tentacle",
            
"monster_turret",
            
"monster_zombie",
            
"monster_blkop_apache",
            
"monster_blkop_osprey",
            
"monster_shockroach",
            
"monster_shocktrooper",
            
"monster_pitdrone",
            
"monster_gonome"
        
}

        for(new 
op4op4 sizeof monster_list1op4++)
            
RegisterHam(Ham_TakeDamage,monster_list1[op4],"Ham_TakeDamage_player"1)

        for(new 
op4op4 sizeof monster_list2op4++)
            
RegisterHam(Ham_TakeDamage,monster_list2[op4],"Ham_TakeDamage_player"1)

        for(new 
op4op4 sizeof monster_list3op4++)
            
RegisterHam(Ham_TakeDamage,monster_list3[op4],"Ham_TakeDamage_player"1)

        
server_print "MM found!"
    
}

    
g_getakill register_cvar("monster_kill""1"//1 show hp/kill|2 show death messages, what wepaon|3 get frags

}

public 
client_putinserver(id)
    if(
is_user_connected(id))
        
get_user_name(id,ClientName[id],charsmax(ClientName[]))

public 
Ham_TakeDamage_player(this_ententidattackerFloat:damagedamagebits)
{
    if(
is_user_alive(idattacker) && idattacker != this_ent)
    {
        if(
equal(ClientName[idattacker],""))
            
get_user_name(idattacker,ClientName[idattacker],charsmax(ClientName[]))

        
entity_get_string(this_ent,EV_SZ_classname,g_SzMonster_class,charsmax(g_SzMonster_class))
    
        for ( new 
MENTMENT sizeof REPLACE; ++MENT )
            
replace(g_SzMonster_class,charsmax(g_SzMonster_class), REPLACE[MENT], " ");
    
        new 
Float:health entity_get_float(this_ent,EV_FL_health)
        new 
killer idattacker
        
new victim this_ent
        
new temp_npc
        
new weapon get_user_weapon(killer)
        if(
is_user_connected(killer) && !is_user_bot(killer) && victim != killer)
            
client_print killer,print_center,"%s health:%i",g_SzMonster_class,floatround(health)
        if (
health damage 1.0 && get_pcvar_num(g_getakill) > 1)
        {
            @
fake_death(this_ent,idattacker)
            if(!
is_user_bot(this_ent))
                
SetHamParamInteger(5DMG_ALWAYSGIB//otherwise multi kills on corpse!
            
temp_npc engfunc(EngFunc_CreateFakeClient,g_SzMonster_class)
            if(
temp_npc 0)
            {
                static 
szRejectReason[128]
                new 
effects pev(temp_npcpev_effects)
                
dllfunc(DLLFunc_ClientConnect,temp_npc,g_SzMonster_class,"::1",szRejectReason)
                
set_pev(temp_npcpev_effects, (effects EF_NODRAW ));

                
victim temp_npc
                log_kill
(killer,victim ,weapon)

            }


        }

        else if (
health damage 1.0 && get_pcvar_num(g_getakill) > 0)
            @
fake_death(this_ent,idattacker)
    }

    
GetHamReturnStatus() != HAM_SUPERCEDE
}

public 
pin_scoreboard(killer)
{
    if(
is_user_connected(killer) && get_pcvar_num(g_getakill) > 2)
    {
        
//Scoring
        
fm_set_user_frags(killer,get_user_frags(killer) +1);
        
#define DEATHS 422
        
new deaths get_pdata_int(killerDEATHS)
        new 
frags get_user_frags(killer)

        
emessage_begin(MSG_BROADCAST,get_user_msgid("ScoreInfo"))
        
ewrite_byte(killer);
        
ewrite_short(frags)
        
ewrite_short(deaths)

        if(
is_running("cstrike") == 1)
        {
            
ewrite_short(0); //TFC CLASS
            
ewrite_short(get_user_team(killer));
        }
        
emessage_end();
    }

}
@
event_damage(id)
{
    new 
victim id;new killer get_user_attacker(victim);
    if( 
is_user_alive(killer) && !is_user_bot(killer) &&  killer != victim)
        
client_print(killer,print_center,"%s HP: %i",ClientName[victim], get_user_health(victim));
    else if (
killer == victim && is_user_alive(killer) && !is_user_bot(killer))
        
client_print killer,print_center,"CAREFUL!"
    
return PLUGIN_CONTINUE;
}

@
fake_death(this_ent,idattacker)
{
    
entity_get_string(this_ent,EV_SZ_classname,g_SzMonster_class,charsmax(g_SzMonster_class))

    for ( new 
MENTMENT sizeof REPLACE; ++MENT )
        
replace(g_SzMonster_class,charsmax(g_SzMonster_class), REPLACE[MENT], "");

    if( 
is_user_connected(idattacker) && is_user_alive(idattacker) && !is_user_bot(idattacker) && is_valid_ent(this_ent))

    
client_print 0print_center"%s slayed a %s"ClientName[idattacker],g_SzMonster_class
}

@
disco(victim)
server_cmd"kick #%d ^"temp_bot^""get_user_userid(victim) );

stock log_kill(killervictimweapon)
{
    new 
weapon_name[MAX_NAME_LENGTH]

    if(
is_user_connected(killer))
    {

        
get_weaponname(weapon,weapon_name,charsmax(weapon_name))

        
replace(weapon_namecharsmax(weapon_name), "weapon_""")

        
emessage_begin(MSG_BROADCASTget_user_msgid("DeathMsg"), {0,0,0}, 0);
        
ewrite_byte(killer);
        
ewrite_byte(victim);
        
ewrite_string(weapon_name)
        
emessage_end();

        
//Logging the message as seen on console.
        
new kname[MAX_PLAYERS+1], kauthid[MAX_PLAYERS+1]
        
get_user_authid(killerkauthidcharsmax(kauthid))
        
get_user_name(killerknamecharsmax(kname))

        
log_message("^"%s<%d><%s>^" killed ^"%s^" with ^"%s^""knameget_user_userid(killer), kauthidg_SzMonster_classweapon_name)
        if(
get_pcvar_num(g_getakill) > 1)
        {
            
pin_scoreboard(killer)
            
set_task(0.5,"@disco",victim)
        }

    }


The only thing I see looking back now is monster_scientist is in there twice.

Something I wish I would have discovered before starting!
[OP4] Monstername
https://forums.alliedmods.net/showthread.php?p=1527624
__________________
"It's not the actual programming that's interesting. But it's what you can accomplish with the end results that are important." -Dennis Ritchie
"Mathematics, rightly viewed, possesses not only truth, but supreme beauty a beauty cold and austere, like that of sculpture..." -Bertrand Russell
DJEarthQuake is offline
Reply


Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump


All times are GMT -4. The time now is 11:57.


Powered by vBulletin®
Copyright ©2000 - 2021, vBulletin Solutions, Inc.
Theme made by Freecode