Фикс стрелы

Статус
В этой теме нельзя размещать новые ответы.
Сообщения
7
Реакции
-15
День добрый, Собственно требуется помощь с фиксом плагина [ZP] Weapon Stinger
Оружие выпускает стрелу, которая цепляется за ентити и игроков. Как можно сделать, чтобы стрела не встревала в людей, а только в зомби и другие объекты?
Заранее низкий поклон
Код:
/*
*        [1.0] - Первый релиз
*
*            [1.0.1] - Bug fix: WeaponList на кастомных оружиях M249 не работал, кроме этого оружия
*
*            [1.0.2] - Перенос Touch & Think с fakemeta на hamsandwich модуль
*/

#include <amxmodx>
#include <fakemeta_util>
#include <hamsandwich>
#include <zombieplague>

#define IsCustomItem(%0)             (pev(%0, pev_impulse) == WEAPON_SPECIAL_CODE)

#define PDATA_SAFE                     2
#define DMG_GRENADE                    (1<<24)

/* ~ [ Weapon Animations ] ~ */
#define WEAPON_ANIM_IDLE_TIME         61/30.0
#define WEAPON_ANIM_SHOOT_TIME         31/30.0
#define WEAPON_ANIM_RELOAD_TIME     59/30.0
#define WEAPON_ANIM_DRAW_TIME         46/30.0

enum
{
    WEAPON_ANIM_IDLE = 0,
    WEAPON_ANIM_IDLE2,
    WEAPON_ANIM_IDLE3,
    WEAPON_ANIM_SHOOT,
    WEAPON_ANIM_SHOOT2,
    WEAPON_ANIM_SHOOT3,
    WEAPON_ANIM_RELOAD,
    WEAPON_ANIM_DRAW,
    WEAPON_ANIM_DRAW2,
    WEAPON_ANIM_DRAW3,
    WEAPON_ANIM_DRAW_EMPTY,
    WEAPON_ANIM_IDLE_EMPTY,
    WEAPON_ANIM_SHOOT_EMPTY
};

/* ~ [ Extra Item ] ~ */
new const WEAPON_ITEM_NAME[]         = "Stinger";
const WEAPON_ITEM_COST                 = 0;

/* ~ [ Weapon Settings ] ~ */
new const WEAPON_REFERENCE[]         = "weapon_m249";
new const WEAPON_WEAPONLIST[]         = "x/weapon_speargunm";
new const WEAPON_NATIVE[]             = "zp_give_user_speargunm";
new const WEAPON_MODEL_VIEW[]         = "models/x/v_speargunm.mdl";
new const WEAPON_MODEL_PLAYER[]        = "models/x/p_speargunm.mdl";
new const WEAPON_MODEL_WORLD[]        = "models/x/w_speargunm.mdl";
new const WEAPON_SOUND_FIRE[]        = "weapons/speargunm-1.wav";
new const WEAPON_SOUND_EMPTY[]        = "weapons/speargunm_empty.wav";

const WEAPON_SPECIAL_CODE             = 2019;
const WEAPON_BODY                     = 0;

const WEAPON_MAX_CLIP                 = 3;
const WEAPON_DEFAULT_AMMO             = 30;
const Float: WEAPON_RATE             = 0.88;

new const iWeaponList[]             = { 3, WEAPON_DEFAULT_AMMO,-1, -1, 0, 4, 20, 0 };

/* ~ [ Entity ] ~ */
new const ENTITY_REFERENCE[]        = "info_target";
new const ENTITY_CLASSNAME[]        = "ent_spearm";
new const ENTITY_MODEL[]            = "models/x/spearm.mdl";
new const ENTITY_EXPLODE_MODEL[]    = "models/x/spearm2.mdl";
new const ENTITY_EXPLODE_SPRITE[]    = "sprites/fexplo.spr";
new const ENTITY_TRAIL_SPRITE[]     = "sprites/laserbeam.spr";
const Float: ENTITY_SPEED            = 2000.0; // Max value 2000
const Float: ENTITY_KNOCKBACK        = 1500.0;
const Float: ENTITY_KNOCK_EXP        = 225.0;
const Float: ENTITY_DAMAGE            = 250.0;
const Float: ENTITY_RADIUS_EXP        = 100.0;
#define ENTITY_DAMAGE_EXP            random_float(250.0, 400.0)

/* ~ [ Offsets ] ~ */
// Linux extra offsets
#define linux_diff_weapon 4
#define linux_diff_player 5

// CWeaponBox
#define m_rgpPlayerItems_CWeaponBox 34

// CBaseAnimating
#define m_flLastEventCheck 38

// CBasePlayerItem
#define m_pPlayer 41
#define m_pNext 42
#define m_iId 43

