Project Zomboid

Project Zomboid

Subpar Survivors
Sardes 17 aug, 2021 @ 11:33
NPC cant run issue
The only safe way to fix NPC run issue I have found is to recreate all original code from TIS. Here it is (copy and past to SuperSurvivor.lua):

function SuperSurvivor:NPCcalculateInjurySpeed(bodypart,b)
local scratchSpeedModifier = bodypart:getScratchSpeedModifier();
local cutSpeedModifier = bodypart:getCutSpeedModifier();
local burnSpeedModifier = bodypart:getBurnSpeedModifier();
local deepWoundSpeedModifier = bodypart:getDeepWoundSpeedModifier();
local n = 0.0;
if ((bodypart:getType() == "Foot_L" or bodypart:getType() == "Foot_R") and (bodypart:getBurnTime() > 5.0 or bodypart:getBiteTime() > 0.0 or bodypart:deepWounded() or bodypart:isSplint() or bodypart:getFractureTime() > 0.0 or bodypart:haveGlass())) then
n = 1.0f
if (bodypart:bandaged()) then
n = 0.7;
end
if (bodypart:getFractureTime() > 0.0) then
n = self:NPCcalcFractureInjurySpeed(bodypart);
end
end
if (bodypart:haveBullet()) then
return 1.0;
end
if (bodypart:getScratchTime() > 2.0 or bodypart:getCutTime() > 5.0 or bodypart:getBurnTime() > 0.0 or bodypart:getDeepWoundTime() > 0.0 or bodypart:isSplint() or bodypart:getFractureTime() > 0.0 or bodypart:getBiteTime() > 0.0) then
n = n + (bodypart:getScratchTime() / scratchSpeedModifier + bodypart:getCutTime() / cutSpeedModifier + bodypart:getBurnTime() / burnSpeedModifier + bodypart:getDeepWoundTime() / deepWoundSpeedModifier) + bodypart:getBiteTime() / 20.0;
if (bodypart:bandaged()) then
n = n / 2.0;
end
if (bodypart:getFractureTime() > 0.0) then
n = self:NPCcalcFractureInjurySpeed(bodypart);
end
end
if (b and bodypart:getPain() > 20.0) then
n = n + bodypart:getPain() / 10.0;
end
return n;
end

function SuperSurvivor:NPCgetFootInjurySpeedModifier()
local b = true;
local n = 0.0;
local n2 = 0.0;
for i = BodyPartType.UpperLeg_L:index(), (BodyPartType.MAX:index() - 1) do
local bodydamage = self.player:getBodyDamage()
local bodypart = bodydamage:getBodyPart(BodyPartType.FromIndex(i));
local calculateInjurySpeed = self:NPCcalculateInjurySpeed(bodypart, false);
if (b) then
n = n + calculateInjurySpeed;
b = false
else
n2 = n2 + calculateInjurySpeed;
b = true
end
end
if (n > n2) then
return -(n + n2);
else
return n + n2;
end
end

function SuperSurvivor:NPCgetrunSpeedModifier()
local NPCrunSpeedModifier = 1.0;
local items = self.player:getWornItems()
for i=0, items:size()-1 do
local item = items:getItemByIndex(i)
if item ~= nil and (item:getCategory() == "Clothing") then
NPCrunSpeedModifier = NPCrunSpeedModifier + (item:getRunSpeedModifier() - 1.0);
end
end
local shoeitem = items:getItem("Shoes");
if not (shoeitem) or (shoeitem:getCondition() == 0) then
NPCrunSpeedModifier = NPCrunSpeedModifier * 0.85;
end
return NPCrunSpeedModifier
end

function SuperSurvivor:NPCgetwalkSpeedModifier()
local NPCwalkSpeedModifier = 1.0;
local items = self.player:getWornItems()
local shoeitem = items:getItem("Shoes");
if not (shoeitem) or (shoeitem:getCondition() == 0) then
NPCwalkSpeedModifier = NPCwalkSpeedModifier * 0.85;
end
return NPCwalkSpeedModifier
end

function SuperSurvivor:NPCcalcRunSpeedModByBag(bag)
return (bag:getScriptItem().runSpeedModifier - 1.0) * (1.0 + bag:getContentsWeight() / bag:getEffectiveCapacity(self.player) / 2.0);
end

function SuperSurvivor:NPCgetfullSpeedMod()
local NPCfullSpeedMod
local NPCbagRunSpeedModifier = 0
if (self.player:getClothingItem_Back() ~= nil) and (instanceof(self.player:getClothingItem_Back(),"InventoryContainer")) then
NPCbagRunSpeedModifier = NPCbagRunSpeedModifier + self:NPCcalcRunSpeedModByBag(self.player:getClothingItem_Back():getItemContainer())
end
if (self.player:getSecondaryHandItem() ~= nil) and (instanceof(self.player:getSecondaryHandItem(),"InventoryContainer")) then
NPCbagRunSpeedModifier = NPCbagRunSpeedModifier + self:NPCcalcRunSpeedModByBag(self.player:getSecondaryHandItem():getItemContainer());
end
if (self.player:getPrimaryHandItem() ~= nil) and (instanceof(self.player:getPrimaryHandItem(),"InventoryContainer")) then
NPCbagRunSpeedModifier = NPCbagRunSpeedModifier + self:NPCcalcRunSpeedModByBag(self.player:getPrimaryHandItem():getItemContainer());
end
NPCfullSpeedMod = self:NPCgetrunSpeedModifier() + (NPCbagRunSpeedModifier - 1.0);
return NPCfullSpeedMod
end

