FurryEskimo Posted February 25, 2021 Share Posted February 25, 2021 I think I know how to do this, but it's not working the way I expect it to. print("Entity Tracker: ", inst.components.entitytracker:GetEntity("leader")) print("Combat Target: ", inst.components.combat.target) print("Attacker: ", inst.components.combat.attacker) I've coded some dogs to follow the player as followers, and when they stop following the player they die. This was meant to keep the hounds from going feral once the player exits the game. To my surprise, these hounds 'stop following the player' if the leader punches the dogs. This has resulted in some of my testers punching and resummoning the dogs for infinite meat. I'm sort of fixed this by limiting the likelihood of respawning to 80% as well as another punishment, but I figured I'd just make the respawn rate super low if the leader was the attacker. Well, for some reason the hounds consistently register 'nil' as an attacker. Does anyone know why this might be? function Follower:StopFollowing() if self.inst:IsValid() then self.inst:PushEvent("loseloyalty", { leader = self.leader }) self:SetLeader(nil) end end I've been looking through the code to figure out exactly why the hounds stop following the player when punched, but it's a little weird. I figure they're likely rejecting the player as their leader before registering the player as an attacker, but there may be something else going on, since I think I told the hounds they can't attack the player. hound_ai.lua Link to comment https://forums.kleientertainment.com/forums/topic/127394-detecting-your-attacker/ Share on other sites More sharing options...
CarlZalph Posted February 25, 2021 Share Posted February 25, 2021 2 hours ago, FurryEskimo said: To my surprise, these hounds 'stop following the player' if the leader punches the dogs. I've been looking through the code to figure out exactly why the hounds stop following the player when punched, but it's a little weird. I figure they're likely rejecting the player as their leader before registering the player as an attacker It's because the combat component has EngageTarget which when the player is starting to punch is considered engagement, and it tries breaking the leader-follower relationship. Then there's a case in the follower component that also tries to clear the relationship. But there's a handy function that stops both cases in one call: hound.components.follower:KeepLeaderOnAttacked() 1 1 Link to comment https://forums.kleientertainment.com/forums/topic/127394-detecting-your-attacker/#findComment-1432557 Share on other sites More sharing options...
FurryEskimo Posted February 25, 2021 Author Share Posted February 25, 2021 (edited) @CarlZalph Wow, cool! I'll give that a try soon! Edit 1: It appears to be working! Edit 2: I actually did manage to figure out a general solution to this. I can now compare the name of the player against a hound's follower, and vise-versa. This made it so I can cause a penalty for killing wild hounds or another player's hounds, and a heavier penalty for killing your own, discouraging players from summoning and killing their pet hounds (which has been an issue in the beta, as players could farm hounds for food.) local function onkilled(inst, data) --Negative sanity penalty when you kill hounds. print("Hound killed!") --Test code. local victim = data.victim if victim and victim:HasTag("hound") and not victim:HasTag("companion") then print("Killed a wild hound.") --Test code. inst.components.sanity:DoDelta(victim.sanityreward or -TUNING.SANITY_SMALL) --Note: Tiny=5 Sanity, Small=10 Sanity, Med=15 Sanity, MED_LARGE=XXX Sanity, Large=33 Sanity, Huge=50 Sanity, Superhuge=XXX Sanity elseif victim and victim:HasTag("hound") and victim:HasTag("companion") then if inst.name == victim.components.follower.leader.name then print("Killed your own trained hound.") --Test code. inst.components.sanity:DoDelta(victim.sanityreward or -TUNING.SANITY_MED) --Note: Tiny=5 Sanity, Small=10 Sanity, Med=15 Sanity, MED_LARGE=XXX Sanity, Large=33 Sanity, Huge=50 Sanity, Superhuge=XXX Sanity else print("Killed someone else's trained hound.") --Test code. inst.components.sanity:DoDelta(victim.sanityreward or -TUNING.SANITY_SMALL) --Note: Tiny=5 Sanity, Small=10 Sanity, Med=15 Sanity, MED_LARGE=XXX Sanity, Large=33 Sanity, Huge=50 Sanity, Superhuge=XXX Sanity end print("Player's name: ", inst.name) --Test code. print("Victim's Leader: ", victim.components.follower.leader.name) end end I've reviewing this old hound AI code though and wow, it's a little weird. The hounds are generally well behaved, but they can get into fights with one another, and PvP with the hounds wasn't possible before now. I think I can tell them not to attack targets with the same leader as they have, but for some reason I can't remember what code prevents the hounds attacking players.. I was hoping to remove that code and replace it with new, updated code. if inst.components.combat then -- Prevent hounds from attacking other players local targetfn_orig = inst.components.combat.targetfn local targetfn_new = function(inst) local target = nil -- Choose target normally if targetfn_orig then target = targetfn_orig(inst) end -- Check if this hound has a hound tamer as a leader. if target ~= nil and inst.components.follower and inst.components.follower.leader and inst.components.follower.leader:HasTag("player") then -- Check if target should be kept Note: Hounds are mostly useless in PvP? if target:HasTag("player") or target:HasTag("companion") -- or target:HasTag("trainedhound") --Redundant? or target:HasTag("character") --Prevents hounds starting fights with pigs, bunnymen, and rock lobsters, but they will still attack trained hounds. or target:AddTag("largecreature") --Usually prevents hounds starting fights with larger enemies, like beefalo. --Note: Hounds attacking targets (like birds) very close to a beefalo often go on to attack the beefalo. -- or target:AddTag("epic") --Prevents hounds starting fights with giants, but these are also taged with 'largecreature' so this would be redundant. or target:HasTag("insect") --Prevents hounds starting fights with bees, mosquitos, and butterflies. This is mostly to prevent hounds resulting in endless loot when players stand next to flowers. or target:HasTag("hive") --Prevents hounds attacking beehives, spider dens. -- or target:HasTag("prey") -- or target:HasTag("structure") -- or target.name == inst.components.follower.leader.name --Test code. --Note: Walruses have the tag 'houndfriend', meaning they may be partially immune to these trained hounds. then print("Hound's Target: Not Valid") print("Target's Name: ", target.name) --Test code. print("Hound's Leader's Name: ", inst.components.follower.leader.name) target = nil else print("Hound's Target: Valid") print("Target's Name: ", target.name) --Test code. print("Hound's Leader's Name: ", inst.components.follower.leader.name) end end return target end inst.components.combat.targetfn = targetfn_new local ShareTarget_prev = inst.components.combat.ShareTarget function inst.components.combat:ShareTarget(target, ...) -- Share target normally if being led by someone other than hound tamer. if inst.components.follower and inst.components.follower.leader and not inst.components.follower.leader:HasTag("player") then return ShareTarget_prev(self, target, ...) end -- Prevents hound tamers from being shared as a target. if target:HasTag("houndtamer") then --Note: "inst.components.follower.leader.name == target.components.follower.leader.name" return end -- Prevents players and companions from being shared as a target. if target:HasTag("player") or target:HasTag("companion") then local houndtamer = GLOBAL.FindEntity(inst, 20, function(guy) return guy:HasTag("houndtamer") end) if houndtamer ~= nil then return end end return ShareTarget_prev(self, target, ...) end end My memory is hazy, but I thought I coded it to act normally with normally hounds, not to pick fights with players or big monsters, and not to gang up on players if a fight did start. hound_ai.lua Edited February 26, 2021 by FurryEskimo Link to comment https://forums.kleientertainment.com/forums/topic/127394-detecting-your-attacker/#findComment-1432558 Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now