// CBasePlayerWeapon
#define m_flNextPrimaryAttack 46
#define m_flNextSecondaryAttack 47
#define m_flTimeWeaponIdle 48
#define m_iPrimaryAmmoType 49
#define m_iClip 51
#define m_fInReload 54

// CBaseMonster
#define m_LastHitGroup 75
#define m_flNextAttack 83

// CBasePlayer
#define m_rpgPlayerItems 367
#define m_pActiveItem 373
#define m_rgAmmo 376

/* ~ [ Params ] ~ */
new g_iszAllocString_Entity,
    g_iszAllocString_ModelView,
    g_iszAllocString_ModelPlayer,

    g_iszAllocString_InfoTarget,
    g_iszAllocString_SpearClass,

    g_iszModelIndex_BloodSpray,
    g_iszModelIndex_BloodDrop,
    g_iszModelIndex_LaserBeam,
    g_iszModelIndex_Explosion,
    g_iszModelIndex_BreakSpear,

    g_iMsgID_Weaponlist,
    g_iItemID;

public plugin_init()
{
    register_plugin("[ZP] Weapon: Stinger", "1.0.2", "xUnicorn (t3rkecorejz) / Batcoh: Code base");

    g_iItemID = zp_register_extra_item(WEAPON_ITEM_NAME, WEAPON_ITEM_COST, ZP_TEAM_HUMAN);

    register_forward(FM_UpdateClientData,    "FM_Hook_UpdateClientData_Post", true);
    register_forward(FM_SetModel,             "FM_Hook_SetModel_Pre", false);

    RegisterHam(Ham_Item_Holster,            WEAPON_REFERENCE,    "CWeapon__Holster_Post", true);
    RegisterHam(Ham_Item_Deploy,            WEAPON_REFERENCE,    "CWeapon__Deploy_Post", true);
    RegisterHam(Ham_Item_PostFrame,            WEAPON_REFERENCE,    "CWeapon__PostFrame_Pre", false);
    RegisterHam(Ham_Item_AddToPlayer,        WEAPON_REFERENCE,    "CWeapon__AddToPlayer_Post", true);
    RegisterHam(Ham_Weapon_Reload,            WEAPON_REFERENCE,    "CWeapon__Reload_Pre", false);
    RegisterHam(Ham_Weapon_WeaponIdle,        WEAPON_REFERENCE,    "CWeapon__WeaponIdle_Pre", false);
    RegisterHam(Ham_Weapon_PrimaryAttack,    WEAPON_REFERENCE,    "CWeapon__PrimaryAttack_Pre", false);

    RegisterHam(Ham_Think,                    ENTITY_REFERENCE,    "CEntity__Think_Pre", false);
    RegisterHam(Ham_Touch,                    ENTITY_REFERENCE,    "CEntity__Touch_Pre", false);

    g_iMsgID_Weaponlist = get_user_msgid("WeaponList");
}

public plugin_precache()
{
    // Hook weapon
    register_clcmd(WEAPON_WEAPONLIST, "Command_HookWeapon");

    // Precache models
    engfunc(EngFunc_PrecacheModel, WEAPON_MODEL_VIEW);
    engfunc(EngFunc_PrecacheModel, WEAPON_MODEL_PLAYER);
    engfunc(EngFunc_PrecacheModel, WEAPON_MODEL_WORLD);

    engfunc(EngFunc_PrecacheModel, ENTITY_MODEL);

    // Precache generic
    UTIL_PrecacheSpritesFromTxt(WEAPON_WEAPONLIST);
  
    // Precache sounds
    engfunc(EngFunc_PrecacheSound, WEAPON_SOUND_FIRE);
    engfunc(EngFunc_PrecacheSound, WEAPON_SOUND_EMPTY);

    UTIL_PrecacheSoundsFromModel(WEAPON_MODEL_VIEW);

    // Other
    g_iszAllocString_Entity = engfunc(EngFunc_AllocString, WEAPON_REFERENCE);
    g_iszAllocString_ModelView = engfunc(EngFunc_AllocString, WEAPON_MODEL_VIEW);
    g_iszAllocString_ModelPlayer = engfunc(EngFunc_AllocString, WEAPON_MODEL_PLAYER);

    g_iszAllocString_InfoTarget = engfunc(EngFunc_AllocString, ENTITY_REFERENCE);
    g_iszAllocString_SpearClass = engfunc(EngFunc_AllocString, ENTITY_CLASSNAME);

    g_iszModelIndex_BloodSpray = engfunc(EngFunc_PrecacheModel, "sprites/bloodspray.spr");
    g_iszModelIndex_BloodDrop = engfunc(EngFunc_PrecacheModel, "sprites/blood.spr");
    g_iszModelIndex_LaserBeam = engfunc(EngFunc_PrecacheModel, ENTITY_TRAIL_SPRITE);
    g_iszModelIndex_Explosion = engfunc(EngFunc_PrecacheModel, ENTITY_EXPLODE_SPRITE);
    g_iszModelIndex_BreakSpear = engfunc(EngFunc_PrecacheModel, ENTITY_EXPLODE_MODEL);
}

