This version came from Pere Serrat. In Simon’s own words, “WOW !!! now this rocks….” It’s basically a complete re write, making much better use of nibble testing.
Version 2 on the left, 3 on the right.
Looking at version 3, on the right side:
Lines 3–5 is the same old same old, just preloading everything with the sprite, background and destination (mixbuf).
Lines 6–8 load up registers A and B with the data from the sprite and background in preparation to inspect them.
Lines 9–15, we want to work with the left nibble, so we mask off the right with the
ANDA will set the zero (Z) flag if the result is 0, and
BEQ will branch if Z is set. So what ends up happening is if the left nibble is not zero, we store the byte into the mixbuf (
std ,u) then proceed to seeN2 were can can check the right nibble. If however the left nibble is zero, the code ends up at
useB1 and will store the background nibble instead.
Lines 17–29 deal with the right nibble in a similar way. However instead of an
sta ,u or a
stb ,u which would store A or B to the mixbuf, we need to preserve what is already there. We do that at line 22 and 26 with an
ora ,u and
orb ,u which does a logical or of A and the byte in mixbuf, storing the result in A. Once or’ed together we can store the byte into the mixbuf with
I think line 28 & 29 is a bug. Considering line 24
bra ctrl would end up at the wrong place. I think the ctrl label should be going to line 28, where we check for the end of the buffer.
24 bra ctrl ; go control end 25 useB2 andb #$0f ; use right nibble 26 orb ,u ; add dest buffer 27 stb ,u+ ; update buffer 28 cmpx #sp_end ; got to end? 29 ctrl bne loop1 ; no loopback
Line 28–30 decide if we have processed the last byte of the sprite and jump to the top if not.
Next, Version 5