In this post I am assuming you have basic knowledge of how a State Machine Works
This is a Hierarchical Finite State Machine!
This means it is setup in the editor as custom nodes!
The State Class
In this state machine, each state will extend from theState
class below. Transitions between states can be called with this nice function I made calledtransition_to()
. When using this state machine treat theupdate
andphysics_update
like_process
and_physics_process
respectively.
class_nameStateextendsNodesignaltransitioned(state:State,new_state_name:String)varplayer:CharacterBody2D@onreadyvarsprite:AnimatedSprite2D=%AnimatedSprite2Dfuncenter()->void:passfuncexit()->void:passfuncupdate(delta:float)->void:passfuncphysics_update(delta:float)->void:passfunctransition_to(new_state_name:String)->void:transitioned.emit(self,new_state_name)
The State Machine
The State Machine node is where we will be adding our State nodes to as children. The state machine mostly takes care of transitions, keeping track of current state, and executes the code of the states.
Must be a child of a CharacterBody2D (Aka your player)
class_nameStateMachineextendsNode@exportvarinitial_state:Statevarcurrent_state:Statevarstates:Dictionary={}func_ready()->void:_initialize_states()_set_initial_state()func_initialize_states()->void:forchildinget_children():ifchildisState:states[child.name.to_lower()]=childchild.transitioned.connect(_on_state_transition)func_set_initial_state()->void:ifinitial_state:_assign_player_reference(initial_state)initial_state.enter()current_state=initial_stateelse:push_warning("No initial state set for StateMachine in "+owner.name)func_process(delta:float)->void:ifcurrent_state:current_state.update(delta)func_physics_process(delta:float)->void:ifcurrent_state:current_state.physics_update(delta)func_on_state_transition(state:State,new_state_name:String)->void:ifstate!=current_state:returnvarnew_state=states.get(new_state_name.to_lower())ifnotnew_state:push_warning("State '"+new_state_name+"' not found in StateMachine")return_transition_to_new_state(new_state)func_transition_to_new_state(new_state:State)->void:current_state.exit()current_state=new_state_assign_player_reference(new_state)new_state.enter()func_assign_player_reference(state:State)->void:varparent=get_parent()ifparentisCharacterBody2D:state.player=parentelse:push_warning("StateMachine's parent must be CharacterBody2D")
Example States and proper usage:
Write code necessary only for that state.
class_nameIdleStateextendsState@export_range(120,420)varfriction:floatfuncenter()->void:print("Entered Idle")sprite.play("idle")funcexit()->void:print("Exited Idle")funcupdate(delta:float)->void:ifInput.get_axis("ui_left","ui_right")!=0:transition_to("Walk")ifnotplayer.is_on_floor():transition_to("Fall")funcphysics_update(delta:float)->void:ifplayer.velocity.x!=0:player.velocity.x=lerp(player.velocity.x,0,friction*delta)
Top comments(0)
For further actions, you may consider blocking this person and/orreporting abuse