public plugin_natives() register_native(WEAPON_NATIVE, "Command_GiveWeapon", 1);

// [ Amxx ]
public zp_extra_item_selected(iPlayer, iItem)
{
    if(iItem == g_iItemID)
        Command_GiveWeapon(iPlayer);
}

public Command_HookWeapon(iPlayer)
{
    engclient_cmd(iPlayer, WEAPON_REFERENCE);
    return PLUGIN_HANDLED;
}

public Command_GiveWeapon(iPlayer)
{
    static iEntity; iEntity = engfunc(EngFunc_CreateNamedEntity, g_iszAllocString_Entity);
    if(iEntity <= 0) return 0;

    set_pev(iEntity, pev_impulse, WEAPON_SPECIAL_CODE);
    ExecuteHam(Ham_Spawn, iEntity);
    set_pdata_int(iEntity, m_iClip, WEAPON_MAX_CLIP, linux_diff_weapon);
    UTIL_DropWeapon(iPlayer, 1);

    if(!ExecuteHamB(Ham_AddPlayerItem, iPlayer, iEntity))
    {
        set_pev(iEntity, pev_flags, pev(iEntity, pev_flags) | FL_KILLME);
        return 0;
    }

    ExecuteHamB(Ham_Item_AttachToPlayer, iEntity, iPlayer);

    new iAmmoType = m_rgAmmo + get_pdata_int(iEntity, m_iPrimaryAmmoType, linux_diff_weapon);
    if(get_pdata_int(iPlayer, m_rgAmmo, linux_diff_player) < WEAPON_DEFAULT_AMMO)
        set_pdata_int(iPlayer, iAmmoType, WEAPON_DEFAULT_AMMO, linux_diff_player);

    emit_sound(iPlayer, CHAN_ITEM, "items/gunpickup2.wav", VOL_NORM, ATTN_NORM, 0, PITCH_NORM);
    return 1;
}

// [ Fakemeta ]
public FM_Hook_UpdateClientData_Post(iPlayer, SendWeapons, CD_Handle)
{
    if(!is_user_alive(iPlayer)) return;

    static iItem; iItem = get_pdata_cbase(iPlayer, m_pActiveItem, linux_diff_player);
    if(pev_valid(iItem) != PDATA_SAFE || !IsCustomItem(iItem)) return;

    set_cd(CD_Handle, CD_flNextAttack, get_gametime() + 0.001);
}

public FM_Hook_SetModel_Pre(iEntity)
{
    static i, szClassName[32], iItem;
    pev(iEntity, pev_classname, szClassName, charsmax(szClassName));

    if(!equal(szClassName, "weaponbox")) return FMRES_IGNORED;

    for(i = 0; i < 6; i++)
    {
        iItem = get_pdata_cbase(iEntity, m_rgpPlayerItems_CWeaponBox + i, linux_diff_weapon);

        if(iItem > 0 && IsCustomItem(iItem))
        {
            engfunc(EngFunc_SetModel, iEntity, WEAPON_MODEL_WORLD);
            set_pev(iEntity, pev_body, WEAPON_BODY);
          
            return FMRES_SUPERCEDE;
        }
    }

    return FMRES_IGNORED;
}

// [ HamSandwich ]
public CWeapon__Holster_Post(iItem)
{
    if(!IsCustomItem(iItem)) return;
    static iPlayer; iPlayer = get_pdata_cbase(iItem, m_pPlayer, linux_diff_weapon);
  
    set_pdata_float(iItem, m_flNextPrimaryAttack, 0.0, linux_diff_weapon);
    set_pdata_float(iItem, m_flNextSecondaryAttack, 0.0, linux_diff_weapon);
    set_pdata_float(iItem, m_flTimeWeaponIdle, 0.0, linux_diff_weapon);
    set_pdata_float(iPlayer, m_flNextAttack, 0.0, linux_diff_player);
}

public CWeapon__Deploy_Post(iItem)
{
    if(!IsCustomItem(iItem)) return;
  
    static iClip; iClip = get_pdata_int(iItem, m_iClip, linux_diff_weapon);
    static iPlayer; iPlayer = get_pdata_cbase(iItem, m_pPlayer, linux_diff_weapon);

    set_pev_string(iPlayer, pev_viewmodel2, g_iszAllocString_ModelView);
    set_pev_string(iPlayer, pev_weaponmodel2, g_iszAllocString_ModelPlayer);

    UTIL_SendWeaponAnim(iPlayer, iClip <= 0 ? WEAPON_ANIM_DRAW_EMPTY : (WEAPON_ANIM_DRAW3 + 1) - iClip);

    set_pdata_float(iPlayer, m_flNextAttack, WEAPON_ANIM_DRAW_TIME, linux_diff_player);
    set_pdata_float(iItem, m_flTimeWeaponIdle, WEAPON_ANIM_DRAW_TIME, linux_diff_weapon);
}

