Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Gelişmiş NPC - Oyuncu Olmayan Karakter
#1
NPC, Non Player Character yani Türkçe karşılığı ile Oyuncu olmayan karakterdir. Bu derste ayrıntılı bir şekilde açıklayarak anlatacağım. Bu ders biraz ileri seviye olabilir. Düzenleyerek kullana kullana öğrenebilirsiniz. Bunun için bilinmesi gereken kütüphaneler,

fakemeta,
engine,
hamsandwich

Fakemeta ve engine kütüphaneleri kod bakımından birbirine çok benzer ama çalışma mantıkları farklıdır. Evet zor kütüphaneler ama ingilizce oldukları ve Türkçe kaynak olmadığı için zor geliyor. Mantığını kavrayabilirsek eğlenceli hale gelebiliyor.


Gelelim konumuza, NPC yani oyuncu olmayan karakter, adından da anlaşılacağı gibi herhangi bir oyuncu tarafındandan yönetilmez, sanal zekadır. Çoğu oyunda karşılaşırız mesela en anlamlı örnek, Half-Life' da karşılaştığımız her yaratık, insan, bilim adamı vb. birer NPC dir. Yönetilmezler. Onlar için daha önceden belirlenmiş belli başlı görevleri yaparlar. Bizde CS' de bu şekilde NPC yapabiliriz. Peki NPC ile neler yapabiliriz? Oyun içinde bir market, size sadık bir köpek, bir zombi, size yardım eden bir asker vb. bu şekilde sırayabiliriz. Yani bu NPC işiyle ortaya çok eğlenceli işler çıkabiliyor.

Bu derste biz NPC' ye ne yaptıracağız?

*NPC' yi öldürebileceğiz.
*NPC' yi konuşturacağız.
*NPC'yi hareket ettireceğiz.( şimdilik olduğu yerde )

Öncelikle gerekli kütüphaneleri girelim.

PHP Code:
#include <amxmodx>
#include <amxmisc>
#include <fakemeta>
#include <engine>
#include <hamsandwich> 

Şimdi de plugin için gerekli değişken ve sabit değerleri tanımlıyoruz. Burada NPC için ses, model ve sayısal değişkenleri tanımlayacağız. Buradaki sesleri değiştirebilirsiniz. Ancak modeli değiştirirseniz animasyonlar farklı olabileceği için sorun çıkabilir. Farklı modeller kullanacaksanız Jed's Half-Life Model Viewer programını kullanarak model için gerekli animasyonları seçebilirsiniz. Bunun için de programda bulunan squences bölümünü açın ve oradan hareketi seçip squence# nin karşısındaki sayıyı not alın. Bu sayı model için o hareketin değeridir. Daha sonra değişkendeki sayı değerini not aldığınız sayı ile değiştirebilirsiniz.

PHP Code:
#define PLUGIN "NPC - Non Playar Character - Oyuncu Olmayan Karakter"
#define VERSION "1.0"
#define AUTHOR "peNgueN"

//NPC oldu mu yasiyor mu ?
new boolg_NpcOldu512 ]; 

//NPC Entity Ismi
new const NpcClass[] = "entity_npc"

//NPC Hareketleri
new const g_NpcIdleAnimations[] = { 1314151617 }; //NPC Durus Animasyonlari
new const g_NpcDamageAnimations[] = { 8910 }; //NPC Hasar Animasyonlari
new const g_NpcDeathAnimations[] = { 313233343536 }; //NPC Olum Animasyonlari
new const g_NpcTalkAnimations[] = { 5960616263 }; //NPC Konusma Hareketleri

//NPC kan efektleri
new npc_kan_sprnpc_kan_spr_sprey;

//NPC Modeli
new const g_NpcModel[] = "models/hostage.mdl";

//NPC Sayisi
new NpcSayisi;

//NPC Sesleri
new const g_NpcOlumSesi[][] =  {
    
    
"barney/ba_die1.wav"
    
"barney/ba_die2.wav"
    
"barney/ba_die3.wav" 


new const 
g_NpcHasarSesi[][] = {
    
    
"barney/ba_pain1.wav"
    
"barney/ba_pain2.wav"
    
"barney/ba_pain3.wav" 
}

new const 
g_NpcKonusma[][] = {
    
    
"barney/dontaskme.wav"
    
"barney/haybuddy.wav"
    
"barney/hayfella.wav",
    
"barney/hellonicesuit.wav",
    
"barney/howyoudoing.wav"
    


Daha sonra plugin başlangıcını yazıyoruz.( plugin_init ) Burada NPC için gerekli kodları gireceğiz ve model, sesleri yükleyeceğiz.

PHP Code:
public plugin_init()
{
    
register_pluginPLUGINVERSIONAUTHOR );
    
    
//NPC Kontrol Menusu
    
register_clcmd"say /npc""NpcMenu" );
    
register_clcmd"say_team /npc""NpcMenu" );
    
    
//NPC Kontrol Fonksiyonlari
    
RegisterHamHam_TakeDamage"info_target""fw_NpcTakeDamage" ); //Hasar Fonksiyonu
    
RegisterHamHam_Killed"info_target""fw_NpcKilled" ); //Olum Fonksiyonu
    
RegisterHamHam_Think"info_target""fw_NpcThink" ); //Beyin Fonksiyonu
    
