Skip to content

Instantly share code, notes, and snippets.

@YuRaNnNzZZ
Last active August 19, 2024 11:27
Show Gist options
  • Save YuRaNnNzZZ/8411ef8233714784c25b7dafd54104cb to your computer and use it in GitHub Desktop.
Save YuRaNnNzZZ/8411ef8233714784c25b7dafd54104cb to your computer and use it in GitHub Desktop.
TFA-VOX Template Collection

This is a collection of templates for TFA-VOX.

Before going through anything from here, make sure you have read through Lua basics guide for GMod here first!

List of contents:

For example custom gamemode integration, take a look at nZombies module implementation made by Zet0rz

List of community-made TFA-VOX extension modules (additional callouts/integrations)

If you have additional modules/integrations that could be useful for VOX pack makers, feel free to suggest them below!

-- TFA-VOX custom hooks reference
-- To be used with https://wiki.facepunch.com/gmod/hook.Add in your own code
-- All returns are optional, you can use hooks just to listen for events happening
-- Where state is listed as Shared, hook has to be added both on server and client to avoid any issues!
--------------
-- --
-- SPOTTING --
-- --
--------------
GM:TFAVOX_Spotting_PopulateNPCTypes()
-- Hook name: TFAVOX_Spotting_PopulateNPCTypes
-- Description: Allows to add custom spotting line types
-- State: Shared (only used serverside)
-- Arguments:
-- 1. table module - Spotting module
-- 2. table types - NPC types table (key is classname, value is key in "spot" VOX pack table)
GM:TFAVOX_SpotEntity()
-- Hook name: TFAVOX_SpotEntity
-- Description: Called when player attempts to spot an NPC/Player
-- State: Server
-- Arguments:
-- 1. Player ply - The player who attempts to spot
-- 2. Entity ent - The player/NPC who is getting spotted
-- Returns:
-- 1. boolean or Entity - Return false to prevent spotting, return an entity to override entity to be spotted (must be player/npc/nextbot)
--------------------
-- --
-- INITIALIZATION --
-- --
--------------------
GM:TFAVOX_InitializePlayer()
-- Hook name: TFAVOX_InitializePlayer
-- Description: Called when player does not a VOX table
-- State: Server
-- Arguments:
-- 1. Player ply
-- 2. boolean force
-- 3. boolean clean - VOX table was cleared after reload
GM:TFAVOX_InitializePlayerDone()
-- Hook name: TFAVOX_InitializePlayerDone
-- Description: Called after TFAVOX_InitializePlayer hook
-- State: Server
-- Arguments:
-- 1. Player ply
-- 2. boolean force
-- 3. boolean clean
GM:TFAVOX_InitializePlayerTimings()
-- Hook name: TFAVOX_InitializePlayerTimings
-- Description: Called every server tick or packs/modules reload before both TFAVOX_InitializePlayer and TFAVOX_InitializePlayerDone
-- State: Server
-- Arguments:
-- 1. Player ply
-- 2. boolean force
-- 3. boolean clean
if !MODULE then TFAVOX_Modules_Initialize() return end
MODULE.name = "Example Module" -- Module Label
MODULE.description = "Example implementation of a custom TFA-VOX module" -- Module Description
MODULE.author = "TFA" -- Module Author (optional)
MODULE.realm = "shared" -- Module Realm (client, server or shared)
MODULE.activedefault = true -- Module is active by default? (defaults to true)
MODULE.options = { -- Configurable module settings/options
["sampleopt"] = { -- Option Key/Name
["name"] = "Sample Option", -- Option Label
["description"] = "Sample option", -- Option Description
["type"] = "integer", -- Option type (int or integer)
["min"] = 0, -- Minimum value
["max"] = 100, -- Maximum value
["default"] = 100 -- Default value
},
["sampleoptfloat"] = {
["name"] = "Sample Float Option",
["description"] = "Sample option that's a float",
["type"] = "float", -- float or double
["min"] = 0,
["max"] = 100,
["default"] = 50.5
},
["sampleoptbool"] = {
["name"] = "Sample Boolean Option",
["description"] = "Sample option that's a boolean",
["type"] = "boolean", -- bool or boolean
["default"] = true
},
["sampleoptstr"] = {
["name"] = "Sample String Option",
["description"] = "Sample option that's a string",
["type"] = "string",
["default"] = "test"
},
["sampleoptcol"] = {
["name"] = "Sample Color Option",
["description"] = "Sample option that's a color",
["type"] = "color",
["default"] = Color(255, 0, 0, 255)
},
["sampleoptvec"] = {
["name"] = "Sample Vector Option",
["description"] = "Sample option that's a vector",
["type"] = "vector",
["default"] = Vector(0, 0, 0)
}
}
function MODULE:GetSampleOptBool() -- example module function to access module parameter
return self:GetOption("sampleoptbool", true) -- Arguments: module table, parameter key/name, fallback value (optional)
end
local lastprint = -999
-- Note: "self" in hooks is reserved for "MODULE" table of the module; for non-hooks usage you might want to localize "MODULE" variable
-- All module's hooks are disabled when module is not active
hook.Add("Think", "TestDH", function()
if not self:GetSampleOptBool() then return end -- calling module's function from above to access the boolean parameter
if CurTime() > lastprint + 5 then
lastprint = CurTime()
print("It works!")
end
end)
--------------------------------------
-- Custom module sounds integration --
--------------------------------------
-- First, you need to initialize the custom sounds from the pack:
hook.Add("TFAVOX_InitializePlayer", "TFAVOX_ExampleModuleInit", function(ply)
if IsValid(ply) then
local mdtbl = TFAVOX_GetPack(ply:GetModel())
if mdtbl then
ply.TFAVOX_Sounds = ply.TFAVOX_Sounds or {}
if mdtbl.examplemodule then
ply.TFAVOX_Sounds.examplemodule = ply.TFAVOX_Sounds.examplemodule or {}
ply.TFAVOX_Sounds.examplemodule.customsound = mdtbl.examplemodule.customsound
end
end
end
end)
-- In the VOX pack it would go like this:
--[[
local VOXPackTable = {
-- all base module sounds here
["examplemodule"] = {
["customsound"] = {
["sound"] = TFAVOX_GenerateSound(mdlprefix, "CustomModuleSound", {"snd1", "snd2", "snd3"})
}
}
}
]]--
-- Then, to play the sound, you need to call the sound playing function:
--[[
if SERVER and ply.TFAVOX_Sounds then
local sndtbl = ply.TFAVOX_Sounds.examplemodule
if sndtbl and sndtbl.customsound then
TFAVOX_PlayVoicePriority(ply, sndtbl.customsound, 0, false) -- Arguments: player entity, sound table, priority, interrupt
end
end
]]--
-- Click "Raw" then save the whole file (the last line is important!)
-- Then rename and put to lua/tfa_vox/packs in your addon folder
-- Path to your player model. Use forward slashes.
-- You can get the path for your current player model in Q -> Utilities -> TFA-VOX -> Debug/Development
local model = "models/player/player.mdl"
-- If you wish to use this pack with more than one playermodel, please look at the bottom of this file.
--[[ CONVENIENCE FUNCTIONS, DO NOT EDIT FROM THIS POINT UNTIL CLEAR ]]--
-- Automated prefix extraction from player name (for sound generation)
local tmptbl = string.Split(model, "/")
local mdlprefix = string.Replace(tmptbl[#tmptbl] or model, ".mdl", "")
-- OR! you can specify the prefix manually, like this:
-- local mdlprefix = "SHORT_MODEL_NAME" -- uncomment this line and comment two lines above
if model == "models/player/player.mdl" then return end
--[[ CLEAR ]]--
--[[
-- To give VOX sound paths, I recommend TFAVOX_GenerateSound.
-- TFAVOX_GenerateSound( mdlprefix, "sound_event_here", { "path/to/sound1.wav", "path/to/sound2.wav", "path/to/sound3.wav" }
-- You may have as many sounds as you want in the GenerateSound table ^^
-- Please have at least one.
-- Sound paths are relative to "sound" folder of your addon.
-- For example from above, the sounds should be placed there:
-- - garrysmod/addons/<YOUR ADDON>/sound/path/to/sound1.wav
-- - garrysmod/addons/<YOUR ADDON>/sound/path/to/sound2.wav
-- - garrysmod/addons/<YOUR ADDON>/sound/path/to/sound3.wav
-- and so on.
-- Allowed file types are: WAV, MP3 and OGG (without proper delay autocalculation.)
-- If you insist on doing things manually, ['sound'] can be a TABLE | { "sound1.wav", "sound2.wav", "sound3.wav" } | or a STRING | "snd" |
-- Manual sounds require soundscripts.
-- TFA VOX will now automatically calculate delays.
-- If you need to manually override, feed ['delay'] with a TABLE | {min,max} | or a NUMBER | 999 |
]]--
local VOXPackTable = {
['main'] = { -- subtable id
['heal'] = { -- event id
['delay'] = nil, -- delay (nil to autocalc, doesn't work with ogg)
['sound'] = TFAVOX_GenerateSound( mdlprefix, "heal", { "snd1", "snd2", "snd3" } ) -- sound path(s)
},
['healmax'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "healmax", { "snd1", "snd2", "snd3" } )
},
['crithit'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "crithit", { "snd1", "snd2", "snd3" } )
},
['crithealth'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "crithealth", { "snd1", "snd2", "snd3" } )
},
['death'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "death", { "snd1", "snd2", "snd3" } )
},
['spawn'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spawn", { "snd1", "snd2", "snd3" } )
},
['pickup'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "pickup", { "snd1", "snd2", "snd3" } )
},
['reload'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "reload", { "snd1", "snd2", "snd3" } )
},
['noammo'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "noammo", { "snd1", "snd2", "snd3" } )
},
['fall'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "fall", { "snd1", "snd2", "snd3" } )
},
['jump'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "jump", { "snd1", "snd2", "snd3" } )
},
['step'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "step", { "snd1", "snd2", "snd3" } )
}
},
['murder'] = {
['combine'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdcomb", { "snd1", "snd2", "snd3" } )
},
['cp'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdcp", { "snd1", "snd2", "snd3" } )
},
['zombie'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdzomb", { "snd1", "snd2", "snd3" } )
},
['headcrab'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdhc", { "snd1", "snd2", "snd3" } )
},
['antlion'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdant", { "snd1", "snd2", "snd3" } )
},
['barnacle'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdbarn", { "snd1", "snd2", "snd3" } )
},
['manhack'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdmh", { "snd1", "snd2", "snd3" } )
},
['scanner'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdsca", { "snd1", "snd2", "snd3" } )
},
['sniper'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdsni", { "snd1", "snd2", "snd3" } )
},
['turret'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdtur", { "snd1", "snd2", "snd3" } )
},
['ally'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdally", { "snd1", "snd2", "snd3" } )
},
-- ['npc_pigeon'] = { -- classname overrides category entry
-- ['delay'] = nil,
-- ['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdpigeon", { "snd1", "snd2", "snd3" } )
-- },
-- [HITGROUP_HEAD] = { -- last hit bodypart override; chanced (configurable); accepts enum https://wiki.facepunch.com/gmod/Enums/HITGROUP
-- ['delay'] = nil,
-- ['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdheadshot", { "snd1", "snd2", "snd3" } )
-- },
['generic'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "murdgener", { "snd1", "snd2", "snd3" } )
}
},
['spot'] = {
['combine'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotcomb", { "snd1", "snd2", "snd3" } )
},
['cp'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotcp", { "snd1", "snd2", "snd3" } )
},
['zombie'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotzom", { "snd1", "snd2", "snd3" } )
},
['headcrab'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spothc", { "snd1", "snd2", "snd3" } )
},
['antlion'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotant", { "snd1", "snd2", "snd3" } )
},
['barnacle'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotbarn", { "snd1", "snd2", "snd3" } )
},
['manhack'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotmh", { "snd1", "snd2", "snd3" } )
},
['scanner'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotsca", { "snd1", "snd2", "snd3" } )
},
['sniper'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotsni", { "snd1", "snd2", "snd3" } )
},
['turret'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spottur", { "snd1", "snd2", "snd3" } )
},
['ally'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotally", { "snd1", "snd2", "snd3" } )
},
-- ['npc_crow'] = { -- classname overrides category entry
-- ['delay'] = nil,
-- ['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotcrow", { "snd1", "snd2", "snd3" } )
-- },
['generic'] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "spotgener", { "snd1", "snd2", "snd3" } )
}
},
['taunt'] = {
[ACT_GMOD_GESTURE_AGREE] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_GESTURE_AGREE", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_GESTURE_BECON] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_GESTURE_BECON", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_GESTURE_BOW] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_GESTURE_BOW", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_GESTURE_DISAGREE] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_GESTURE_DISAGREE", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_TAUNT_SALUTE] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_TAUNT_SALUTE", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_GESTURE_WAVE] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_GESTURE_WAVE", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_TAUNT_PERSISTENCE] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_TAUNT_PERSISTENCE", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_TAUNT_MUSCLE] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_TAUNT_MUSCLE", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_TAUNT_LAUGH] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_TAUNT_LAUGH", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_GESTURE_POINT] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_GESTURE_POINT", { "snd1", "snd2", "snd3" } )
},
[ACT_GMOD_TAUNT_CHEER] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_GMOD_TAUNT_CHEER", { "snd1", "snd2", "snd3" } )
},
[ACT_SIGNAL_FORWARD] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_SIGNAL_FORWARD", { "snd1", "snd2", "snd3" } )
},
[ACT_SIGNAL_GROUP] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_SIGNAL_GROUP", { "snd1", "snd2", "snd3" } )
},
[ACT_SIGNAL_HALT] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "ACT_SIGNAL_HALT", { "snd1", "snd2", "snd3" } )
}
},
['damage'] = {
[HITGROUP_GENERIC] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_GENERIC", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_HEAD] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_HEAD", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_CHEST] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_CHEST", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_STOMACH] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_STOMACH", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_LEFTARM] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_LEFTARM", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_RIGHTARM] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_RIGHTARM", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_LEFTLEG] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_LEFTLEG", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_RIGHTLEG] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_RIGHTLEG", { "snd1", "snd2", "snd3" } )
},
[HITGROUP_GEAR] = {
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "HITGROUP_GEAR", { "snd1", "snd2", "snd3" } )
}
},
['callouts'] = {
['agree'] = { -- callout id/classname in these quotes
['name'] = "Agree",-- Callout friendly name ( what you see in the wheel )
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "Wheel_Agree", { "snd1", "snd2", "snd3" } ),
['order'] = nil, -- Sorting order index number (incremental, any entries with index will be put above others)
},
['disagree'] = { -- callout id/classname in these quotes
['name'] = "Disagree",-- Callout friendly name ( what you see in the wheel )
['delay'] = nil,
['sound'] = TFAVOX_GenerateSound( mdlprefix, "Wheel_Disagree", { "snd1", "snd2", "snd3" } ),
['order'] = nil,
}
},
['external'] = { --Completely optional, allows you to integrate with external mods
['bash'] = { -- Used by TFA Base
['sound'] = TFAVOX_GenerateSound( mdlprefix, "Bash", { "snd1", "snd2", "snd3" } )
}
}
}
TFAVOX_RegisterPack(model, VOXPackTable)
-- Manual registration for additional models with same pack:
-- TFAVOX_RegisterPack("models/player/player.mdl", VOXPackTable)
@H4RP00N770X
Copy link

I wonder if everyone will have to update their TFA VOX requirements from some of the older VOX addons. It's nice to know this is getting updated, but I just hope the older VOX addons can still be functional with this one.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment