Jump to content

[Solved] How to add extra thing to idle state?


Recommended Posts

Hello, I'm very sorry for asking for a lot of help ,but I have no idea how to fix this :(...

So, I made some swimming thing for my character when he's in the ocean & I want him to play this state instead of idle state

inst.sg:GoToState("swim_idle")

 

I tried doing StateGraphPostInIt in modmain.lua to add my state in the idle state, but the game keep crashing saying " :2344: unexpected symbol near ',' "

Spoiler

AddStategraphPostInit("wilson", function(inst)
    State{
        name = "idle",
        tags = { "idle", "canrotate" },

        onenter = function(inst, pushanim)
            inst.components.locomotor:Stop()
            inst.components.locomotor:Clear()

            inst.sg.statemem.ignoresandstorm = true

            if inst.components.rider:IsRiding() then
                inst.sg:GoToState("mounted_idle", pushanim)
                return
            end

            local equippedArmor = inst.components.inventory:GetEquippedItem(EQUIPSLOTS.BODY)
            if equippedArmor ~= nil and equippedArmor:HasTag("band") then
                inst.sg:GoToState("enter_onemanband", pushanim)
                return
            end

            local anims = {}
            local dofunny = true

            if inst:HasTag("beaver") then
                if inst:HasTag("groggy") then
                    table.insert(anims, "idle_groggy_pre")
                    table.insert(anims, "idle_groggy")
                else
                    table.insert(anims, "idle_loop")
                end
                dofunny = false
            elseif inst.components.inventory:IsHeavyLifting() then
                table.insert(anims, "heavy_idle")
                dofunny = false
            else
                inst.sg.statemem.ignoresandstorm = false
                if inst:GetSandstormLevel() >= TUNING.SANDSTORM_FULL_LEVEL
                    and not inst.components.playervision:HasGoggleVision() then
                    if not (inst.AnimState:IsCurrentAnimation("sand_walk_pst") or
                            inst.AnimState:IsCurrentAnimation("sand_walk") or
                            inst.AnimState:IsCurrentAnimation("sand_walk_pre")) then
                        table.insert(anims, "sand_idle_pre")
                    end
                    table.insert(anims, "sand_idle_loop")
                    inst.sg.statemem.sandstorm = true
                    dofunny = false
                elseif not inst.components.sanity:IsSane() then
                    table.insert(anims, "idle_sanity_pre")
                    table.insert(anims, "idle_sanity_loop")
                elseif inst.components.temperature:IsFreezing() then
                    table.insert(anims, "idle_shiver_pre")
                    table.insert(anims, "idle_shiver_loop")
                elseif inst.components.temperature:IsOverheating() then
                    table.insert(anims, "idle_hot_pre")
                    table.insert(anims, "idle_hot_loop")
                    dofunny = false
                elseif inst:HasTag("groggy") then
                    table.insert(anims, "idle_groggy_pre")
                    table.insert(anims, "idle_groggy")
				elseif not inst:IsOnValidGround() then -- This my thing I added
					inst.sg:GoToState("swim_idle")
                else
                    table.insert(anims, "idle_loop")
                end
            end

            if pushanim then
                for k, v in pairs(anims) do
                    inst.AnimState:PushAnimation(v, k == #anims)
                end
            else
                inst.AnimState:PlayAnimation(anims[1], #anims == 1)
                for k, v in pairs(anims) do
                    if k > 1 then
                        inst.AnimState:PushAnimation(v, k == #anims)
                    end
                end
            end

            if dofunny then
                inst.sg:SetTimeout(math.random() * 4 + 2)
            end
        end,

        events =
        {
            EventHandler("sandstormlevel", function(inst, data)
                if not inst.sg.statemem.ignoresandstorm then
                    if data.level < TUNING.SANDSTORM_FULL_LEVEL then
                        if inst.sg.statemem.sandstorm then
                            inst.sg:GoToState("idle")
                        end
                    elseif not (inst.sg.statemem.sandstorm or inst.components.playervision:HasGoggleVision()) then
                        inst.sg:GoToState("idle")
                    end
                end
            end),
        },

        ontimeout = function(inst)
            local royalty = nil
            local mindistsq = 25
            for i, v in ipairs(AllPlayers) do
                if v ~= inst and
                    not v:HasTag("playerghost") and
                    v.entity:IsVisible() and
                    v.components.inventory:EquipHasTag("regal") then
                    local distsq = v:GetDistanceSqToInst(inst)
                    if distsq < mindistsq then
                        mindistsq = distsq
                        royalty = v
                    end
                end
            end
            if royalty ~= nil then
                inst.sg:GoToState("bow", royalty)
            else
                inst.sg:GoToState("funnyidle")
            end
        end,
    }, -- It crashes over here, I don't know what I'm doing wrong
end)

 

Does someone know how I can stop this from crashing? And thanks a lot for reading my problem :wilson_dorky:!! Have an amazing day/night :wilson_flower:!!!

Edited by SuperDavid
Link to comment
Share on other sites

You are not using the AddStategraphPostInit properly.

You have to define a new State and then feed the AddStategraphPostInit with that State.

e.g.

local mystate = State({
[...]
})

AddStategraphPostInit("stategraph", mystate)

 

Link to comment
Share on other sites

Well I put this new idle state in modmain.lua with StateGraphPostInIt & it doesn't seem to have replaced the old idle state?

Spoiler

local Idle = State({
        name = "idle",
        tags = { "idle", "canrotate" },

        onenter = function(inst, pushanim)
            inst.components.locomotor:Stop()
            inst.components.locomotor:Clear()

            inst.sg.statemem.ignoresandstorm = true

            if inst.components.rider:IsRiding() then
                inst.sg:GoToState("mounted_idle", pushanim)
                return
            end

            local equippedArmor = inst.components.inventory:GetEquippedItem(EQUIPSLOTS.BODY)
            if equippedArmor ~= nil and equippedArmor:HasTag("band") then
                inst.sg:GoToState("enter_onemanband", pushanim)
                return
            end

            local anims = {}
            local dofunny = true

            if inst:HasTag("beaver") then
                if inst:HasTag("groggy") then
                    table.insert(anims, "idle_groggy_pre")
                    table.insert(anims, "idle_groggy")
                else
                    table.insert(anims, "idle_loop")
                end
                dofunny = false
            elseif inst.components.inventory:IsHeavyLifting() then
                table.insert(anims, "heavy_idle")
                dofunny = false
            else
                inst.sg.statemem.ignoresandstorm = false
                if inst:GetSandstormLevel() >= TUNING.SANDSTORM_FULL_LEVEL
                    and not inst.components.playervision:HasGoggleVision() then
                    if not (inst.AnimState:IsCurrentAnimation("sand_walk_pst") or
                            inst.AnimState:IsCurrentAnimation("sand_walk") or
                            inst.AnimState:IsCurrentAnimation("sand_walk_pre")) then
                        table.insert(anims, "sand_idle_pre")
                    end
                    table.insert(anims, "sand_idle_loop")
                    inst.sg.statemem.sandstorm = true
                    dofunny = false
                elseif not inst.components.sanity:IsSane() then
                    table.insert(anims, "idle_sanity_pre")
                    table.insert(anims, "idle_sanity_loop")
                elseif inst.components.temperature:IsFreezing() then
                    table.insert(anims, "idle_shiver_pre")
                    table.insert(anims, "idle_shiver_loop")
                elseif inst.components.temperature:IsOverheating() then
                    table.insert(anims, "idle_hot_pre")
                    table.insert(anims, "idle_hot_loop")
                    dofunny = false
                elseif inst:HasTag("groggy") then
                    table.insert(anims, "idle_groggy_pre")
                    table.insert(anims, "idle_groggy")
				  elseif not inst:IsOnValidGround() then
					inst.sg:GoToState("swim_idle")
                else
                    table.insert(anims, "idle_loop")
                end
            end

            if pushanim then
                for k, v in pairs(anims) do
                    inst.AnimState:PushAnimation(v, k == #anims)
                end
            else
                inst.AnimState:PlayAnimation(anims[1], #anims == 1)
                for k, v in pairs(anims) do
                    if k > 1 then
                        inst.AnimState:PushAnimation(v, k == #anims)
                    end
                end
            end

            if dofunny then
                inst.sg:SetTimeout(math.random() * 4 + 2)
            end
        end,

        events =
        {
            EventHandler("sandstormlevel", function(inst, data)
                if not inst.sg.statemem.ignoresandstorm then
                    if data.level < TUNING.SANDSTORM_FULL_LEVEL then
                        if inst.sg.statemem.sandstorm then
                            inst.sg:GoToState("idle")
                        end
                    elseif not (inst.sg.statemem.sandstorm or inst.components.playervision:HasGoggleVision()) then
                        inst.sg:GoToState("idle")
                    end
                end
            end),
        },

        ontimeout = function(inst)
            local royalty = nil
            local mindistsq = 25
            for i, v in ipairs(AllPlayers) do
                if v ~= inst and
                    not v:HasTag("playerghost") and
                    v.entity:IsVisible() and
                    v.components.inventory:EquipHasTag("regal") then
                    local distsq = v:GetDistanceSqToInst(inst)
                    if distsq < mindistsq then
                        mindistsq = distsq
                        royalty = v
                    end
                end
            end
            if royalty ~= nil then
                inst.sg:GoToState("bow", royalty)
            else
                inst.sg:GoToState("funnyidle")
            end
        end,
})
AddStategraphPostInit("stategraph", Idle)

Did I do something wrong?

Edited by SuperDavid
Link to comment
Share on other sites

Sorry my post was not explicit enough.

When you call AddStategraphPostInit, the first argument is the name of the stategraph you want to replace.

So it would be "wilson" in your case (this is the stategraph used by all the player characters).

And don't forget to update the stategraph for the client side "wilson_client"

You can find more info about these in SGWilson.lua and SGWilson_client.lua.

 

Edited by ZupaleX
Link to comment
Share on other sites

It's so close to done, but I keep getting this crash & have no idea why it's happening!

Here's the code in modmain.lua.

Spoiler

local New_Idle = State {
    name = "idle",
        tags = { "idle", "canrotate" },

        onenter = function(inst, pushanim)
			if not inst:IsOnValidGround() then
				inst.sg:GoToState("swim_idle")
				return
			end
            inst.components.locomotor:Stop()
            inst.components.locomotor:Clear()

            inst.sg.statemem.ignoresandstorm = true

            if inst.components.rider:IsRiding() then
                inst.sg:GoToState("mounted_idle", pushanim)
                return
            end

            local equippedArmor = inst.components.inventory:GetEquippedItem(EQUIPSLOTS.BODY)
            if equippedArmor ~= nil and equippedArmor:HasTag("band") then
                inst.sg:GoToState("enter_onemanband", pushanim)
                return
            end

            local anims = {}
            local dofunny = true

            if inst:HasTag("beaver") then
                if inst:HasTag("groggy") then
                    table.insert(anims, "idle_groggy_pre")
                    table.insert(anims, "idle_groggy")
                else
                    table.insert(anims, "idle_loop")
                end
                dofunny = false
            elseif inst.components.inventory:IsHeavyLifting() then
                table.insert(anims, "heavy_idle")
                dofunny = false
            else
                inst.sg.statemem.ignoresandstorm = false
                if inst:GetSandstormLevel() >= TUNING.SANDSTORM_FULL_LEVEL
                    and not inst.components.playervision:HasGoggleVision() then
                    if not (inst.AnimState:IsCurrentAnimation("sand_walk_pst") or
                            inst.AnimState:IsCurrentAnimation("sand_walk") or
                            inst.AnimState:IsCurrentAnimation("sand_walk_pre")) then
                        table.insert(anims, "sand_idle_pre")
                    end
                    table.insert(anims, "sand_idle_loop")
                    inst.sg.statemem.sandstorm = true
                    dofunny = false
                elseif not inst.components.sanity:IsSane() then
                    table.insert(anims, "idle_sanity_pre")
                    table.insert(anims, "idle_sanity_loop")
                elseif inst.components.temperature:IsFreezing() then
                    table.insert(anims, "idle_shiver_pre")
                    table.insert(anims, "idle_shiver_loop")
                elseif inst.components.temperature:IsOverheating() then
                    table.insert(anims, "idle_hot_pre")
                    table.insert(anims, "idle_hot_loop")
                    dofunny = false
                elseif inst:HasTag("groggy") then
                    table.insert(anims, "idle_groggy_pre")
                    table.insert(anims, "idle_groggy")
                else
                    table.insert(anims, "idle_loop")
                end
            end

            if pushanim then
                for k, v in pairs(anims) do
                    inst.AnimState:PushAnimation(v, k == #anims)
                end
            else
                inst.AnimState:PlayAnimation(anims[1], #anims == 1)
                for k, v in pairs(anims) do
                    if k > 1 then
                        inst.AnimState:PushAnimation(v, k == #anims)
                    end
                end
            end

            if dofunny then
                inst.sg:SetTimeout(math.random() * 4 + 2)
            end
        end,

        events =
        {
            EventHandler("sandstormlevel", function(inst, data)
                if not inst.sg.statemem.ignoresandstorm then
                    if data.level < TUNING.SANDSTORM_FULL_LEVEL then
                        if inst.sg.statemem.sandstorm then
                            inst.sg:GoToState("idle")
                        end
                    elseif not (inst.sg.statemem.sandstorm or inst.components.playervision:HasGoggleVision()) then
                        inst.sg:GoToState("idle")
                    end
                end
            end),
        },

        ontimeout = function(inst)
            local royalty = nil
            local mindistsq = 25
            for i, v in ipairs(AllPlayers) do -- It crashes here!
                if v ~= inst and
                    not v:HasTag("playerghost") and
                    v.entity:IsVisible() and
                    v.components.inventory:EquipHasTag("regal") then
                    local distsq = v:GetDistanceSqToInst(inst)
                    if distsq < mindistsq then
                        mindistsq = distsq
                        royalty = v
                    end
                end
            end
            if royalty ~= nil then
                inst.sg:GoToState("bow", royalty)
            else
                inst.sg:GoToState("funnyidle")
            end
        end,
}
AddStategraphState("wilson", New_Idle)

 

The crash is happening at this code, I don't no why it crash I just got the state straight from SGwilson & only added my thing in at the top!

for i, v in ipairs(AllPlayers) do

" :1006: bad argument #1 to 'ipairs' (table expected, got nil) "

 

Also, may I ask do I have to make a wilson_client one too? I have a bunch of custom states just being added to "wilson" & it seems to work for me & any clients on my server just fine. And if I do have to add ones to wilson client can I just add all my states to wilson_client without make a whole new version of the state?

 

And thanks for your help man :D!

 

@ZupaleX Wow, I think that was the problem since it isn't crashing anymore, I feel like a idiot xD..

Thanks so much for your guidance man :wilson_flower:!

Edited by SuperDavid
Link to comment
Share on other sites

If your mod is all clients required then it should indeed be ok to not modify the wilson_client.

I might be wrong though, I always have to think for a bit about this client/server thingy (what requires a communication/exchange between the 2) and it's too late (or early) right now for me to think about it intensively.

 

The error you get is self explanatory. AllPlayers does not exists. Is it a GLOBAL value maybe? :)

 

EDIT:

@SuperDavid don't feel bad, everybody makes this types of mistake at some point.

 

Edited by ZupaleX
Link to comment
Share on other sites

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 account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

×
  • Create New...