RegisterHamHam_TraceAttack"info_target""fw_NpcTraceAttack" ); //Mermi Fonksiyonu
    
RegisterHamHam_Touch"info_target""fw_NpcTouch" ); //Dokunma Fonksiyonu
}

public 
plugin_precache( )
{
    
npc_kan_spr precache_model"sprites/blood.spr" );
    
npc_kan_spr_sprey precache_model"sprites/bloodspray.spr" );
    
    
precache_modelg_NpcModel );
    
    for( new 
sizeof g_NpcOlumSesi i++)
        
precache_soundg_NpcOlumSesi] );
    
    for( new 
sizeof g_NpcHasarSesi i++)
        
precache_soundg_NpcHasarSesi] );
    
    for( new 
sizeof g_NpcKonusma i++)
        
precache_soundg_NpcKonusma] );    
    


Şimdi NPC için kontrol menüsü yapalım. NPC oluşturup, kaldırabilmek için.

PHP Code:
public NpcMenuid )
{
    new 
iMenu64 ];
    
formatexiMenucharsmaxiMenu ), "NPC - Oyuncu Olmayan Karakter" );
    new 
menu menu_createiMenu"NpcMenu_go" );
    
    
formatexiMenucharsmaxiMenu ), "\wNPC Olustur \y( Aim ile yer belirleyin )" );
    
menu_additemmenuiMenu"1" );
    
formatexiMenucharsmaxiMenu ), "\wNPC Kaldir \y( Aim ile secin )" );
    
menu_additemmenuiMenu"2" );
    
formatexiMenucharsmaxiMenu ), "\wButun NPC'leri Kaldir^n \y  %d NPC Mevcut"NpcSayisi );
    
menu_additemmenuiMenu"3" );
    
    
menu_setpropmenuMPROP_EXITMEXIT_ALL);
    
menu_setpropmenuMPROP_EXITNAME"\rCIKIS" );
    
    
menu_display(idmenu);
    return 
PLUGIN_HANDLED;
}

public 
NpcMenu_goidmenuitem )
{
    
    if( 
item == MENU_EXIT )
    {
        
menu_destroymenu );
        return 
PLUGIN_HANDLED;
    }
    
    new 
info], szName64 ];
    new 
accesscallback;
    
    
menu_item_getinfomenuitemaccessinfocharsmaxinfo ), szNamecharsmaxszName ), callback );
    
    new 
key str_to_numinfo );
    
    switch( 
key )
    {
        case 
1:
        {
            if( !
is_user_aliveid ) ) return PLUGIN_HANDLED;
            
            
NpcOlusturid );
        }
        case 
2:
        {
            if( !
is_user_aliveid ) ) return PLUGIN_HANDLED;
            
            new 
iEntVucutNPC64 ];
            
get_user_aimingidiEntVucut );
            
            if ( 
is_valid_entiEnt ) ) 
            {
                
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
                
                if ( 
equalNPCNpcClass ) ) 
                {
                    
remove_entityiEnt );
                    
NpcSayisi--;
                    
client_printidprint_chat"[NPC] Bir NPC Kaldirildi." );
                }
                
            }
        }
        case 
3:
        {
            
remove_entity_nameNpcClass );
            
NpcSayisi 0;
            
client_printidprint_chat"[NPC] Butun NPC'ler Kaldirildi." );
        }
    }
    
    
    
menu_destroy(menu);
    return 
PLUGIN_HANDLED;


Şimdi de NPC'nin hamsandwich ile oluşturduğumuz kontrol fonksiyonlarını ekleyelim. Burada NPC için, öldürme, dokunma, düşünme ve saldırma fonksiyonları bulunuyor.

PHP Code:
//NPC'ye dokundugumuzda bizmle konusacak ve hareket edecek.
public fw_NpcTouchiEntid 
{
    if( !
is_user_aliveid ) )
        return 
HAM_SUPERCEDE;
    
    
//Sadece 1 kere çalismasi için kontrol ediyoruz.
    
static FloatgametimeFloatCooldown32 ]; 
    
gametime get_gametime();
    
    if(
gametime 1.0 Cooldownid ] )
    {
        
//NPC kontrolu yapiyoruz. Burada NPC mizin ClassName yani ismini sorgulayarak onu baska nesnelerden ayiriyoruz.
        //Sadece bizim NPC mizde calismasi icin kontrol ediyoruz. Duvara degdiginde konusmasini istemeyiz :)
        
new NPC64 ];
        
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
        
        if( 
equaliNPCNpcClass ) )
        {
            
//NPC'ye dokundugumuzda hareket edecek. Hareketleri g_NpcTalkAnimations degiskeninden aldik.
            
Util_PlayAnimationiEntg_NpcTalkAnimationsrandomsizeof g_NpcTalkAnimations ) ] );
            
//NPC'ye dokunudugumuzda bizimle konusucak. Sesleri g_NpcKonusma degiskeninden aldik.
            
emit_soundiEntCHAN_VOICEg_NpcKonusmarandomsizeof g_NpcKonusma ) ],  VOL_NORMATTN_NORM0PITCH_NORM );
        }
        
        
Cooldownid ] = gametime;
    }
    return 
HAM_IGNORED;
}