public CWeapon__PostFrame_Pre(iItem)
{
    if(!IsCustomItem(iItem)) return HAM_IGNORED;

    static iPlayer; iPlayer = get_pdata_cbase(iItem, m_pPlayer, linux_diff_weapon);
    if(get_pdata_int(iItem, m_fInReload, linux_diff_weapon) == 1)
    {
        static iClip; iClip = get_pdata_int(iItem, m_iClip, linux_diff_weapon);
        static iAmmoType; iAmmoType = m_rgAmmo + get_pdata_int(iItem, m_iPrimaryAmmoType, linux_diff_weapon);
        static iAmmo; iAmmo = get_pdata_int(iPlayer, iAmmoType, linux_diff_player);
        static j; j = min(WEAPON_MAX_CLIP - iClip, iAmmo);

        set_pdata_int(iItem, m_iClip, iClip + j, linux_diff_weapon);
        set_pdata_int(iPlayer, iAmmoType, iAmmo - j, linux_diff_player);
        set_pdata_int(iItem, m_fInReload, 0, linux_diff_weapon);
    }

    static iButton; iButton = pev(iPlayer, pev_button);
    if(iButton & IN_ATTACK2 && get_pdata_float(iItem, m_flNextSecondaryAttack, linux_diff_weapon) <= 0.0)
    {
        new iEntity = FM_NULLENT;
        while((iEntity = fm_find_ent_by_owner(iEntity, ENTITY_CLASSNAME, iPlayer)) > 0)
        {
            Create_ExplodeSpear(iEntity, pev(iEntity, pev_aiment));
        }

        set_pdata_float(iItem, m_flNextSecondaryAttack, 1.0, linux_diff_weapon);

        iButton &= ~IN_ATTACK2;
        set_pev(iPlayer, pev_button, iButton);
    }

    return HAM_IGNORED;
}

public CWeapon__AddToPlayer_Post(iItem, iPlayer)
{
    if(pev(iItem, pev_impulse) == WEAPON_SPECIAL_CODE) UTIL_WeaponList(iPlayer, true);
    else if(pev(iItem, pev_impulse) == 0) UTIL_WeaponList(iPlayer, false);
}

public CWeapon__Reload_Pre(iItem)
{
    if(!IsCustomItem(iItem)) return HAM_IGNORED;

    static iClip; iClip = get_pdata_int(iItem, m_iClip, linux_diff_weapon);
    if(iClip >= WEAPON_MAX_CLIP) return HAM_SUPERCEDE;

    static iPlayer; iPlayer = get_pdata_cbase(iItem, m_pPlayer, linux_diff_weapon);
    static iAmmoType; iAmmoType = m_rgAmmo + get_pdata_int(iItem, m_iPrimaryAmmoType, linux_diff_weapon);
    if(get_pdata_int(iPlayer, iAmmoType, linux_diff_player) <= 0) return HAM_SUPERCEDE;

    set_pdata_int(iItem, m_iClip, 0, linux_diff_weapon);
    ExecuteHam(Ham_Weapon_Reload, iItem);
    set_pdata_int(iItem, m_iClip, iClip, linux_diff_weapon);
    set_pdata_int(iItem, m_fInReload, 1, linux_diff_weapon);

    UTIL_SendWeaponAnim(iPlayer, WEAPON_ANIM_RELOAD);

    set_pdata_float(iItem, m_flNextPrimaryAttack, WEAPON_ANIM_RELOAD_TIME, linux_diff_weapon);
    set_pdata_float(iItem, m_flNextSecondaryAttack, WEAPON_ANIM_RELOAD_TIME, linux_diff_weapon);
    set_pdata_float(iItem, m_flTimeWeaponIdle, WEAPON_ANIM_RELOAD_TIME, linux_diff_weapon);
    set_pdata_float(iPlayer, m_flNextAttack, WEAPON_ANIM_RELOAD_TIME, linux_diff_player);

    return HAM_SUPERCEDE;
}

public CWeapon__WeaponIdle_Pre(iItem)
{
    if(!IsCustomItem(iItem) || get_pdata_float(iItem, m_flTimeWeaponIdle, linux_diff_weapon) > 0.0) return HAM_IGNORED;
    static iClip; iClip = get_pdata_int(iItem, m_iClip, linux_diff_weapon);
    static iPlayer; iPlayer = get_pdata_cbase(iItem, m_pPlayer, linux_diff_weapon);

    UTIL_SendWeaponAnim(iPlayer, iClip <= 0 ? WEAPON_ANIM_IDLE_EMPTY : (WEAPON_ANIM_IDLE3 + 1) - iClip);
    set_pdata_float(iItem, m_flTimeWeaponIdle, WEAPON_ANIM_IDLE_TIME, linux_diff_weapon);

    return HAM_SUPERCEDE;
}