function SuperSurvivor:NPCcalculateWalkSpeed()
local NPCfootInjurySpeedModifier = self:NPCgetFootInjurySpeedModifier();
self.player:setVariable("WalkInjury", NPCfootInjurySpeedModifier);
local NPCcalculateBaseSpeed = self.player:calculateBaseSpeed();
local wmax;
if self:getRunning() == true then
wmax = ((NPCcalculateBaseSpeed - 0.15) * self:NPCgetfullSpeedMod() + self.player:getPerkLevel(Perks.FromString("Sprinting")) / 20.0 - AbsoluteValue(NPCfootInjurySpeedModifier / 1.5));
else
wmax = NPCcalculateBaseSpeed * self:NPCgetwalkSpeedModifier();
end
if (self.player:getSlowFactor() > 0.0) then
wmax = wmax * 0.05;
end
local wmin = math.min(1.0, wmax);
local bodydamage = self.player:getBodyDamage()
if (bodydamage) then
local thermo = bodydamage:getThermoregulator()
end
if (thermo) then
wmin = wmin * thermo:getMovementModifier();
end
--local gametime = getGameTime()
if (self.player:isAiming()) then
self.player:setVariable("StrafeSpeed", math.max(math.min(0.9 + self.player:getPerkLevel(Perks.FromString("Nimble")) / 10.0, 1.5) * math.min(wmin * 2.5, 1.0), 0.6) * 0.8);
end
if (self.player:isInTreesNoBush()) then
local cs = self.player:getCurrentSquare()
if (cs) and cs:HasTree() then
local tree = cs:getTree();
end
if tree then
wmin = wmin * tree:getSlowFactor(self.player);
end
end
self.player:setVariable("WalkSpeed", wmin * 0.8);
end

And in update() function add self:NPCcalculateWalkSpeed() before dovision for example. You can also call this in other places. It need to be tested though, cos I have not tested it well, but it works for random single spawned NPC.
< >
Visar 1-15 av 15 kommentarer
Sardes 17 aug, 2021 @ 11:34 
Oh great, it deletes all spaces and tabs... Any way I can send it to you, if you are interested?
Senast ändrad av Sardes; 17 aug, 2021 @ 11:35
SlightlyMadman  [utvecklare] 17 aug, 2021 @ 17:38 
Oh wow, great work! Do you use git? If so, you can just submit a PR to my repo https://github.com/bsarsgard/Subpar-Survivors
Sardes 17 aug, 2021 @ 20:32 
not sure if did it right, never did it before. Check...
SlightlyMadman  [utvecklare] 18 aug, 2021 @ 7:21 
I see your fork, I'll make the PR.
Sardes 18 aug, 2021 @ 7:50 
Ok, good. BTW I have same fix for NPC damage, if you are interested.
SlightlyMadman  [utvecklare] 18 aug, 2021 @ 9:21 
Yes actually, I'm sure it's better than my quick hack!
Sardes 18 aug, 2021 @ 9:37 
Done, I guess, in SuperSurvivorUpdate
SlightlyMadman  [utvecklare] 18 aug, 2021 @ 11:43 
Thanks, got it! I'll get these in ASAP but I'm heading out of town tomorrow for the weekend.
SlightlyMadman  [utvecklare] 19 aug, 2021 @ 10:10 
These updates seem to work, but I'm getting a lot of glitches like survivors getting stuck after attacking. I'll need to debug a bit more before I can release.
Sardes 19 aug, 2021 @ 13:11 
That's strange, coz I tested it with many NPC spawned. The only problem I saw is problems with AI-manager and flee task, but I thought it was always like that.
Anyway, there is a bug actualy with damage logic, needs to add these strings at the begining

if weapon:getType() == "BareHands" then
return
end

Without it pushing with hands damages too.

I will try to look again too.
Senast ändrad av Sardes; 19 aug, 2021 @ 13:11
SlightlyMadman  [utvecklare] 19 aug, 2021 @ 14:27 
Yes, for some reason friendly NPCs are going directly into the FleeFromHere task, which also doesn't seem to be working properly.

Still testing more, but also just watched an NPC get swarmed by 5 melee-armed raiders for at least 10-20 hits. He fought them off and I inspected him, and he'd taken barely any damage. Damage from the PC to NPCs seems good.
SlightlyMadman  [utvecklare] 19 aug, 2021 @ 14:32 
BTW it's entirely possible this behavior all has nothing to do with your changes and I'm just noticing it for the first time because of my test setup. Actually it would explain some other bug reports I've seen if this has been around since the 41.51 update.
SlightlyMadman  [utvecklare] 22 aug, 2021 @ 18:24 
It looks like the fleeing issues are entirely an old bug, I've included these and update the mod. Thank you so much for this fix!
Datboi 10 sep, 2021 @ 21:01 
Ursprungligen skrivet av SlightlyMadman:
It looks like the fleeing issues are entirely an old bug, I've included these and update the mod. Thank you so much for this fix!

Does running work then? Right now it doesn't seem to work still
SlightlyMadman  [utvecklare] 13 sep, 2021 @ 6:11 
It's been working for me. Try setting an NPC to follow and running away from them. They should now jog to catch up.
< >
Visar 1-15 av 15 kommentarer
Per sida: 1530 50