//NPC'ye hasar verdigimizde hareket edecek ve bagiracak.
public fw_NpcTakeDamageiEntinflictorattackerFloat:damagebits )
{
    
//NPC kontrolu yapiyoruz. Burada NPC mizin ClassName yani ismini sorgulayarak onu baska nesnelerden ayiriyoruz.
    
new NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( 
equaliNPCNpcClass ) )
    {
        
//NPC'ye hasar verdigimizde hareket edecek. Hareketleri g_NpcDamageAnimations degiskeninden aldik.
        
Util_PlayAnimationiEntg_NpcDamageAnimationsrandomsizeof g_NpcDamageAnimations ) ], 1.25 );
        
//NPC'ye hasar verdigimizde bagiracak. Sesleri g_NpcHasarSesi degiskeninden aldik.
        
emit_soundiEntCHAN_VOICEg_NpcHasarSesirandomsizeof g_NpcHasarSesi ) ],  VOL_NORMATTN_NORM0PITCH_NORM );
    }
}

//NPC'yi olduruyoruz.
public fw_NpcKillediEntKiller )
{
    new 
NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( 
equaliNPCNpcClass ) )
    {
        
//g_NpcOldu degiskenini dogru tanimladik.
        
g_NpcOlduiEnt ] = true;
        
//NPC oldugunde olum animasyonu calisacak.
        
Util_PlayAnimation(iEntg_NpcDeathAnimationsrandomsizeof g_NpcDeathAnimations ) ] );
        
//Oldugunde NPC'nin içinden geçebiliriz. SOLID_NOT entity nin içinden geçilmesini kapatir.
        
entity_set_intiEntEV_INT_solidSOLID_NOT );
        
//NPC'yi olu olarak tanimladik.
        
entity_set_intiEntEV_INT_deadflagDEAD_DEAD );
        
//NPC'nin cesedinin hasar almasini kapattik.
        
entity_set_float(iEntEV_FL_takedamage0.0 ); 
        
//NPC oldugunde bagiracak.
        
emit_soundiEntCHAN_VOICEg_NpcOlumSesirandomsizeof g_NpcOlumSesi ) ],  VOL_NORMATTN_NORM0PITCH_NORM );
        
        
client_printKillerprint_chat"[NPC] NPC'yi oldurdunuz." );
        
        
//NPC oldugunden 5 saniye sonra cesedi yerden silinecek.
        
set_task5.0"NpcOluyuKaldir"iEnt );
    }
    return 
HAM_SUPERCEDE;
}

//NPC'yi kaldir
public NpcOluyuKaldirNpc )
{
    
remove_entityNpc );
}

//NPC'nin dusunme fonksiyonu yani beyni. bu fonksiyon içine NPC mize ne yaptirmak istiyorsaniz ekleyebilirsiniz.
//Biz sadece durmasini istiyoruz bu yuzden NPC miz durmaktan baska bisey yapmayacak.
public fw_NpcThinkiEnt )
{
    if( !
is_valid_entiEnt ) )
        return 
HAM_SUPERCEDE;
    
    new 
NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( !
equaliNPCNpcClass ) )
        return 
HAM_SUPERCEDE;
    
    
//Eger NPC'miz oluyse dusunme fonksiyonunu kapat.
    
if( g_NpcOlduiEnt ] )
        return 
HAM_SUPERCEDE;
    
    
//NPC sadece duracak yani durus animasyonu.
    
Util_PlayAnimation(iEntg_NpcIdleAnimationsrandomsizeof g_NpcIdleAnimations ) ] );
    
//NPC'nin beyni her 5 saniyede bir çalisacak.
    
entity_set_floatiEntEV_FL_nextthinkget_gametime() + 5.0 );
    return 
HAM_IGNORED;
}

//NPC hasar fonksiyonu2, fark, bu fonksiyonda hasarimizin yonunu belirleyebiliyoruz. Bir bu fonksiyonu-
//NPC hasar aldiginda vucudundan kan cikmasi icin kullanacagiz.
public fw_NpcTraceAttack(iEntattackerFloatdamageFloatdirection[3], tracedamageBits)
{
    if( !
is_valid_entiEnt ) )
        return 
HAM_SUPERCEDE;
    
    new 
NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( 
equaliNPCNpcClass ) )
    {
        
//NPC hasar alma kapaliysa kan cikmasin.
        
if( entity_get_floatiEntEV_FL_takedamage ) == 0.0 )
            return 
HAM_SUPERCEDE;
        
        
//Merminin son carptigi yerin koordinatlarini buluyoruz.
        
new Floatend];
        
get_tr2traceTR_vecEndPosend );
        
        
//Mermi NPC'nin neresine çarptiysa kan o bolgeden cikacak.
        
message_beginMSG_BROADCAST,SVC_TEMPENTITY );
        
write_byteTE_BLOODSPRITE );
        
engfuncEngFunc_WriteCoordend] );
        
engfuncEngFunc_WriteCoordend] );
        
engfuncEngFunc_WriteCoordend] );
        
write_shortnpc_kan_spr_sprey );
        
write_shortnpc_kan_spr );
        
write_byte247 );
        
write_byterandom_num515 ) ); 
        
message_end();
    }
    return 
HAM_IGNORED;


NPC için ekstra oluşturduğumuz stockları ekliyoruz. NPC için hareket ve Nişan alınan noktanın koordinatları fonksiyonlarını kullanacağız.

