Devgirl_Neko Posted June 9, 2022 Share Posted June 9, 2022 I recently got back into modding for this game after a several year hiatus. I'm currently making a character mod and I want to implement a sanity system where killing a mob grants a non-stacking buff of slight sanity gain for 12 hours. If the character has gone 24 hours without killing they speak a line of dialogue and they lose sanity at a fixed rate. If the character has gone 48 hours without killing they speak a different line of dialogue and lose sanity at a greater rate indefinitely. Killing immediately resets the timer on this system to 0, at which point the sanity loss will start again after another 24 hours. Is there a way I can implement such a dynamic into my character mod? Link to comment Share on other sites More sharing options...
Devgirl_Neko Posted June 14, 2022 Author Share Posted June 14, 2022 bump Link to comment Share on other sites More sharing options...
Devgirl_Neko Posted June 21, 2022 Author Share Posted June 21, 2022 bump Link to comment Share on other sites More sharing options...
. . . Posted June 21, 2022 Share Posted June 21, 2022 (edited) I whipped up this code right now so IDK 100% if it will work or crash, but you can test it hopefully it work put all this code inside yourcharacter.lua inside the master_postinit Spoiler if inst.secs_since_killed == nil then inst.secs_since_killed = 0 end -- Add value if doesn't exist inst:DoPeriodicTask(1, Secs_Since_Killed) inst.components.sanity.custom_rate_fn = SanityFN inst:ListenForEvent("killed", Killed) inst:ListenForEvent("murdered", Killed) inst.OnSave = OnSave inst.OnLoad = OnLoad and put all these code inside yourcharacter.lua above the master_postinit Spoiler local KILL_DEBUFF1 = 480 -- 480 seconds = 8 minutes = full DST day local KILL_DEBUFF2 = 960 -- 960 seconds = 16 minutes = 2 DST day local function Killed(inst) inst.secs_since_killed = 0 -- Reset end local function Secs_Since_Killed(inst) inst.secs_since_killed = inst.secs_since_killed + 1 end local function SanityFN(inst) local delta = 0 if inst.secs_since_killed < KILL_DEBUFF1 then delta = TUNING.SANITYAURA_TINY * 1 -- You can replace 1 with a higher value to make it stronger or a smaller value to make it weaker elseif inst.secs_since_killed >= KILL_DEBUFF2 then delta = -TUNING.SANITYAURA_TINY * 2 -- You can replace 2 with a higher value to make it stronger or a smaller value to make it weaker elseif inst.secs_since_killed >= KILL_DEBUFF1 then delta = -TUNING.SANITYAURA_TINY * 1 -- You can replace 1 with a higher value to make it stronger or a smaller value to make it weaker end return delta end local function OnSave(inst, data) data.secs_since_killed = inst.secs_since_killed end local function OnLoad(inst, data) if data ~= nil and data.secs_since_killed then inst.secs_since_killed = data.secs_since_killed end end if yourcharacter.lua already has an "OnLoad" or "OnSave" function then take the code of the OnLoad and OnSave functions here and put it in those instead with this code your character will gain tiny sanity for a day upon killing something and if didnt kill something for a day you will start lose sanity and if 2 day past you lose even more sanity. If you kill a mob or murder a critter in your inventory it resets that. I couldn't think of a easy way to make char say something without spamming it so hopefully somebody else can help you with that, hopefully the code will work for you also the time you last killed a mob should save when you go in cave or exit server so the sanity gain/drain should remain Edited June 21, 2022 by . . . Link to comment Share on other sites More sharing options...
Devgirl_Neko Posted June 22, 2022 Author Share Posted June 22, 2022 3 hours ago, . . . said: I whipped up this code right now so IDK 100% if it will work or crash, but you can test it hopefully it work put all this code inside yourcharacter.lua inside the master_postinit Hide contents if inst.secs_since_killed == nil then inst.secs_since_killed = 0 end -- Add value if doesn't exist inst:DoPeriodicTask(1, Secs_Since_Killed) inst.components.sanity.custom_rate_fn = SanityFN inst:ListenForEvent("killed", Killed) inst:ListenForEvent("murdered", Killed) inst.OnSave = OnSave inst.OnLoad = OnLoad and put all these code inside yourcharacter.lua above the master_postinit Hide contents local KILL_DEBUFF1 = 480 -- 480 seconds = 8 minutes = full DST day local KILL_DEBUFF2 = 960 -- 960 seconds = 16 minutes = 2 DST day local function Killed(inst) inst.secs_since_killed = 0 -- Reset end local function Secs_Since_Killed(inst) inst.secs_since_killed = inst.secs_since_killed + 1 end local function SanityFN(inst) local delta = 0 if inst.secs_since_killed < KILL_DEBUFF1 then delta = TUNING.SANITYAURA_TINY * 1 -- You can replace 1 with a higher value to make it stronger or a smaller value to make it weaker elseif inst.secs_since_killed >= KILL_DEBUFF2 then delta = -TUNING.SANITYAURA_TINY * 2 -- You can replace 2 with a higher value to make it stronger or a smaller value to make it weaker elseif inst.secs_since_killed >= KILL_DEBUFF1 then delta = -TUNING.SANITYAURA_TINY * 1 -- You can replace 1 with a higher value to make it stronger or a smaller value to make it weaker end return delta end local function OnSave(inst, data) data.secs_since_killed = inst.secs_since_killed end local function OnLoad(inst, data) if data ~= nil and data.secs_since_killed then inst.secs_since_killed = data.secs_since_killed end end if yourcharacter.lua already has an "OnLoad" or "OnSave" function then take the code of the OnLoad and OnSave functions here and put it in those instead with this code your character will gain tiny sanity for a day upon killing something and if didnt kill something for a day you will start lose sanity and if 2 day past you lose even more sanity. If you kill a mob or murder a critter in your inventory it resets that. I couldn't think of a easy way to make char say something without spamming it so hopefully somebody else can help you with that, hopefully the code will work for you also the time you last killed a mob should save when you go in cave or exit server so the sanity gain/drain should remain The mod crashes the game with this error. Specifically referring to the line "if data ~= nil and data.secs_since_killed then inst.secs_since_killed = data.secs_since_killed end" Link to comment Share on other sites More sharing options...
. . . Posted June 22, 2022 Share Posted June 22, 2022 can you post yourcharacter.lua file here then i can see what it looks like Link to comment Share on other sites More sharing options...
Devgirl_Neko Posted June 22, 2022 Author Share Posted June 22, 2022 1 hour ago, . . . said: can you post yourcharacter.lua file here then i can see what it looks like local MakePlayerCharacter = require "prefabs/player_common" local assets = { Asset("SCRIPT", "scripts/prefabs/player_common.lua"), } -- Your character's stats TUNING.KOUSAI_HEALTH = 150 TUNING.KOUSAI_HUNGER = 125 TUNING.KOUSAI_SANITY = 175 -- Custom starting inventory TUNING.GAMEMODE_STARTING_ITEMS.DEFAULT.KOUSAI = { } local start_inv = {} for k, v in pairs(TUNING.GAMEMODE_STARTING_ITEMS) do start_inv[string.lower(k)] = v.KOUSAI end local prefabs = FlattenTree(start_inv, true) -- When the character is revived from human local function onbecamehuman(inst) -- Set speed when not a ghost (optional) inst.components.locomotor:SetExternalSpeedMultiplier(inst, "kousai_speed_mod", 1) end local function onbecameghost(inst) -- Remove speed modifier when becoming a ghost inst.components.locomotor:RemoveExternalSpeedMultiplier(inst, "kousai_speed_mod") end -- When loading or spawning the character local function onload(inst) inst:ListenForEvent("ms_respawnedfromghost", onbecamehuman) inst:ListenForEvent("ms_becameghost", onbecameghost) if inst:HasTag("playerghost") then onbecameghost(inst) else onbecamehuman(inst) end if data ~= nil and data.secs_since_killed then inst.secs_since_killed = data.secs_since_killed end end -- Sanity Implementation local KILL_DEBUFF1 = 480 -- 480 seconds = 8 minutes = full DST day local KILL_DEBUFF2 = 960 -- 960 seconds = 16 minutes = 2 DST day local function Killed(inst) inst.secs_since_killed = 0 -- Reset end local function Secs_Since_Killed(inst) inst.secs_since_killed = inst.secs_since_killed + 1 end local function SanityFN(inst) local delta = 0 if inst.secs_since_killed < KILL_DEBUFF1 then delta = TUNING.SANITYAURA_TINY * 1 -- You can replace 1 with a higher value to make it stronger or a smaller value to make it weaker elseif inst.secs_since_killed >= KILL_DEBUFF2 then delta = -TUNING.SANITYAURA_TINY * 2 -- You can replace 2 with a higher value to make it stronger or a smaller value to make it weaker elseif inst.secs_since_killed >= KILL_DEBUFF1 then delta = -TUNING.SANITYAURA_TINY * 1 -- You can replace 1 with a higher value to make it stronger or a smaller value to make it weaker end return delta end local function OnSave(inst, data) data.secs_since_killed = inst.secs_since_killed end -- This initializes for both the server and client. Tags can be added here. local common_postinit = function(inst) -- Minimap icon inst.MiniMapEntity:SetIcon( "kousai.tex" ) end -- This initializes for the server only. Components are added here. local master_postinit = function(inst) -- Set starting inventory inst.starting_inventory = start_inv[TheNet:GetServerGameMode()] or start_inv.default -- choose which sounds this character will play inst.soundsname = "kousaievent" inst.talker_path_override = "customvoice/" -- Uncomment if "wathgrithr"(Wigfrid) or "webber" voice is used --inst.talker_path_override = "dontstarve_DLC001/characters/" -- Stats inst.components.health:SetMaxHealth(TUNING.KOUSAI_HEALTH) inst.components.hunger:SetMax(TUNING.KOUSAI_HUNGER) inst.components.sanity:SetMax(TUNING.KOUSAI_SANITY) -- Damage multiplier (optional) inst.components.combat.damagemultiplier = 2 -- Hunger rate (optional) inst.components.hunger.hungerrate = 1.2 * TUNING.WILSON_HUNGER_RATE -- Sanity modifiers inst.components.sanity.night_drain_mult = 0.5 -- Sanity Implementation if inst.secs_since_killed == nil then inst.secs_since_killed = 0 end -- Add value if doesn't exist inst:DoPeriodicTask(1, Secs_Since_Killed) inst.components.sanity.custom_rate_fn = SanityFN inst:ListenForEvent("killed", Killed) inst:ListenForEvent("murdered", Killed) inst.OnLoad = onload inst.OnNewSpawn = onload inst.OnSave = OnSave end return MakePlayerCharacter("kousai", prefabs, assets, common_postinit, master_postinit, prefabs) For the dialogue, would it be possible to make a check like this to prevent spamming: if inst.secs_since_killed = 0 dialogue 0 (I'm not sure what code is used to create dialogue) if inst.secs_since_killed = 480 dialogue 1 if inst.secs_since_killed = 960 dialogue 2 Link to comment Share on other sites More sharing options...
. . . Posted June 22, 2022 Share Posted June 22, 2022 Your "onload" function is missing data you need to change it from this local function onload(inst) to this local function onload(inst, data) and for dialogue maybe it can work use this and replace the old one local function Secs_Since_Killed(inst) inst.secs_since_killed = inst.secs_since_killed + 1 if inst.secs_since_killed == KILL_DEBUFF1 then inst.components.talker:Say("ah, i want to kill something dangit") elseif inst.secs_since_killed == KILL_DEBUFF2 then inst.components.talker:Say("im itching to KILLLLLLLLLLLLllll") end end Link to comment Share on other sites More sharing options...
Devgirl_Neko Posted June 22, 2022 Author Share Posted June 22, 2022 3 hours ago, . . . said: Your "onload" function is missing data you need to change it from this local function onload(inst) to this local function onload(inst, data) and for dialogue maybe it can work use this and replace the old one local function Secs_Since_Killed(inst) inst.secs_since_killed = inst.secs_since_killed + 1 if inst.secs_since_killed == KILL_DEBUFF1 then inst.components.talker:Say("ah, i want to kill something dangit") elseif inst.secs_since_killed == KILL_DEBUFF2 then inst.components.talker:Say("im itching to KILLLLLLLLLLLLllll") end end After doing some testing, this works! Thank you! 1 Link to comment 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