View Single Post
PC Gamer
Veteran Member
Join Date: Mar 2014
Old 09-28-2021 , 23:33   Re: [TF2] Plugin to have BOTH grappling hook AND spell book
Reply With Quote #5

Quote:
Originally Posted by Isiah Scott View Post
Thank you so much for sharing.
You're welcome! Here's a slightly different version that doesn't require TF2Items.

PHP Code:
#pragma semicolon 1
#include <sourcemod>
#include <tf2_stocks>

#define PLUGIN_VERSION "1.1" 

#define MAGIC    "vo/halloween_merasmus/sf12_staff_magic13.mp3" 

public Plugin:myinfo =  

    
name "Spellbook"
    
author "PC Gamer"
    
description "Give Spellbook with Spells"
    
version PLUGIN_VERSION
    
url "www.sourcemod.com" 


Handle g_hWearableEquip;

public 
OnPluginStart() 

    
LoadTranslations("common.phrases"); 
    
RegAdminCmd("sm_spellbook"Command_nobookADMFLAG_SLAY"Give Spells"); 

    
GameData hTF2 = new GameData("sm-tf2.games"); // sourcemod's tf2 gamedata

    
if (!hTF2)
    
SetFailState("This plugin is designed for a TF2 dedicated server only.");

    
StartPrepSDKCall(SDKCall_Player);
    
PrepSDKCall_SetVirtual(hTF2.GetOffset("RemoveWearable") - 1);    // EquipWearable offset is always behind RemoveWearable, subtract its value by 1
    
PrepSDKCall_AddParameter(SDKType_CBaseEntitySDKPass_Pointer);
    
g_hWearableEquip EndPrepSDKCall();

    if (!
g_hWearableEquip)
    
SetFailState("Failed to create call: CBasePlayer::EquipWearable");

    
delete hTF2


public 
OnMapStart()
{
    
PrecacheSound(MAGICtrue); 
}

public 
Action:Command_nobook(clientargs

    
decl String:arg1[32]; 
    if (
args 1
    { 
        
arg1 "@me"
    } 
    else 
GetCmdArg(1arg1sizeof(arg1)); 
    new 
String:target_name[MAX_TARGET_LENGTH]; 
    new 
target_list[MAXPLAYERS], target_count
    new 
bool:tn_is_ml

    if ((
target_count ProcessTargetString
                    
arg1
                    
client
                    
target_list
                    
MAXPLAYERS
                    
COMMAND_FILTER_ALIVE|(args COMMAND_FILTER_NO_IMMUNITY 0), 
                    
target_name
                    
sizeof(target_name), 
                    
tn_is_ml)) <= 0
    { 
        
ReplyToTargetError(clienttarget_count); 
        return 
Plugin_Handled
    } 

    for (new 
0target_counti++) 
    { 
        
forceSpellbook(target_list[i]); 
        
SetSpell2(target_list[i], 010); 
        
EmitSoundToClient(target_list[i],MAGIC);          
        
PrintToChat(target_list[i], "You received 10 Fireball Spells.  Use 'H' key to cast.");        
    } 
    
    return 
Plugin_Handled



stock forceSpellbook(client)
{
    
TF2_RemoveWeaponSlot(client10);

    
CreateHat(client11321006); //Spellbook    
    
    
TF2_RegeneratePlayer(client);
}

SetSpell2(clientspelluses)
{
    new 
ent GetSpellBook(client);
    if(!
IsValidEntity(ent)) return;
    
SetEntProp(entProp_Send"m_iSelectedSpellIndex"spell);
    
SetEntProp(entProp_Send"m_iSpellCharges"uses);
}  

GetSpellBook(client)
{
    new 
entity = -1;
    while((
entity FindEntityByClassname(entity"tf_weapon_spellbook")) != INVALID_ENT_REFERENCE)
    {
        if(
GetEntPropEnt(entityProp_Send"m_hOwnerEntity") == client) return entity;
    }
    return -
1;
}

bool CreateHat(int clientint itemindexint levelint quality)
{
    
int hat CreateEntityByName("tf_wearable");
    
    if (!
IsValidEntity(hat))
    {
        return 
false;
    }
    
    
char entclass[64];
    
GetEntityNetClass(hatentclasssizeof(entclass));
    
SetEntData(hatFindSendPropInfo(entclass"m_iItemDefinitionIndex"), itemindex);
    
SetEntData(hatFindSendPropInfo(entclass"m_bInitialized"), 1);     
    
SetEntData(hatFindSendPropInfo(entclass"m_iEntityLevel"), level);
    
SetEntData(hatFindSendPropInfo(entclass"m_iEntityQuality"), quality);

    if (
level)
    {
        
SetEntData(hatFindSendPropInfo(entclass"m_iEntityLevel"), level);
    }
    else
    {
        
SetEntData(hatFindSendPropInfo(entclass"m_iEntityLevel"), GetRandomInt(1,100));
    }

    
DispatchSpawn(hat);
    
SDKCall(g_hWearableEquipclienthat);
    return 
true;

PC Gamer is offline