PHP Code:
//NPC icin animasyon,hareket fonksiyonu.
stock Util_PlayAnimation(indexsequenceFloatframerate 1.0)
{
    
entity_set_float(indexEV_FL_animtimeget_gametime());
    
entity_set_float(indexEV_FL_framerate,  framerate);
    
entity_set_float(indexEV_FL_frame0.0);
    
entity_set_int(indexEV_INT_sequencesequence);
}  

//Nisan alinan noktanin koordinatlarini bul. - akcaliberkk
stock get_user_hitpoint(idFloat:hOrigin[3]) {
    if ( ! 
is_user_aliveid ))
        return 
0;
    
    new 
Float:fOrigin[3], Float:fvAngle[3], Float:fvOffset[3], Float:fvOrigin[3], Float:feOrigin[3];
    new 
Float:fTemp[3];
    
    
pev(idpev_originfOrigin);
    
pev(idpev_v_anglefvAngle);
    
pev(idpev_view_ofsfvOffset);
    
    
xs_vec_add(fOriginfvOffsetfvOrigin);
    
    
engfunc(EngFunc_AngleVectorsfvAnglefeOriginfTempfTemp);
    
    
xs_vec_mul_scalar(feOrigin9999.9feOrigin);
    
xs_vec_add(fvOriginfeOriginfeOrigin);
    
    
engfunc(EngFunc_TraceLinefvOriginfeOrigin0id);
    
global_get(glb_trace_endposhOrigin);
    return 
1;


ve son olarak NPC'mizi oluşturuyoruz. Kodların üstünde açıkladım bazı değerleri istediğiniz gibi ayarlayabilirsiniz.

PHP Code:
//ve NPC mizi bu fonksiyonda olusturuyoruz.
public NpcOlusturid )
{
    
//NPC icin koordinat ve aci degiskenleri olusturduk.
    
new FloatOrigin], FloatAngle];
    
    
//Herhangi bir entity yani nesne yaratiyoruz sonra bu nesneyi NPC olarak tanimlayacagiz.
    
new iEnt create_entity"info_target" );
    
//Yaptigimiz nesneyi bizim NPC miz olarak tanimladik.
    
entity_set_stringiEntEV_SZ_classnameNpcClass );
    
    
//Aim ile koordinatlari buluyoruz. NPC miz o koordinatlarda olucak.
    
get_user_hitpointidOrigin );
    
Origin] += 70.0;
    
entity_set_originiEntOrigin );
    
    
//Oyuncunun bakis acisini aliyoruzki NPC de o acida olussun.
    
entity_get_vector(idEV_VEC_anglesAngle );
    
Angle] = 0.0;
    
    
entity_set_vectoriEntEV_VEC_anglesAngle );
    
    
//NPC mizin modelini ayarliyoruz.
    
entity_set_modeliEntg_NpcModel );
    
//NPC miz hareketini ayarliyoruz. Yani ittirilebilir bir entity olacak.
    
entity_set_int(iEntEV_INT_movetypeMOVETYPE_PUSHSTEP );
    
//NPC miz içi dolu bir nesne olucak yani içinden geçemeyiz.
    
entity_set_int(iEntEV_INT_solidSOLID_BBOX );
    
    
//NPC miz hasar alabilir.
    
entity_set_floatiEntEV_FL_takedamage1.0 );
    
//NPC'nin canini 500 yaptik.
    
entity_set_floatiEntEV_FL_health500.0 );
    
    
//Simdide NPC mizin buyuklugunu ayarliyoruz bu degerler min ve max olarak ayarlanir. 3 boyutlu olarak yani.
    
new Floatmins[3] = {-12.0, -12.00.0 };
    new 
Floatmaxs[3] = { 12.012.075.0 };
    
    
entity_set_size(iEntminsmaxs);
    
    
//NPC kafasini kontrol edebilir.
    
entity_set_byteiEntEV_BYTE_controller1125 );
    
    
//ve NPC mizi yere sabitliyoruz yanlis anlamayin yani havada duvarda vb. yerde olusabilir eger olusursa yere indirir
    //bu kod.
    
drop_to_flooriEnt );
    
    
//NPC mizin canli oldugunu tanimliyoruz.
    
g_NpcOlduiEnt ] = false;
    
//NPC sayisina +1 ekliyoruz.
    
NpcSayisi++;
    
    
//NPC nin beyni 1 saniye sonra calisacak. 
    
entity_set_floatiEntEV_FL_nextthinkget_gametime() + 1.0 );    



NPC plugininin son hali:

PHP Code:
#include <amxmodx>
#include <amxmisc>
#include <fakemeta>
#include <engine>
#include <hamsandwich>  

#define PLUGIN "NPC - Non Playar Character - Oyuncu Olmayan Karakter"
#define VERSION "1.0"
#define AUTHOR "peNgueN"

//NPC oldu mu yasiyor mu ?
new boolg_NpcOldu512 ]; 

//NPC Entity Ismi
new const NpcClass[] = "entity_npc"

//NPC Hareketleri
new const g_NpcIdleAnimations[] = { 1314151617 }; //NPC Durus Animasyonlari
new const g_NpcDamageAnimations[] = { 8910 }; //NPC Hasar Animasyonlari
new const g_NpcDeathAnimations[] = { 313233343536 }; //NPC Olum Animasyonlari
new const g_NpcTalkAnimations[] = { 5960616263 }; //NPC Konusma Hareketleri

