So I implemented the following jump function in my game:
function jump(sp,vel,factor) for i=1,factor do player.sprite = 12 player.velocity+=sp if player.y<=player.origpos then player.y+=(player.velocity*player.speed) else player.velocity=vel player.y=flr(player.origpos) player.sprite = 0 player.jumping = false end end end |
The problem I am having here, is that the Y of the player every second jump is equal to player.origpos+0.24
I moved stuff around because what I feel is happening is that the routine is entering some condition one time too many, but why does it every second frame? Does it have to do with the fact that I am calling "factor" twice? And how would I fix this problem?
The difference is every second jump, the character ends up one pixel above the floor, and let me tell you, it does NOT let my OCD rest peacefully :D
Any help appreciated!
My first guess with no context is the "<=" might be important.
Another thing that I notice is player.y is tested before anything has been done to its value, so its initial state might be doing something. The other variable I'd watch is player.origpos , since from this snippet I don't know what sets it and it could be related.
Sanity check - make sure it's not related to flr and negative numbers behaving sort of opposite positive numbers. ( flr(1.5)==1 and flr(-1.5)==-2 )
I think I would apply the velocity first, and then check the resulting position and, if necessary, correct it and change mode.
Also, once player.y is below player.origpos on screen, there's no need to continue, so you should early-out at that point by breaking out of the loop.
There's also no need to set the sprite every iteration. Just use the final state.
function jump(sp,vel,factor) for i=1,factor do player.velocity+=sp player.y+=(player.velocity*player.speed) if player.y>=player.origpos then player.velocity=vel player.y=flr(player.origpos) player.jumping = false break end end player.sprite = player.jumping and 12 or 0 end |
Ahh good call with the sprite changing, I really shouldn't have it inside the loop indeed.
I'll look at this suggestions and report back.
Why did you change the direction of < though? That's like going in the opposite direction.
I think the main thing here is that break statement, I might be doing an extra step I don't need indeed. Is there any other way I could do this without having to use a forceful break?
One more: I don't understand at all that last line Felice. What are you doing there?
Thanks guys!
player.sprite = player.jumping and 12 or 0 |
pico-8 has a feature where you can use "and" or "or" when you assign a value to a variable as shorthand.
This might be easier to read:
player.sprite = (player.jumping and 12) or 0 |
It means that, if player.jumping is True, then it will set player.sprite to 12. Otherwise, it will set player.sprite to 0.
Which is equivalent to:
if player.sprite == true then player.sprite = 12 else player.sprite=0 end |
tbh I use the "x = value OR default" shorthand a lot. It's really helpful in functions:
function add(number1,number2) --if number2 is not defined, just add 1 return number1+(number2 or 1) end x = 10 --will print 15 print(add(x,5)) --will print 11 print(add(x)) |
But I didn't know you could do that using "and" that way, but if anyone would know it's @Felice.
Yeah, sorry, I forget that that shorthand might not be familiar to others. Enargy's got you covered at least. :)
Also the condition was reversed because the top half of the if/else ended up empty, so I only wanted what happened for the else block.
I totally have no idea about shorthand, thanks for the explanation! I'm all in for smaller, tidier code.
By the way, the reason this was happening was because I wasn't getting out of the loop early as Felice said. Just adding "break" inside that condition fixed it.
Bonus: I learned some shorthand :) Thanks everyone!
[Please log in to post a comment]