Scrolling Game Development Kit Forum
SGDK Version 1 => Script => Topic started by: popple on 2005-09-06, 02:37:27 AM
-
HI. I am having a problem with my sprite switching script. I believe i have narrowed the problem down to the SwitchPlayerSprite Sub. The weird thing is when i have the player sprite stationary, and a player switch is called, it works fine, but if i have moving (holding down either the right or left arrow) and a player switch is called, this sub runs in a infinate loop. I have an inventory item that is displayed on screen, and i added a line in the SwitchPlayerSprite function so i could see if it was looping.
Code in question
Sub SwitchPlayerSprite(NewSpriteName)
Dim NewSpr
Dim Idx
Dim MyState, SprCount
Dim oLayer
ProjectObj.GamePlayer.InvQuantityOwned(8) = ProjectObj.GamePlayer.InvQuantityOwned(8) + 1
Set oLayer = ProjectObj.GamePlayer.PlayerSprite.rDef.rLayer
MyState = ProjectObj.GamePlayer.PlayerSprite.CurState
With ProjectObj.GamePlayer.PlayerSprite.rDef.rLayer
Set NewSpr = .pMap.SpriteDefs(NewSpriteName).MakeInstance
'.rDef.rLayer.AddSprite HostObj.AsObject(NewSpr)
NewSpr.X = ProjectObj.GamePlayer.PlayerSprite.X
NewSpr.Y = ProjectObj.GamePlayer.PlayerSprite.Y
SprCount = .SpriteCount
Idx = 0
Do While Idx < SprCount
If .Sprite(Idx) Is ProjectObj.GamePlayer.PlayerSprite Then
oLayer.RemoveSprite(Idx)
Exit Do
End If
Idx = Idx + 1
Loop
.AddSprite(NewSpr)
Set ProjectObj.GamePlayer.PlayerSprite = NewSpr
End With
'Reset the state of the playersprite
ProjectObj.GamePlayer.PlayerSprite.CurState = MyState
End Sub
Any help or ideas is greatly appricated!!
-
What is the code that calls that function, that's more likely the problem.
-
I am attaching all the code that calls this. It is happening both when i am switching characters, and when my player sprite is injured. The odd thing is now, it works fine when i start out in one character (patch), but not in the other character (kimmy)
'==============Hit control to switch characters
Sub Player_OnControllerMove(OldActions, NewActions)
Dim oPlayerSprite, oLayer
Dim NewSpr
Dim NewSpr2
Set oPlayerSprite = ProjectObj.GamePlayer.PlayerSprite
Set oLayer = ProjectObj.GamePlayer.PlayerSprite.rDef.rLayer
If ((OldActions And eActionBits.ACTION_BUTTON2) = 0) And _
((NewActions And eActionBits.ACTION_BUTTON2) <> 0) Then
SwitchCharacters
End If
End Sub
'=================Switch Characters between kimmy and patch
Sub SwitchCharacters()
If Timer - CharacterSwitchTimer > CharacterSwitchDelay And PlayerHurtBool = False and PlayerDeathBool = False Then
CharacterSwitchBool = True
If CurrentCharacter = "Kimmy" Then
SwitchPlayerSprite "kimmytopatch"
CurrentCharacter = "Patch"
ProjectObj.GamePlayer.InvQuantityOwned(0) = 1 'alter climbing inv. so kimmy cant climb hurt
ProjectObj.GamePlayer.InvQuantityOwned(1) = 0
ProjectObj.GamePlayer.InvQuantityOwned(2) = 1
ProjectObj.GamePlayer.InvQuantityOwned(3) = 1
ProjectObj.GamePlayer.InvQuantityOwned(4) = 1
ProjectObj.GamePlayer.InvQuantityOwned(13) = 1
ProjectObj.GamePlayer.InvQuantityOwned(14) = 0
Elseif CurrentCharacter = "Patch" Then
SwitchPlayerSprite "patchtokimmy"
CurrentCharacter = "Kimmy"
ProjectObj.GamePlayer.InvQuantityOwned(0) = 0
ProjectObj.GamePlayer.InvQuantityOwned(1) = 1
ProjectObj.GamePlayer.InvQuantityOwned(2) = 0
ProjectObj.GamePlayer.InvQuantityOwned(3) = 0
ProjectObj.GamePlayer.InvQuantityOwned(4) = 0
ProjectObj.GamePlayer.InvQuantityOwned(13) = 0
ProjectObj.GamePlayer.InvQuantityOwned(14) = 1
End If
CharacterSwitchTimer = Timer
End If
End Sub
'===================PLAYER HURT===============================================
Sub PlayerHurt()
Dim oPlayerSprite, oLayer
Set oPlayerSprite = ProjectObj.GamePlayer.PlayerSprite
If (Timer - PlayerHurtTimer > PlayerHurtDelay) And (PlayerHurtBool = False) Then
PlayerHurtBool = True
If oPlayerSprite.rDef.Name = "patch" Then
SwitchPlayerSprite "patchhurt"
ProjectObj.GamePlayer.InvQuantityOwned(6) = ProjectObj.GamePlayer.InvQuantityOwned(6) - 1
UpdateHUD
Elseif oPlayerSprite.rDef.Name = "kimmy" Then
SwitchPlayerSprite "kimmyhurt"
ProjectObj.GamePlayer.InvQuantityOwned(6) = ProjectObj.GamePlayer.InvQuantityOwned(6) - 1 'take a health away
ProjectObj.GamePlayer.InvQuantityOwned(14) = 0 'ProjectObj.GamePlayer.InvQuantityOwned(14) - 1 'take 1 away from kimmy inv. item, so she cant switch back to patch right away, which voids the invincibility
ProjectObj.GamePlayer.InvQuantityOwned(0) = 1 'alter climbing inv. so kimmy cant climb hurt
ProjectObj.GamePlayer.InvQuantityOwned(1) = 0
ProjectObj.GamePlayer.InvQuantityOwned(2) = 1
ProjectObj.GamePlayer.InvQuantityOwned(3) = 1
ProjectObj.GamePlayer.InvQuantityOwned(4) = 1
UpdateHUD
Elseif oPlayerSprite.rDef.Name = "kimmyclimb" Then
SwitchPlayerSprite "kimmyclimbhurt"
ProjectObj.GamePlayer.InvQuantityOwned(6) = ProjectObj.GamePlayer.InvQuantityOwned(6) - 1
UpdateHUD
End If
PlayerHurtTimer = Timer
End If
End Sub
'================== ON AFTER MOVE SPRITE======================================
Sub Player_OnAfterMoveSprites()
Const CollClass14 = 16383
Const CollClass15 = 32767
Dim oPlayerSprite, oLayer
Set oPlayerSprite = ProjectObj.GamePlayer.PlayerSprite
Set oLayer = ProjectObj.GamePlayer.PlayerSprite.rDef.rLayer
Dim I
Dim Spr, Def
Dim NewSpr, NewSpr2
I=0
'------------------ SEARCH THROUGH ALL SPRITES ON THE ACTIVE LAYER -----------
Do While I < oLayer.SpriteCount
Set Spr = oLayer.Sprite(I)
Set Def = Spr.rDef
If oPlayerSprite.rDef.Name = "kimmytopatch" And CharacterSwitchBool = False Then
If oPlayerSprite.CurFrame = (oPlayerSprite.rDef.StateFramecount(Spr.CurState) - 1) Then
SwitchPlayerSprite "patch"
UpdateHUD
End If
End If
If oPlayerSprite.rDef.Name = "patchtokimmy" And CharacterSwitchBool = False Then
If oPlayerSprite.CurFrame = (oPlayerSprite.rDef.StateFramecount(Spr.CurState) - 1) Then
SwitchPlayerSprite "kimmy"
UpdateHUD
End If
End If
If Timer - CharacterSwitchTimer > CharacterSwitchDelay Then
CharacterSwitchBool = False
End If
If oPlayerSprite.rDef.Name = SpriteDefAttack And _
oPlayerSprite.CurFrame = (oPlayerSprite.rDef.StateFrameCount(oPlayerSprite.CurState) -1) Then
SwitchPlayerSprite SpriteDefPatch
AttackTimer = Timer
End If
If oPlayerSprite.rDef.Name = "patchhurt" And PlayerHurtBool = False Then
If oPlayerSprite.CurFrame = (oPlayerSprite.rDef.StateFrameCount(oPlayerSprite.CurState) -1) Then
SwitchPlayerSprite "patch"
End If
ElseIf oPlayerSprite.rDef.Name = "kimmyhurt" And PlayerHurtBool = False Then
If oPlayerSprite.CurFrame = (oPlayerSprite.rDef.StateFrameCount(oPlayerSprite.CurState) -1)Then
SwitchPlayerSprite "kimmy"
End If
Elseif oPlayerSprite.rDef.Name = "kimmyclimbhurt" And PlayerHurtBool = False Then
If oPlayerSprite.CurFrame = (oPlayerSprite.rDef.StateFrameCount(oPlayerSprite.CurState) -1) Then
SwitchPlayerSprite "kimmyclimb"
End If
End If
If Timer - PlayerHurtTimer > PlayerHurtDelay Then
PlayerHurtBool = False
End If
I=I+1
Loop
I=0
End Sub
'================== SWITCH PLAYER SPRITE =====================================
Sub SwitchPlayerSprite(NewSpriteName)
Dim NewSpr
Dim Idx
Dim MyState, SprCount
Dim oLayer
ProjectObj.GamePlayer.InvQuantityOwned(8) = ProjectObj.GamePlayer.InvQuantityOwned(8) + 1
Set oLayer = ProjectObj.GamePlayer.PlayerSprite.rDef.rLayer
MyState = ProjectObj.GamePlayer.PlayerSprite.CurState
With ProjectObj.GamePlayer.PlayerSprite.rDef.rLayer
Set NewSpr = .pMap.SpriteDefs(NewSpriteName).MakeInstance
'.rDef.rLayer.AddSprite HostObj.AsObject(NewSpr)
NewSpr.X = ProjectObj.GamePlayer.PlayerSprite.X
NewSpr.Y = ProjectObj.GamePlayer.PlayerSprite.Y
If (NewSpriteName <> "kimmyhurt") And (NewSpriteName <> "patchhurt") And (NewSpriteName <> "kimmyclimbhurt") Then
NewSpr.DY = ProjectObj.GamePlayer.PlayerSprite.DY
End If
SprCount = .SpriteCount
Idx = 0
Do While Idx < SprCount
If .Sprite(Idx) Is ProjectObj.GamePlayer.PlayerSprite Then
oLayer.RemoveSprite(Idx)
Exit Do
End If
Idx = Idx + 1
Loop
'Idx = 0
.AddSprite(NewSpr)
Set ProjectObj.GamePlayer.PlayerSprite = NewSpr
End With
'Reset the state of the playersprite
ProjectObj.GamePlayer.PlayerSprite.CurState = MyState
End Sub
-
I just added a new sticky topic called "Tip: Debugging Script" in this Script forum. Perhaps you could take advantage of this to help find out what is going on in your script. Try outputting some debug log messages wherever you are calling SwitchSprites. If you are stuck in an infinite loop where the display does not update, you may need to use code like the following to force the log to the display inside the loop:
DrawLog
CurrentDisplay.Flip
That should redraw the display even when no events are getting a chance to run. You might want to do that inside your loop inside SwitchSprite, and also add a something to the log inside the loop so you can see if anything is happening:
LogMsg Idx