//NPC kan efektleri
new npc_kan_sprnpc_kan_spr_sprey;

//NPC Modeli
new const g_NpcModel[] = "models/hostage.mdl";

//NPC Sayisi
new NpcSayisi;

//NPC Sesleri
new const g_NpcOlumSesi[][] =  {
    
    
"barney/ba_die1.wav"
    
"barney/ba_die2.wav"
    
"barney/ba_die3.wav" 


new const 
g_NpcHasarSesi[][] = {
    
    
"barney/ba_pain1.wav"
    
"barney/ba_pain2.wav"
    
"barney/ba_pain3.wav" 
}

new const 
g_NpcKonusma[][] = {
    
    
"barney/dontaskme.wav"
    
"barney/haybuddy.wav"
    
"barney/hayfella.wav",
    
"barney/hellonicesuit.wav",
    
"barney/howyoudoing.wav"
    
}

public 
plugin_init()
{
    
register_pluginPLUGINVERSIONAUTHOR );
    
    
//NPC Kontrol Menusu
    
register_clcmd"say /npc""NpcMenu" );
    
register_clcmd"say_team /npc""NpcMenu" );
    
    
//NPC Kontrol Fonksiyonlari
    
RegisterHamHam_TakeDamage"info_target""fw_NpcTakeDamage" ); //Hasar Fonksiyonu
    
RegisterHamHam_Killed"info_target""fw_NpcKilled" ); //Olum Fonksiyonu
    
RegisterHamHam_Think"info_target""fw_NpcThink" ); //Beyin Fonksiyonu
    
RegisterHamHam_TraceAttack"info_target""fw_NpcTraceAttack" ); //Mermi Fonksiyonu
    
RegisterHamHam_Touch"info_target""fw_NpcTouch" ); //Dokunma Fonksiyonu
}

public 
plugin_precache( )
{
    
npc_kan_spr precache_model"sprites/blood.spr" );
    
npc_kan_spr_sprey precache_model"sprites/bloodspray.spr" );
    
    
precache_modelg_NpcModel );
    
    for( new 
sizeof g_NpcOlumSesi i++)
        
precache_soundg_NpcOlumSesi] );
    
    for( new 
sizeof g_NpcHasarSesi i++)
        
precache_soundg_NpcHasarSesi] );
    
    for( new 
sizeof g_NpcKonusma i++)
        
precache_soundg_NpcKonusma] );    
    
}

public 
NpcMenuid )
{
    new 
iMenu64 ];
    
formatexiMenucharsmaxiMenu ), "NPC - Oyuncu Olmayan Karakter" );
    new 
menu menu_createiMenu"NpcMenu_go" );
    
    
formatexiMenucharsmaxiMenu ), "\wNPC Olustur \y( Aim ile yer belirleyin )" );
    
menu_additemmenuiMenu"1" );
    
formatexiMenucharsmaxiMenu ), "\wNPC Kaldir \y( Aim ile secin )" );
    
menu_additemmenuiMenu"2" );
    
formatexiMenucharsmaxiMenu ), "\wButun NPC'leri Kaldir^n \y  %d NPC Mevcut"NpcSayisi );
    
menu_additemmenuiMenu"3" );
    
    
menu_setpropmenuMPROP_EXITMEXIT_ALL);
    
menu_setpropmenuMPROP_EXITNAME"\rCIKIS" );
    
    
menu_display(idmenu);
    return 
PLUGIN_HANDLED;
}

public 
NpcMenu_goidmenuitem )
{
    
    if( 
item == MENU_EXIT )
    {
        
menu_destroymenu );
        return 
PLUGIN_HANDLED;
    }
    
    new 
info], szName64 ];
    new 
accesscallback;
    
    
menu_item_getinfomenuitemaccessinfocharsmaxinfo ), szNamecharsmaxszName ), callback );
    
    new 
key str_to_numinfo );
    
    switch( 
key )
    {
        case 
1:
        {
            if( !
is_user_aliveid ) ) return PLUGIN_HANDLED;
            
            
NpcOlusturid );
        }
        case 
2:
        {
            if( !
is_user_aliveid ) ) return PLUGIN_HANDLED;
            
            new 
iEntVucutNPC64 ];
            
get_user_aimingidiEntVucut );
            
            if ( 
is_valid_entiEnt ) ) 
            {
                
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
                
                if ( 
equalNPCNpcClass ) ) 
                {
                    
remove_entityiEnt );
                    
NpcSayisi--;
                    
client_printidprint_chat"[NPC] Bir NPC Kaldirildi." );
                }
                
            }
        }
        case 
3:
        {
            
remove_entity_nameNpcClass );
            
NpcSayisi 0;
            
client_printidprint_chat"[NPC] Butun NPC'ler Kaldirildi." );
        }
    }
    
    
    
menu_destroy(menu);
    return 
PLUGIN_HANDLED;
}


//NPC'ye dokundugumuzda bizmle konusacak ve hareket edecek.
public fw_NpcTouchiEntid 
{
    if( !
is_user_aliveid ) )
        return 
HAM_SUPERCEDE;
    
    
//Sadece 1 kere çalismasi için kontrol ediyoruz.
    
static FloatgametimeFloatCooldown32 ]; 
    