public CWeapon__PrimaryAttack_Pre(iItem)
{
    if(!IsCustomItem(iItem)) return HAM_IGNORED;

    static iClip; iClip = get_pdata_int(iItem, m_iClip, linux_diff_weapon);
    static iPlayer; iPlayer = get_pdata_cbase(iItem, m_pPlayer, linux_diff_weapon);
    if(iClip == 0)
    {
        UTIL_SendWeaponAnim(iPlayer, WEAPON_ANIM_SHOOT_EMPTY);
        emit_sound(iPlayer, CHAN_WEAPON, WEAPON_SOUND_EMPTY, VOL_NORM, ATTN_NORM, 0, PITCH_NORM);

        set_pdata_float(iItem, m_flNextPrimaryAttack, WEAPON_ANIM_SHOOT_TIME, linux_diff_weapon);
        set_pdata_float(iItem, m_flTimeWeaponIdle, WEAPON_ANIM_SHOOT_TIME, linux_diff_weapon);

        return HAM_SUPERCEDE;
    }

    Create_Spear(iPlayer);

    UTIL_SendWeaponAnim(iPlayer, (WEAPON_ANIM_SHOOT3 + 1) - iClip);
    emit_sound(iPlayer, CHAN_WEAPON, WEAPON_SOUND_FIRE, VOL_NORM, ATTN_NORM, 0, PITCH_NORM);

    set_pdata_int(iItem, m_iClip, iClip - 1, linux_diff_weapon);

    set_pdata_float(iItem, m_flNextPrimaryAttack, WEAPON_RATE, linux_diff_weapon);
    set_pdata_float(iItem, m_flTimeWeaponIdle, WEAPON_ANIM_SHOOT_TIME, linux_diff_weapon);

    return HAM_SUPERCEDE;
}

public CEntity__Think_Pre(iEntity)
{
    if(pev_valid(iEntity) != PDATA_SAFE) return HAM_IGNORED;
    if(pev(iEntity, pev_classname) == g_iszAllocString_SpearClass)
    {
        Create_ExplodeSpear(iEntity, pev(iEntity, pev_aiment));
    }

    return HAM_IGNORED;
}

public CEntity__Touch_Pre(iEntity, iTouch)
{
    if(pev_valid(iEntity) != PDATA_SAFE) return HAM_IGNORED;
    if(pev(iEntity, pev_classname) == g_iszAllocString_SpearClass)
    {
        new iOwner = pev(iEntity, pev_owner);
        new Float: vecOrigin[3]; pev(iEntity, pev_origin, vecOrigin);
        new Float: flGameTime = get_gametime();

        if(engfunc(EngFunc_PointContents, vecOrigin) == CONTENTS_SKY)
        {
            set_pev(iEntity, pev_flags, FL_KILLME);
            return HAM_IGNORED;
        }

        if(iTouch == iOwner) return HAM_SUPERCEDE;

        // Aiment + Velocity
        if(is_user_connected(iTouch))
        {
            if(zp_get_user_zombie(iTouch))
            {
                new Float: vecVVelocity[3]; pev(iEntity, pev_vuser1, vecVVelocity);
                set_pev(iTouch, pev_velocity, vecVVelocity);
            }
          
            set_pev(iEntity, pev_aiment, iTouch);
            set_pev(iEntity, pev_movetype, MOVETYPE_FOLLOW);
        }
        else
        {
            set_pev(iEntity, pev_movetype, MOVETYPE_NONE);
        }

        set_pev(iEntity, pev_solid, SOLID_NOT);
        set_pev(iEntity, pev_velocity, Float: {0.0, 0.0, 0.0});
        set_pev(iEntity, pev_nextthink, flGameTime + 1.2);

        // Damage
        if(iTouch)
        {
            if(pev(iTouch, pev_takedamage) == DAMAGE_NO)
                return HAM_IGNORED;

            if(is_user_alive(iTouch))
            {
                if(iTouch == iOwner || zp_get_user_zombie(iOwner) || !zp_get_user_zombie(iTouch))
                    return HAM_IGNORED;
            }
            else if(pev(iTouch, pev_solid) == SOLID_BSP)
            {
                if(pev(iTouch, pev_spawnflags) & SF_BREAK_TRIGGER_ONLY)
                    return HAM_IGNORED;
            }

            new Float: flDamage = ENTITY_DAMAGE;

            if(is_user_connected(iTouch) && zp_get_user_zombie(iTouch))
            {
                new Float: vecVelocity[3]; pev(iEntity, pev_velocity, vecVelocity);
      
                vecVelocity[0] += vecOrigin[0];
                vecVelocity[1] += vecOrigin[1];
                vecVelocity[2] += vecOrigin[2];

                new iTrace = create_tr2();
                engfunc(EngFunc_TraceLine, vecOrigin, vecVelocity, DONT_IGNORE_MONSTERS, iEntity, iTrace);

                new iHitGroup = get_tr2(iTrace, TR_iHitgroup);
                set_pdata_int(iTouch, m_LastHitGroup, iHitGroup, linux_diff_player);

                switch(iHitGroup)
                {
                    case HIT_HEAD:                    flDamage *= 3.0;
                    case HIT_LEFTARM, HIT_RIGHTARM:    flDamage *= 0.75;
                    case HIT_LEFTLEG, HIT_RIGHTLEG:    flDamage *= 0.75;
                    case HIT_STOMACH:                flDamage *= 1.5;
                }

                new Float: vecEndPos[3]; get_tr2(iTrace, TR_vecEndPos, vecEndPos);
                UTIL_BloodDrips(vecEndPos, ExecuteHamB(Ham_BloodColor, iTouch), floatround(flDamage));

                free_tr2(iTrace);
            }

            ExecuteHamB(Ham_TakeDamage, iTouch, iOwner, iOwner, flDamage, DMG_BULLET|DMG_NEVERGIB);
        }
    }

    return HAM_IGNORED;
}

