Saturday, June 20, 2015

Atari Green Toady

So the Green Toady in Anguna is the first somewhat difficult challenge the player faces. Unlike the simple slimes in the first few rooms, the Green Toady not only take a number of a hits to defeat, but also has a more difficult movement pattern:

He first wanders slowly and randomly, but as soon as he is lined up (or more accurately, close-to-lined up) with the player (on either the X or Y axis), he pauses, then charges quickly at the player, until he hits a wall.

Tonight's challenge was to get that working on Atari Anguna. This is the most complicated enemy so far on the Atari, and would require a bit more code than the other enemies. The trickiest part was something that should be simple for anyone with any real 6502 experience, but required some thought for me: figuring out a reasonably efficient way to determine if two numbers are within a certain range of each other. (ie I wanted to see if the enemy X position was within 5 (plus or minus) of the player X position).

What I ended up doing is below, although it's late, and I don't have the brain power to really figure out if there's any edge conditions that I'm missing involving overflowing between positive and negative numbers. (The X register contains the index of which enemy we're dealing with, as there can be more than 1 enemy onscreen at once):

    lda Enemy0X,X
    sbc PlayerX
    adc #5
    bmi .NotLinedUpX
    sbc #10
    bpl .NotLinedUpX
    ;chase main char only on Y axis

I'm loading the first value, subtracting the second. Then add 5. I check if the result is negative. If so, they're more than 5 apart in the one direction. Then subtract 10, and check if the result is positive. If so, it's more than 5 apart in the other direction. If neither is the case, then they're within 5 of each other.  It's only 16 cycles, so pretty efficient. I didn't bother to set or clear the carry flag, so it's not going to be exact (I could be off by 1, depending on the carry flag's state coming into this), but I'm not too worried -- for this case, "around 5" is all I need)

Anyway, the amazing part, is that after fixing a couple typos, the toady mostly worked on the first try. That NEVER happens.

I do have a couple minor tweaks to make him work better (I put the charge on a timer which is too short, and I didn't initialize him into any state, so he just sits there for awhile when he's first on the screen). But still, it was certainly an unexpected lucky outcome for a relatively complex enemy.

No comments:

NNNNNN in 12 hours

I recently announced my NESdev competition entry for this year: NNNNNN , a multiplayer NES port of the Gravitron from VVVVVV .  Now that it&...