gametime get_gametime();
    
    if(
gametime 1.0 Cooldownid ] )
    {
        
//NPC kontrolu yapiyoruz. Burada NPC mizin ClassName yani ismini sorgulayarak onu baska nesnelerden ayiriyoruz.
        //Sadece bizim NPC mizde calismasi icin kontrol ediyoruz. Duvara degdiginde konusmasini istemeyiz :)
        
new NPC64 ];
        
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
        
        if( 
equaliNPCNpcClass ) )
        {
            
//NPC'ye dokundugumuzda hareket edecek. Hareketleri g_NpcTalkAnimations degiskeninden aldik.
            
Util_PlayAnimationiEntg_NpcTalkAnimationsrandomsizeof g_NpcTalkAnimations ) ] );
            
//NPC'ye dokunudugumuzda bizimle konusucak. Sesleri g_NpcKonusma degiskeninden aldik.
            
emit_soundiEntCHAN_VOICEg_NpcKonusmarandomsizeof g_NpcKonusma ) ],  VOL_NORMATTN_NORM0PITCH_NORM );
        }
        
        
Cooldownid ] = gametime;
    }
    return 
HAM_IGNORED;
}

//NPC'ye hasar verdigimizde hareket edecek ve bagiracak.
public fw_NpcTakeDamageiEntinflictorattackerFloat:damagebits )
{
    
//NPC kontrolu yapiyoruz. Burada NPC mizin ClassName yani ismini sorgulayarak onu baska nesnelerden ayiriyoruz.
    
new NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( 
equaliNPCNpcClass ) )
    {
        
//NPC'ye hasar verdigimizde hareket edecek. Hareketleri g_NpcDamageAnimations degiskeninden aldik.
        
Util_PlayAnimationiEntg_NpcDamageAnimationsrandomsizeof g_NpcDamageAnimations ) ], 1.25 );
        
//NPC'ye hasar verdigimizde bagiracak. Sesleri g_NpcHasarSesi degiskeninden aldik.
        
emit_soundiEntCHAN_VOICEg_NpcHasarSesirandomsizeof g_NpcHasarSesi ) ],  VOL_NORMATTN_NORM0PITCH_NORM );
    }
}

//NPC'yi olduruyoruz.
public fw_NpcKillediEntKiller )
{
    new 
NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( 
equaliNPCNpcClass ) )
    {
        
//g_NpcOldu degiskenini dogru tanimladik.
        
g_NpcOlduiEnt ] = true;
        
//NPC oldugunde olum animasyonu calisacak.
        
Util_PlayAnimation(iEntg_NpcDeathAnimationsrandomsizeof g_NpcDeathAnimations ) ] );
        
//Oldugunde NPC'nin içinden geçebiliriz. SOLID_NOT entity nin içinden geçilmesini kapatir.
        
entity_set_intiEntEV_INT_solidSOLID_NOT );
        
//NPC'yi olu olarak tanimladik.
        
entity_set_intiEntEV_INT_deadflagDEAD_DEAD );
        
//NPC'nin cesedinin hasar almasini kapattik.
        
entity_set_float(iEntEV_FL_takedamage0.0 ); 
        
//NPC oldugunde bagiracak.
        
emit_soundiEntCHAN_VOICEg_NpcOlumSesirandomsizeof g_NpcOlumSesi ) ],  VOL_NORMATTN_NORM0PITCH_NORM );
        
        
client_printKillerprint_chat"[NPC] NPC'yi oldurdunuz." );
        
        
//NPC oldugunden 5 saniye sonra cesedi yerden silinecek.
        
set_task5.0"NpcOluyuKaldir"iEnt );
    }
    return 
HAM_SUPERCEDE;
}

//NPC'yi kaldir
public NpcOluyuKaldirNpc )
{
    
remove_entityNpc );
}

//NPC'nin dusunme fonksiyonu yani beyni. bu fonksiyon içine NPC mize ne yaptirmak istiyorsaniz ekleyebilirsiniz.
//Biz sadece durmasini istiyoruz bu yuzden NPC miz durmaktan baska bisey yapmayacak.
public fw_NpcThinkiEnt )
{
    if( !
is_valid_entiEnt ) )
        return 
HAM_SUPERCEDE;
    
    new 
NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( !
equaliNPCNpcClass ) )
        return 
HAM_SUPERCEDE;
    
    
//Eger NPC'miz oluyse dusunme fonksiyonunu kapat.
    
if( g_NpcOlduiEnt ] )
        return 
HAM_SUPERCEDE;
    
    
//NPC sadece duracak yani durus animasyonu.
    
Util_PlayAnimation(iEntg_NpcIdleAnimationsrandomsizeof g_NpcIdleAnimations ) ] );
    
//NPC'nin beyni her 5 saniyede bir çalisacak.
    
entity_set_floatiEntEV_FL_nextthinkget_gametime() + 5.0 );
    return 
HAM_IGNORED;
}

//NPC hasar fonksiyonu2, fark, bu fonksiyonda hasarimizin yonunu belirleyebiliyoruz. Bir bu fonksiyonu-
//NPC hasar aldiginda vucudundan kan cikmasi icin kullanacagiz.
public fw_NpcTraceAttack(iEntattackerFloatdamageFloatdirection[3], tracedamageBits)
{
    if( !
is_valid_entiEnt ) )
        return 
HAM_SUPERCEDE;
    
    new 
