New convar changes and readme shit

This commit is contained in:
toasterpanic 2026-05-27 12:13:26 -04:00
parent 85eb62a495
commit 66f34f8aa1
3 changed files with 24 additions and 11 deletions

View file

@ -5,14 +5,15 @@ Adds better NPC integration for the Garry's Mod addon Z-City. While Z-City has a
- NPCs can now be alive while ragdolled, and can move around in that state.
- NPCs can collapse due to unconsciousness or pain.
- NPCs can get back up after being ragdolled.
- Various performance settings are included, with the biggest one being automatic corpse removal.
- Various configurableperformance settings are included, with the biggest one being automatic corpse removal.
This plugin is based off of Kazarei's Euphoria, which in turn is a fork of Fedhoria by Rama. Credits to them for making the cool thing.
## Known issues
- Kicking NPCs does not knock them down. This is not something I can easily fix -- I would have to override code in Z-City, which I would rather not do.
- Kicking NPCs does not knock them down. The same goes for many melee attacks. This is not something I can easily fix -- I would have to override code in Z-City, which I would rather not do.
- NPCs currently instantly get up, with no animation. I plan on remedying this in the future.
- Enemy NPCs will not target living downed NPCs. This is an issue I plan on fixing.
## Incompatibilities

View file

@ -20,8 +20,8 @@ local function PopulateRagdollSBXToolMenu(pnl)
end
local function PopulatePerformanceSBXToolMenu(pnl)
pnl:NumSlider("Activation range", "zcnpci_active_range", 0, 5000, 0)
pnl:ControlHelp("How close the ragdoll has to be to a player to be living when downed by damage. Enemies downed by other causes are unaffected.")
pnl:NumSlider("Activation range", "zcnpci_active_range", 0, 32768, 0)
pnl:ControlHelp("How close the ragdoll has to be to a player to live when downed by direct damage. Enemies downed by other causes are unaffected.")
pnl:CheckBox("Always activate on player kill", "zcnpci_always_active_on_player_kill")
pnl:ControlHelp("If on, all player-damaged ragdolls will be activated regardless of other factors.")
@ -42,14 +42,17 @@ local function PopulatePerformanceSBXToolMenu(pnl)
pnl:NumSlider("Max distance between player", "zcnpci_max_corpse_distance", -1, 32768, 2)
pnl:ControlHelp("If the corpse is further than this distance, it will be removed. Set to -1 to disable")
pnl:CheckBox("Never remove corpses near the player", "zcnpci_disable_corpse_removal_near_player")
pnl:ControlHelp("If on, corpses under the variable above in distance will never be cleared.")
pnl:NumSlider("Min distance between player", "zcnpci_min_corpse_distance", 0, 32768, 2)
pnl:ControlHelp("If the corpse is closer than this distance, it will never be cleared.")
pnl:CheckBox("Treat crippled NPCs as dead", "zcnpci_treat_crippled_as_dead")
pnl:ControlHelp("If on, corpses with amputations or both legs broken will be clearable.")
pnl:ControlHelp("If on, bodies with amputations or both legs broken will be clearable.")
pnl:CheckBox("Treat unconscious NPCs as dead", "zcnpci_treat_unconscious_as_dead")
pnl:ControlHelp("If on, bodies that are unconscious will be clearable.")
pnl:CheckBox("Treat near-death NPCs as dead", "zcnpci_treat_near_death_as_dead")
pnl:ControlHelp("If on, corpses near death (severe blood loss, comas, etc.) will be clearable.")
pnl:ControlHelp("If on, bodies near death (severe blood loss, comas, etc.) will be clearable.")
end
if engine.ActiveGamemode() == "sandbox" then

View file

@ -1,18 +1,20 @@
include("zcnpci/modules.lua")
local enabled = CreateConVar("zcnpci_enabled", 1, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local active_range = CreateConVar("zcnpci_active_range", 3000, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local active_range = CreateConVar("zcnpci_active_range", 32768, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local always_active_on_player_kill = CreateConVar("zcnpci_always_active_on_player_kill", 1, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local remove_corpses = CreateConVar("zcnpci_enable_corpse_removal", 0, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local max_corpses = CreateConVar("zcnpci_max_corpses", 8, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local max_corpse_time = CreateConVar("zcnpci_max_corpse_time", 120, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local min_corpse_distance = CreateConVar("zcnpci_min_corpse_distance", 500, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local max_corpse_distance = CreateConVar("zcnpci_max_corpse_distance", 2500, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local no_corpse_removal_near_player = CreateConVar("zcnpci_disable_corpse_removal_near_player", 0, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local treat_crippled_as_dead = CreateConVar("zcnpci_treat_crippled_as_dead", 1, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local treat_unconscious_as_dead = CreateConVar("zcnpci_treat_unconscious_as_dead", 1, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local treat_near_death_as_dead = CreateConVar("zcnpci_treat_near_death_as_dead", 1, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local debug_ragdoll_all = CreateConVar("zcnpci_debug_ragdoll_all", 0, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED, FCVAR_PROTECTED))
local debug_ragdoll_all = CreateConVar("zcnpci_debug_ragdoll_all", 0, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED))
local last_dmgpos = {}
local last_hitgroup = {}
@ -150,6 +152,8 @@ hook.Add("Think", "zcnpci", function()
(ent.organism.blood < 3000) or
(ent.organism.pulse < 10)
) then clearable = true end
if treat_unconscious_as_dead:GetBool() and (ent.organism.consciousness <= 0.3)
then clearable = true end
if !clearable then return end
@ -160,6 +164,7 @@ hook.Add("Think", "zcnpci", function()
-- Get nearest player for future checks
local nearby_player
local player_too_close
local players = player.GetAll()
for i, loop_player in pairs(players) do
@ -169,11 +174,15 @@ hook.Add("Think", "zcnpci", function()
if (distance <= max_corpse_distance:GetFloat()) or (max_corpse_distance:GetFloat() == -1) then
nearby_player = loop_player
end
if (distance <= min_corpse_distance:GetFloat()) then
player_too_close = loop_player
break
end
end
if nearby_player and IsValid(nearby_player) and no_corpse_removal_near_player:GetBool() then continue
if player_too_close and IsValid(player_too_close) then continue
elseif (max_corpse_distance:GetFloat() != -1) and !nearby_player then
ent:Remove()
continue