// [ Other ]
public Create_Spear(iPlayer)
{
    new iEntity = engfunc(EngFunc_CreateNamedEntity, g_iszAllocString_InfoTarget);
    if(!iEntity) return 0;

    new Float: flGameTime = get_gametime();
    new Float: vecOrigin[3]; pev(iPlayer, pev_origin, vecOrigin);
    new Float: vecAngles[3]; pev(iPlayer, pev_v_angle, vecAngles);
    new Float: vecVelocity[3]; angle_vector(vecAngles, ANGLEVECTOR_FORWARD, vecVelocity);
    new Float: vecViewOfs[3]; pev(iPlayer, pev_view_ofs, vecViewOfs);

    vecOrigin[0] += vecViewOfs[0] + vecVelocity[0] * 20.0;
    vecOrigin[1] += vecViewOfs[1] + vecVelocity[1] * 20.0;
    vecOrigin[2] += vecViewOfs[2] + vecVelocity[2] * 20.0;

    vecVelocity[0] *= ENTITY_SPEED;
    vecVelocity[1] *= ENTITY_SPEED;
    vecVelocity[2] *= ENTITY_SPEED;

    new Float: vecVVelocity[3]; // Victim velocity
    velocity_by_aim(iPlayer, floatround(ENTITY_KNOCKBACK), vecVVelocity);

    engfunc(EngFunc_SetModel, iEntity, ENTITY_MODEL);
    engfunc(EngFunc_SetOrigin, iEntity, vecOrigin);

    set_pev_string(iEntity, pev_classname, g_iszAllocString_SpearClass);
    set_pev(iEntity, pev_solid, SOLID_TRIGGER);
    set_pev(iEntity, pev_movetype, MOVETYPE_FLY);
    set_pev(iEntity, pev_owner, iPlayer);
    set_pev(iEntity, pev_velocity, vecVelocity);
    engfunc(EngFunc_VecToAngles, vecVelocity, vecAngles);
    set_pev(iEntity, pev_angles, vecAngles);
    set_pev(iEntity, pev_nextthink, flGameTime + 2.0);
    set_pev(iEntity, pev_vuser1, vecVVelocity);

    // https://github.com/baso88/SC_AngelScript/wiki/TE_BEAMFOLLOW
    message_begin(MSG_BROADCAST, SVC_TEMPENTITY);
    write_byte(TE_BEAMFOLLOW); // TE
    write_short(iEntity); // Target
    write_short(g_iszModelIndex_LaserBeam); // Model Index
    write_byte(2); // Life
    write_byte(1); // Width
    write_byte(210); // Red
    write_byte(210); // Green
    write_byte(210); // Blue
    write_byte(150); // Alpha
    message_end(); 

    return iEntity;
}