NPC64 ];
    
entity_get_stringiEntEV_SZ_classnameNPCcharsmaxNPC ) );
    
    if( 
equaliNPCNpcClass ) )
    {
        
//NPC hasar alma kapaliysa kan cikmasin.
        
if( entity_get_floatiEntEV_FL_takedamage ) == 0.0 )
            return 
HAM_SUPERCEDE;
        
        
//Merminin son carptigi yerin koordinatlarini buluyoruz.
        
new Floatend];
        
get_tr2traceTR_vecEndPosend );
        
        
//Mermi NPC'nin neresine çarptiysa kan o bolgeden cikacak.
        
message_beginMSG_BROADCAST,SVC_TEMPENTITY );
        
write_byteTE_BLOODSPRITE );
        
engfuncEngFunc_WriteCoordend] );
        
engfuncEngFunc_WriteCoordend] );
        
engfuncEngFunc_WriteCoordend] );
        
write_shortnpc_kan_spr_sprey );
        
write_shortnpc_kan_spr );
        
write_byte247 );
        
write_byterandom_num515 ) ); 
        
message_end();
    }
    return 
HAM_IGNORED;
}

//NPC icin animasyon,hareket fonksiyonu.
stock Util_PlayAnimation(indexsequenceFloatframerate 1.0)
{
    
entity_set_float(indexEV_FL_animtimeget_gametime());
    
entity_set_float(indexEV_FL_framerate,  framerate);
    
entity_set_float(indexEV_FL_frame0.0);
    
entity_set_int(indexEV_INT_sequencesequence);
}  

//Nisan alinan noktanin koordinatlarini bul.
stock get_user_hitpoint(idFloat:hOrigin[3]) {
    if ( ! 
is_user_aliveid ))
        return 
0;
    
    new 
Float:fOrigin[3], Float:fvAngle[3], Float:fvOffset[3], Float:fvOrigin[3], Float:feOrigin[3];
    new 
Float:fTemp[3];
    
    
pev(idpev_originfOrigin);
    
pev(idpev_v_anglefvAngle);
    
pev(idpev_view_ofsfvOffset);
    
    
xs_vec_add(fOriginfvOffsetfvOrigin);
    
    
engfunc(EngFunc_AngleVectorsfvAnglefeOriginfTempfTemp);
    
    
xs_vec_mul_scalar(feOrigin9999.9feOrigin);
    
xs_vec_add(fvOriginfeOriginfeOrigin);
    
    
engfunc(EngFunc_TraceLinefvOriginfeOrigin0id);
    
global_get(glb_trace_endposhOrigin);
    return 
1;
}  

//ve NPC mizi bu fonksiyonda olusturuyoruz.
public NpcOlusturid )
{
    
//NPC icin koordinat ve aci degiskenleri olusturduk.
    
new FloatOrigin], FloatAngle];
    
    
//Herhangi bir entity yani nesne yaratiyoruz sonra bu nesneyi NPC olarak tanimlayacagiz.
    
new iEnt create_entity"info_target" );
    
//Yaptigimiz nesneyi bizim NPC miz olarak tanimladik.
    
entity_set_stringiEntEV_SZ_classnameNpcClass );
    
    
//Aim ile koordinatlari buluyoruz. NPC miz o koordinatlarda olucak.
    
get_user_hitpointidOrigin );
    
Origin] += 70.0;
    
entity_set_originiEntOrigin );
    
    
//Oyuncunun bakis acisini aliyoruzki NPC de o acida olussun.
    
entity_get_vector(idEV_VEC_anglesAngle );
    
Angle] = 0.0;
    
    
entity_set_vectoriEntEV_VEC_anglesAngle );
    
    
//NPC mizin modelini ayarliyoruz.
    
entity_set_modeliEntg_NpcModel );
    
//NPC miz hareketini ayarliyoruz. Yani ittirilebilir bir entity olacak.
    
entity_set_int(iEntEV_INT_movetypeMOVETYPE_PUSHSTEP );
    
//NPC miz içi dolu bir nesne olucak yani içinden geçemeyiz.
    
entity_set_int(iEntEV_INT_solidSOLID_BBOX );
    
    
//NPC miz hasar alabilir.
    
entity_set_floatiEntEV_FL_takedamage1.0 );
    
//NPC'nin canini 500 yaptik.
    
entity_set_floatiEntEV_FL_health500.0 );
    
    
//Simdide NPC mizin buyuklugunu ayarliyoruz bu degerler min ve max olarak ayarlanir. 3 boyutlu olarak yani.
    
new Floatmins[3] = {-12.0, -12.00.0 };
    new 
Floatmaxs[3] = { 12.012.075.0 };
    
    
entity_set_size(iEntminsmaxs);
    
    
//NPC kafasini kontrol edebilir.
    
entity_set_byteiEntEV_BYTE_controller1125 );
    
    
//ve NPC mizi yere sabitliyoruz yanlis anlamayin yani havada duvarda vb. yerde olusabilir eger olusursa yere indirir
    //bu kod.
    
drop_to_flooriEnt );
    
    
//NPC mizin canli oldugunu tanimliyoruz.
    
g_NpcOlduiEnt ] = false;
    
//NPC sayisina +1 ekliyoruz.
    
NpcSayisi++;
    
    
//NPC nin beyni 1 saniye sonra calisacak. 
    
