AddCSLuaFile() ENT.Type = "ai" ENT.Base = "base_ai" ENT.AutomaticFrameAdvance = true local debug_show_ragdoll_targets = CreateConVar("zcnpci_debug_show_ragdoll_targets", 0, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED)) local should_follow_head = CreateConVar("zcnpci_target_should_follow_head", 0, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED)) local stop_targeting_when_unconscious = CreateConVar("zcnpci_no_unconscious_targeting", 1, bit.bor(FCVAR_ARCHIVE, FCVAR_REPLICATED)) local vector_offset_to_shoot_at = Vector(0, 0, 8) local function UpdateRelationship(ent, me) if !IsValid(ent) or !ent:IsNPC() then return end if ent:Disposition(me.dummy_entity) == D_HT then ent:AddEntityRelationship(me, D_HT, -1) end end local function RemoveRelationship(ent, me) if !IsValid(ent) or !ent:IsNPC() then return end if ent:Disposition(me.dummy_entity) == D_HT then ent:AddEntityRelationship(me, D_NU, -1) ent:ClearEnemyMemory(me) if ent:GetEnemy() == me then ent:SetEnemy(nil) ent:ClearSchedule() end end end function ENT:Classify() return self.dummy_entity:Classify() end function ENT:Initialize() if SERVER then self:SetModel("models/maxofs2d/hover_basic.mdl") self:SetCollisionGroup(COLLISION_GROUP_NONE) self:SetHullType(HULL_TINY_CENTERED) self:SetNoDraw(!debug_show_ragdoll_targets:GetBool()) self.dummy_entity = ents.Create(self.ragdoll_to_follow.class_in_previous_life) self.last_stop_targeting = nil -- Have to use this collision group otherwise ragdoll will obstruct visibility of target self.ragdoll_to_follow:SetCollisionGroup(COLLISION_GROUP_DEBRIS) hook.Add("OnEntityCreated", "zcnpci-"..self:GetCreationID(), function(new_entity) if !IsValid(new_entity) or !new_entity:IsNPC() then return end if !self.last_stop_targeting then UpdateRelationship(new_entity, self) end end) end end function ENT:Think() if SERVER then local ragdoll = self.ragdoll_to_follow if !IsValid(ragdoll) then return end if should_follow_head:GetBool() then local head = ragdoll:GetPhysicsObjectNum(ragdoll:TranslateBoneToPhysBone(ragdoll:LookupBone("ValveBiped.Bip01_Head1"))) self:SetPos(head:GetPos() + vector_offset_to_shoot_at) else self:SetPos(ragdoll:GetPos()) end self:SetNoDraw(!debug_show_ragdoll_targets:GetBool()) if !ragdoll.organism then return true end local should_stop_targeting = !zcnpci_no_unconscious_targeting:GetBool() or ( (ragdoll.organism.consciousness <= 0.4) or (ragdoll.organism.critical) ) if true or (should_stop_targeting != self.last_stop_targeting) then self.last_stop_targeting = should_stop_targeting if should_stop_targeting then self:SetColor(Color(255, 0, 0)) for i,ent in ipairs(ents.GetAll()) do RemoveRelationship(ent, self) end else self:SetColor(Color(0, 255, 0)) for i,ent in ipairs(ents.GetAll()) do UpdateRelationship(ent, self) end end end self:NextThink(CurTime()) end return true end function ENT:OnRemove() if SERVER then for i,ent in ipairs(ents.GetAll()) do RemoveRelationship(ent, self) end self.dummy_entity:Remove() hook.Remove("OnEntityCreated", "zcnpci-"..self:GetCreationID()) end end