Yes. There are a couple of ways to do this.
1. If so then it will be pretty easy to do. It would mean making a plugin that uses the features of the plugin above to do most of the work.
2. If not then you'd have to do a make a plugin that does a bit more work to give weapons to players. An example of this is 'Give Bots Weapons' or 'Give Bots More Weapons'.
One issue: Using a weapon not designed for a specific class (such as the Thermal Thruster for scout) will not properly display weapon animations will look weird.
Here is an example plugin that I made for you. It forces specific weapons for each class:
PHP Code:
#include <sourcemod>
#include <tf2_stocks>
#pragma semicolon 1
#pragma newdecls required
#define PLUGIN_VERSION "1.0"
bool g_bMedieval;
Handle g_hEquipWearable;
public Plugin myinfo =
{
name = "Force Weapons by Class",
author = "PC Gamer, with code by luki1412",
description = "Makes players use specific weapons for each class",
version = PLUGIN_VERSION,
url = "https://forums.alliedmods.net"
}
public void OnPluginStart()
{
HookEvent("post_inventory_application", player_inv);
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_CBaseEntity, SDKPass_Pointer);
g_hEquipWearable = EndPrepSDKCall();
if (!g_hEquipWearable)
SetFailState("Failed to create call: CBasePlayer::EquipWearable");
delete hTF2;
}
public void OnMapStart()
{
if (GameRules_GetProp("m_bPlayingMedieval"))
{
g_bMedieval = true;
}
}
public void player_inv(Handle event, const char[] name, bool dontBroadcast)
{
int userd = GetEventInt(event, "userid");
int client = GetClientOfUserId(userd);
if (IsClientInGame(client))
{
CreateTimer(1.0, Timer_GiveWeapons, userd);
}
}
public Action Timer_GiveWeapons(Handle timer, any data)
{
int client = GetClientOfUserId(data);
TFClassType class = TF2_GetPlayerClass(client);
switch (class)
{
case TFClass_Scout:
{
if (!g_bMedieval) //Only give primary and secondary weapons if map is not medieval mode
{
TF2_RemoveWeaponSlot(client, 0); //first we remove existing weapon
CreateWeapon(client, "tf_weapon_scattergun", 15106, 6); //Blue Mew
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_pistol", 30666, 6); //CAPPER
}
TF2_RemoveWeaponSlot(client, 2); //always give melee weapon
CreateWeapon(client, "tf_weapon_bat_fish", 999, 6); //Festive Holy Mackerel
}
case TFClass_Soldier:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_rocketlauncher", 228, 6); //Black Box
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_wearable", 133, 6); //Gunboats
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_shovel", 416, 6); //Market Gardener
}
case TFClass_Pyro:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_rocketlauncher_fireball", 1178, 6); //Dragon's Fury
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_shotgun_pyro", 15047, 6); //Lightning Rod
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_slap", 1181, 6); //Hot Hand
}
case TFClass_DemoMan:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_grenadelauncher", 15142, 6); //Warhawk
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_pipebomblauncher", 15048, 6); //Pink Elephant
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_katana", 357, 6); //Half-Zatoichi
}
case TFClass_Heavy:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_minigun", 15099, 6); //Mr Cuddles
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_shotgun_hwg", 15152, 6); //Red Bear
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_fists", 587, 6); //Apoco-Fists
}
case TFClass_Engineer:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_shotgun_building_rescue", 997, 6); //Rescue Ranger
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_pistol", 15013, 6); //Red Rock Roscoe
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_wrench", 15156, 6); //Airwolf
}
case TFClass_Medic:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_crossbow", 305, 6); //Crusaders Crossbow
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_medigun", 411, 6); //Quick Fix
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_bonesaw", 413, 6); //Solemn Vow
}
case TFClass_Sniper:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_sniperrifle", 230, 6); //Sydney Sleeper
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_jar", 58, 6); //Jarate
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_club", 232, 6); //Bushwacka
}
case TFClass_Spy:
{
if (!g_bMedieval)
{
TF2_RemoveWeaponSlot(client, 0);
CreateWeapon(client, "tf_weapon_revolver", 15064, 6); //Macabre Web
TF2_RemoveWeaponSlot(client, 1);
CreateWeapon(client, "tf_weapon_sapper", 933, 6); //Ap-Sap
}
TF2_RemoveWeaponSlot(client, 2);
CreateWeapon(client, "tf_weapon_knife", 727, 6); //Black Rose
}
}
}
bool CreateWeapon(int client, char[] classname, int itemindex, int quality, int level = 0)
{
int weapon = CreateEntityByName(classname);
if (!IsValidEntity(weapon))
{
return false;
}
char entclass[64];
GetEntityNetClass(weapon, entclass, sizeof(entclass));
SetEntProp(weapon, Prop_Send, "m_iItemDefinitionIndex", itemindex);
SetEntProp(weapon, Prop_Send, "m_bInitialized", 1);
SetEntData(weapon, FindSendPropInfo(entclass, "m_iEntityQuality"), quality);
if (level)
{
SetEntProp(weapon, Prop_Send, "m_iEntityLevel", level);
}
else
{
SetEntProp(weapon, Prop_Send, "m_iEntityLevel", GetRandomInt(1,99));
}
switch (itemindex)
{
case 25, 26:
{
DispatchSpawn(weapon);
EquipPlayerWeapon(client, weapon);
return true;
}
case 735, 736, 810, 933, 1080, 1102:
{
SetEntProp(weapon, Prop_Send, "m_iObjectType", 3);
SetEntProp(weapon, Prop_Data, "m_iSubType", 3);
SetEntProp(weapon, Prop_Send, "m_aBuildableObjectTypes", 0, _, 0);
SetEntProp(weapon, Prop_Send, "m_aBuildableObjectTypes", 0, _, 1);
SetEntProp(weapon, Prop_Send, "m_aBuildableObjectTypes", 0, _, 2);
SetEntProp(weapon, Prop_Send, "m_aBuildableObjectTypes", 1, _, 3);
}
case 998:
{
SetEntProp(weapon, Prop_Send, "m_nChargeResistType", GetRandomInt(0,2));
}
}
if (itemindex == 405 || itemindex == 608 || itemindex == 1101 || itemindex == 133 || itemindex == 444 || itemindex == 57 || itemindex == 231 || itemindex == 642 || itemindex == 131 || itemindex == 406 || itemindex == 1099 || itemindex == 1144)
{
DispatchSpawn(weapon);
SDKCall(g_hEquipWearable, client, weapon);
CreateTimer(0.1, TimerHealth, client);
}
else
{
DispatchSpawn(weapon);
EquipPlayerWeapon(client, weapon);
}
if (!g_bMedieval)
{
TF2_SwitchtoSlot(client, 0);
}
return true;
}
public Action TimerHealth(Handle timer, any client)
{
int hp = GetPlayerMaxHp(client);
if (hp > 0)
{
SetEntityHealth(client, hp);
}
}
int GetPlayerMaxHp(int client)
{
if (!IsClientConnected(client))
{
return -1;
}
int entity = GetPlayerResourceEntity();
if (entity == -1)
{
return -1;
}
return GetEntProp(entity, Prop_Send, "m_iMaxHealth", _, client);
}
stock void TF2_SwitchtoSlot(int client, int slot)
{
if (slot >= 0 && slot <= 5 && IsClientInGame(client) && IsPlayerAlive(client))
{
char wepclassname[64];
int wep = GetPlayerWeaponSlot(client, slot);
if (wep > MaxClients && IsValidEdict(wep) && GetEdictClassname(wep, wepclassname, sizeof(wepclassname)))
{
FakeClientCommandEx(client, "use %s", wepclassname);
SetEntPropEnt(client, Prop_Send, "m_hActiveWeapon", wep);
}
}
}