entity_set_floatiEntEV_FL_nextthinkget_gametime() + 1.0 );    


İşte NPC miz:


[Image: REDdm1.png]


Evet biraz gelişmiş bir NPC oluşturduk. Bu eklentide ki NPC konuşabiliyor, hasar alabiliyor ve hareket edebiliyor ama sadece yerinde duruyor. Bir menü yardımıyla NPC oluşturabilir, onu silebilirsiniz. Bu arada menü kodu "say /npc" Daha sonra biraz daha geliştirebiliriz. Hareket eden, koşan bir NPC gibi.

Anlamadığınız yer olursa sorabilirsiniz. Eklentide hata, bug, sorun olursa veya daha mantıklı bir algoritma varsa beni uyarabilirsiniz.

Kolay gelsin.

PAWN
KOD YARDIMCISI


Eklentiyle ilgili her türlü yardımı edebilirim.( jail shop hariç )
İletişim: hassel-vl
Reply
#2
@peNgueN Bu npc olayı vhe içinde mevcut fakat cs nin eski versyonlarında kaldırılmış sadece half-life için geçerli olmuş. Bunun gibi bir pluginle mapa koyduğumuz npcler geri cs tarafından görülürmü ?. Mesela sen entity_npc oluşturmuşsun .Aşşağıda half-life ın orjinal fgdsinden 2 tane entity kodunu koydum bunları plugin ile csye tekrar entegre edebilirmiyiz?
PHP Code:
@PointClass base(TargetnameTargetxsize(-16 -16 016 16 72color(255 0 255) = scripted_sentence "Scripted Sentence"
[
    
spawnflags(Flags) = 
    [
        
"Fire Once"     1
        2 
"Followers Only"    0
        4 
"Interrupt Speech"    1
        8 
"Concurrent"    0
    
]
    
sentence(string) : "Sentence Name" ""
    
entity(string) : "Speaker Type"
    
duration(string) : "Sentence Time" "3"
    
radius(integer) : "Search Radius" 512
    refire
(string) : "Delay Before Refire" "3"
    
listener(string) : "Listener Type"
    
volume(string) : "Volume 0-10" "10"
    
attenuation(Choices) : "Sound Radius" =
    [
        
"Small Radius"
        
"Medium Radius"
        
"Large  Radius"
        
"Play Everywhere"
    
]
]


@
PointClass base(TargetnameTargetxAnglessize(-16 -16 016 16 72color(255 0 255) = scripted_sequence "Scripted Sequence"
[
    
m_iszEntity(string) : "Target Monster"
    
m_iszPlay(string) : "Action Animation" ""
    
m_iszIdle(string) : "Idle Animation" ""
    
m_flRadius(integer) : "Search Radius" 512
    m_flRepeat
(integer) : "Repeat Rate ms" 0
    m_fMoveTo
(choices) : "Move to Position" =
    [
        
"No"
        
"Walk"
        
"Run"
        
"Instantaneous"
        
"No - Turn to Face"
    
]
    
spawnflags(Flags) = 
    [
        
"Repeatable"    0
        8 
"Leave Corpse"    0
        32
"No Interruptions"    0
        64
"Override AI"    0
        128
"No Script Movement" 0
    
]

Only Know You've Been High When You Feeling Low
CSPLAGUE Forumu ;

Quote:
9 Moderatör
0 Süper Moderatör
2 Co-Admin
1 Admin

Toplamda 12 yönetim üyesiyle çalışıyor!



Reply
#3
@peNgueN Eline Saglık Cok Fayladı Olmuş Bunun Gibi Derslerin devamını bekliyoruz Big Grin
Reply
#4
[MENTION=24]kaptan647[/MENTION] eğer serverde metamod kuruluysa ve bu kütüphaneler mevcutsa olur.

PAWN
KOD YARDIMCISI


Eklentiyle ilgili her türlü yardımı edebilirim.( jail shop hariç )
İletişim: hassel-vl
Reply
#5
Gayet Güzel Anlatmışın Big Grin

Heralde Artık Bizde Belki Çalışırız Big Grin
Coder İmza
PHP Code:
İletişim => cebinihat@hotmail.com 

Model İmza
PHP Code:
İletişim => cebinihat@hotmail.com 

CSP Signatür
PHP Code:
İletişim => cebinihat@hotmail.com 


En İyi Konularım:
Leqend Shop | Furkan Dize Shop |

Reply
#6
Bu dediğim olaylar olursa çok hoş olabilir çünkü vhe den npc yapıp bu npcye birşeyler yaptırmak tahminimce pluginle bunları yapmaktan daha kolay
Only Know You've Been High When You Feeling Low
CSPLAGUE Forumu ;

Quote:
9 Moderatör
0 Süper Moderatör
2 Co-Admin
1 Admin

Toplamda 12 yönetim üyesiyle çalışıyor!



Reply
#7
Beyler Ben şimdi cso venom guard ayarladım modelini onun patlama kodu ne söleyebilirmisiniz?

yardım ederseniz çok sevinirim Smile
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
  Yeni Başlağınca / Oyuncu Doğunca / Yeni Başı / El Sonu Losteps 10 7,325 02-07-15, 00:12
Last Post: CeyhunAKTEPE

Foruma Atla:


Users browsing this thread: 1 Guest(s)