public Create_ExplodeSpear(iEntity, iAimEnt)
{
    new iOwner = pev(iEntity, pev_owner);
    new Float: vecOrigin[3]; pev(iAimEnt ? iAimEnt : iEntity, pev_origin, vecOrigin);

    new iVictim = FM_NULLENT;

    while((iVictim = engfunc(EngFunc_FindEntityInSphere, iVictim, vecOrigin, ENTITY_RADIUS_EXP)) > 0)
    {
        if(pev_valid(iVictim) != PDATA_SAFE) continue;
        if(pev(iVictim, pev_takedamage) == DAMAGE_NO)
            continue;

        if(is_user_alive(iVictim))
        {
            if(!is_wall_between_points(iOwner, iVictim))
                continue;

            if(iVictim == iOwner || zp_get_user_zombie(iVictim))
            {
                static Float: vecVVelocity[3]; pev(iVictim, pev_velocity, vecVVelocity);
                vecVVelocity[2] += ENTITY_KNOCK_EXP;
                set_pev(iVictim, pev_velocity, vecVVelocity);
            }

            if(iVictim == iOwner || !zp_get_user_zombie(iVictim))
                continue;
        }
        else if(pev(iVictim, pev_solid) == SOLID_BSP)
        {
            if(pev(iVictim, pev_spawnflags) & SF_BREAK_TRIGGER_ONLY)
                continue;
        }

        if(is_user_connected(iVictim))
            set_pdata_int(iVictim, m_LastHitGroup, HIT_GENERIC, linux_diff_player);

        ExecuteHamB(Ham_TakeDamage, iVictim, iOwner, iOwner, ENTITY_DAMAGE_EXP, DMG_GRENADE);
    }

    // https://github.com/baso88/SC_AngelScript/wiki/TE_EXPLOSION
    engfunc(EngFunc_MessageBegin, MSG_PAS, SVC_TEMPENTITY, vecOrigin, 0);
    write_byte(TE_EXPLOSION); // TE
    engfunc(EngFunc_WriteCoord, vecOrigin[0]); // Position X
    engfunc(EngFunc_WriteCoord, vecOrigin[1]); // Position Y
    engfunc(EngFunc_WriteCoord, vecOrigin[2] + 50.0); // Position Z
    write_short(g_iszModelIndex_Explosion); // Model Index
    write_byte(14); // Scale
    write_byte(45); // Framerate
    write_byte(0); // Flags
    message_end();

    // https://github.com/baso88/SC_AngelScript/wiki/TE_BREAKMODEL
    message_begin(MSG_BROADCAST, SVC_TEMPENTITY);
    write_byte(TE_BREAKMODEL); // TE
    engfunc(EngFunc_WriteCoord, vecOrigin[0]); // Position X
    engfunc(EngFunc_WriteCoord, vecOrigin[1]); // Position Y
    engfunc(EngFunc_WriteCoord, vecOrigin[2] + 20.0); // Position Z
    engfunc(EngFunc_WriteCoord, 150); // Size X
    engfunc(EngFunc_WriteCoord, 150); // Size Y
    engfunc(EngFunc_WriteCoord, 150); // Size Z
    engfunc(EngFunc_WriteCoord, random_num(-50, 50)); // Velocity X
    engfunc(EngFunc_WriteCoord, random_num(-50, 50)); // Velocity Y
    engfunc(EngFunc_WriteCoord, random_num(-50, 50)); // Velocity Z
    write_byte(30); // Noise
    write_short(g_iszModelIndex_BreakSpear); // Model Index
    write_byte(random_num(15, 20)); // Count
    write_byte(20); // Life
    write_byte(16); // Flags
    message_end();

    set_pev(iEntity, pev_flags, FL_KILLME);
}

// [ Stocks ]
stock is_wall_between_points(iPlayer, iEntity)
{
    // vector
    #define Vector_Equal(%0,%1) ((%1[0] == %0[0]) && (%1[1] == %0[1]) && (%1[2] == %0[2]))

    if(!is_user_alive(iEntity))
        return 0;

    new iTrace = create_tr2();
    new Float: flStart[3], Float: flEnd[3], Float: flEndPos[3];

    pev(iPlayer, pev_origin, flStart);
    pev(iEntity, pev_origin, flEnd);

    engfunc(EngFunc_TraceLine, flStart, flEnd, IGNORE_MONSTERS, iPlayer, iTrace);
    get_tr2(iTrace, TR_vecEndPos, flEndPos);

    free_tr2(iTrace);

    return Vector_Equal(flEnd, flEndPos);
}

stock UTIL_SendWeaponAnim(iPlayer, iAnim)
{
    set_pev(iPlayer, pev_weaponanim, iAnim);

    message_begin(MSG_ONE, SVC_WEAPONANIM, _, iPlayer);
    write_byte(iAnim);
    write_byte(0);
    message_end();
}

stock UTIL_DropWeapon(iPlayer, iSlot)
{
    static iEntity, iNext, szWeaponName[32];
    iEntity = get_pdata_cbase(iPlayer, m_rpgPlayerItems + iSlot, linux_diff_player);

    if(iEntity > 0)
    {
        do
        {
            iNext = get_pdata_cbase(iEntity, m_pNext, linux_diff_weapon);

            if(get_weaponname(get_pdata_int(iEntity, m_iId, linux_diff_weapon), szWeaponName, charsmax(szWeaponName)))
                engclient_cmd(iPlayer, "drop", szWeaponName);
        }
      
        while((iEntity = iNext) > 0);
    }
}

stock UTIL_PrecacheSoundsFromModel(const szModelPath[])
{
    new iFile;
  
    if((iFile = fopen(szModelPath, "rt")))
    {
        new szSoundPath[64];
      
        new iNumSeq, iSeqIndex;
        new iEvent, iNumEvents, iEventIndex;
      
        fseek(iFile, 164, SEEK_SET);
        fread(iFile, iNumSeq, BLOCK_INT);
        fread(iFile, iSeqIndex, BLOCK_INT);
      
        for(new k, i = 0; i < iNumSeq; i++)
        {
            fseek(iFile, iSeqIndex + 48 + 176 * i, SEEK_SET);
            fread(iFile, iNumEvents, BLOCK_INT);
            fread(iFile, iEventIndex, BLOCK_INT);
            fseek(iFile, iEventIndex + 176 * i, SEEK_SET);
          
            for(k = 0; k < iNumEvents; k++)
            {
                fseek(iFile, iEventIndex + 4 + 76 * k, SEEK_SET);
                fread(iFile, iEvent, BLOCK_INT);
                fseek(iFile, 4, SEEK_CUR);
              
                if(iEvent != 5004)
                    continue;
              
                fread_blocks(iFile, szSoundPath, 64, BLOCK_CHAR);
              
                if(strlen(szSoundPath))
                {
                    strtolower(szSoundPath);
                    engfunc(EngFunc_PrecacheSound, szSoundPath);
                }
            }
        }
    }
  
    fclose(iFile);
}

stock UTIL_PrecacheSpritesFromTxt(const szWeaponList[])
{
    new szTxtDir[64], szSprDir[64];
    new szFileData[128], szSprName[48], temp[1];

    format(szTxtDir, charsmax(szTxtDir), "sprites/%s.txt", szWeaponList);
    engfunc(EngFunc_PrecacheGeneric, szTxtDir);

    new iFile = fopen(szTxtDir, "rb");
    while(iFile && !feof(iFile))
    {
        fgets(iFile, szFileData, charsmax(szFileData));
        trim(szFileData);

        if(!strlen(szFileData))
            continue;

        new pos = containi(szFileData, "640"); 
          
        if(pos == -1)
            continue;
          
        format(szFileData, charsmax(szFileData), "%s", szFileData[pos+3]);     
        trim(szFileData);

        strtok(szFileData, szSprName, charsmax(szSprName), temp, charsmax(temp), ' ', 1);
        trim(szSprName);
      
        format(szSprDir, charsmax(szSprDir), "sprites/%s.spr", szSprName);
        engfunc(EngFunc_PrecacheGeneric, szSprDir);
    }

    if(iFile) fclose(iFile);
}

public UTIL_BloodDrips(Float: vecOrigin[3], iColor, iAmount)
{
    if(iAmount > 255) iAmount = 255;
  
    // https://github.com/baso88/SC_AngelScript/wiki/TE_BLOODSPRITE
    engfunc(EngFunc_MessageBegin, MSG_PVS, SVC_TEMPENTITY, vecOrigin, 0);
    write_byte(TE_BLOODSPRITE); // TE
    engfunc(EngFunc_WriteCoord, vecOrigin[0]); // Position X
    engfunc(EngFunc_WriteCoord, vecOrigin[1]); // Position Y
    engfunc(EngFunc_WriteCoord, vecOrigin[2]); // Position Z
    write_short(g_iszModelIndex_BloodSpray); // Model Index (1)
    write_short(g_iszModelIndex_BloodDrop); // Model Index (2)
    write_byte(iColor); // Color
    write_byte(min(max(3,iAmount/10),16)); // Scale
    message_end();
}

stock UTIL_WeaponList(iPlayer, bool: bEnabled)
{
    message_begin(MSG_ONE, g_iMsgID_Weaponlist, _, iPlayer);
    write_string(bEnabled ? WEAPON_WEAPONLIST : WEAPON_REFERENCE);
    write_byte(iWeaponList[0]);
    write_byte(bEnabled ? WEAPON_DEFAULT_AMMO : iWeaponList[1]);
    write_byte(iWeaponList[2]);
    write_byte(iWeaponList[3]);
    write_byte(iWeaponList[4]);
    write_byte(iWeaponList[5]);
    write_byte(iWeaponList[6]);
    write_byte(iWeaponList[7]);
    message_end();
}
 
Сообщения
2,288
Реакции
1,739
Помог
31 раз(а)
Krikkk,
В данном разделе размещаются темы, в которых требуется помощь с доработкой или объяснением материала.
В теме должны быть опубликованы попытки (diff кода или последовательность действий) самостоятельного поиска решения.
Если у вас нет наработок и попыток самому вникнуть в проблему, тогда вам в раздел "Покупка"
 
Статус
В этой теме нельзя размещать новые ответы.

Пользователи, просматривающие эту тему

Сейчас на форуме нет ни одного пользователя.
Сверху Снизу