A89: Re: sprites
[Prev][Next][Index][Thread]
A89: Re: sprites
Here you go
>
>Alright, I've finished this PutSprite routine I've been working so I'm
going
>to post it. It puts a 16x16, masked, clipped, non-aligned, gray scale
>sprite to video memory and stores the background. Even though I didn't
clip
>at the right and bottom of the screen, it will still return when the sprite
>is completely off the screen, leaving $5998 to $5b00 safe for variable
>storage.
>Here's an example to of it in use. Copy and paste the routine into your
>code if you want to use it; there's no need for it to be a library ... just
>be sure to give me credit :-)
>
include "92plus.h"
include "util.h"
include "gray4lib.h
xdef _main
xdef _comment
xdef _ti89
_main:
jsr util::clr_scr
jsr gray4lib::on
jsr clearGray
move.l #50,d0
move.l #20,d1
lea bgSprite(pc),a0
jsr loadSprite
lea xSprite(pc),a2
move.w #10,(a2)+
move.w #20,(a2)
controlLoop:
move.w xSprite(pc),d0
move.w ySprite(pc),d1
lea sprite(pc),a0
lea bg(pc),a2
jsr PutSprite
jsr util::idle_loop
cmp.w #337,d0
beq up
cmp.w #340,d0
beq down
cmp.w #338,d0
beq left
cmp.w #344,d0
beq right
cmp.w #264,d0
bne controlLoop
jsr gray4lib::off
rts
right:
lea xSprite(pc),a2
move.w (a2),d0
move.w 2(a2),d1
lea bg(pc),a0
jsr loadSprite
add.w #2,d0
move.w d0,(a2)
bra controlLoop
left:
lea xSprite(pc),a2
move.w (a2),d0
move.w 2(a2),d1
lea bg(pc),a0
jsr loadSprite
sub.w #2,d0
move.w d0,(a2)
bra controlLoop
up:
lea ySprite(pc),a2
move.w (a2),d1
move.w -2(a2),d0
lea bg(pc),a0
jsr loadSprite
sub.w #2,d1
move.w d1,(a2)
bra controlLoop
down:
lea ySprite(pc),a2
move.w (a2),d1
move.w -2(a2),d0
lea bg(pc),a0
jsr loadSprite
add.w #2,d1
move.w d1,(a2)
bra controlLoop
;*******************************************************
;masked 16x16 nonaligned gray scale sprite
;inputs sprite (64 byte sprite (layer1, layer2), 32 byte mask) pointed to by a0
;& 128 byte background storage area pointed to by a2
;*******************************************************
PutSprite:
movem.l d0-d2/a0-a3,-(a7)
tst.w d1
bmi clipTop ;clip top if d1 negative
tst.w d0
bmi clipLeft ;clip left if d0 negative
cmp.w #100,d1
bgt psReturn ;return if sprite not on screen
cmp.w #160,d0
bgt psReturn ;return if sprite not on screen
jsr FindPixel ;coordinates d0,d1 -> (a1) & bit offset d1
moveq #15,d0 ;loop 15 times in normal PutSprite
psLoop:
move.l (a3),64(a2)
move.l (a1),(a2)+ ;store longword of background
clr.l d2 ;clear upperword
move.w 64(a0),d2 ;sprite mask into d2
lsl.l d1,d2 ;shift it by complemented bit offset
not.l d2 ;complement mask
and.l d2,(a1) ;clear unwanted bits
and.l d2,(a3)
clr.l d2 ;clear upperword
move.w 32(a0),d2
lsl.l d1,d2
or.l d2,(a3)
clr.l d2
move.w (a0)+,d2 ;get current byte of sprite
lsl.l d1,d2 ;shift it by complemented bit offset
or.l d2,(a1) ;and or it to memory
add.w #30,a1 ;point to next row
add.w #30,a3
dbra d0,psLoop ;continue until sprite drawn
psReturn:
movem.l (a7)+,d0-d2/a0-a3
rts
clipTop:
cmp.w #-16,d1 ;if d1 is less than or equal to 16
ble psReturn ;then we don't want to put anything
tst.w d0 ;if clipping both left and top
bmi clipBoth ;run that routine
neg.w d1 ;make d1 positive
move.b d1,d2 ;store it for later
ext.l d1 ;clear the rest of d1
lsl.b #1,d1 ;multiply by 2 (2 words in a sprite row)
add.l d1,a0 ;add it to sprite pointer to get row to start at
clr.w d1 ;we want to start at row 0 (video mem)
jsr FindPixel ;coordinates d0,d1 -> (a1) & bit offset d1
move.b d2,d0 ;d0 from before is the inverse of # of rows to put
eor.b #15,d0 ;invert it
bra psLoop
clipLeft:
tst.w d1 ;check for clipping both top and left
bmi clipBoth
neg.w d0 ;make d0 positve
move.w d0,d2 ;store it in d3
clr.w d0 ;clear upperword
jsr FindPixel ;coordinates d0,d1 -> (a1) & bit offset d1
add.w d2,d1 ;add negated x to bitoffset for new bit offset
moveq #15,d0 ;loop 16 times
bra psLoop
clipBoth: ;the same as the above two, but integrated
neg.w d0
neg.w d1
and.w #15,d1
move.b d1,d2
ext.l d1
lsl.b #1,d1
add.l d1,a0
clr.w d1
move.w d0,-(a7)
clr.w d0
jsr FindPixel
add.w (a7)+,d1
movem.b d2,d0
eor.b #15,d0
bra psLoop
;***********************************************
;loads gray scale sprite (64 byte layer1, 64 byte layer2) at a0 to d0.w, d1.w
;use this to replace backgrounds stored from PutSprite
;***********************************************
loadSprite:
movem.l d0-d2/a0-a1/a3,-(a7)
tst.w d1
bmi ldClipTop
tst.w d0
bmi ldClipLeft
jsr FindPixel
moveq #15,d0
ldLoop:
move.l 64(a0),(a3)
move.l (a0)+,(a1)
add.w #30,a1
add.w #30,a3
dbra d0,ldLoop
ldReturn:
movem.l (a7)+,d0-d2/a0-a1/a3
rts
ldClipTop:
cmp.w #-16,d1
ble ldReturn
tst.w d0
bmi ldClipBoth
neg.w d1
and.w #15,d1
move.b d1,d2
ext.l d1
lsl.b #1,d1
add.l d1,a0
clr.w d1
jsr FindPixel
move.b d2,d0
eor.b #15,d0
bra ldLoop
ldClipLeft:
tst.w d1
bmi ldClipBoth
clr.w d0
jsr FindPixel
moveq #15,d0
bra ldLoop
ldClipBoth:
neg.w d1
and.w #15,d1
move.b d1,d2
ext.l d1
lsl.b #1,d1
add.l d1,a0
clr.w d1
clr.w d0
jsr FindPixel
movem.b d2,d0
eor.b #15,d0
bra ldLoop
FindPixel:
lea $4c00,a1 ;video mem -> a1
mulu.w #30,d1 ;multiply x coordinate by 30 (30 bytes in each row)
move.w d1,-(a7) ;add it to video mem
move.b d0,d1 ;store y coordinate
and.w #$fff0,d0 ;
lsr.b #3,d0 ;divide by 8 (8 pixels in a byte)
add.w d0,(a7) ;add it to video mem
and.b #15,d1 ;bottom 4 bits -> bit offset
eori.b #15,d1 ;but inverted
move.l (gray4lib::plane0),a3
add.w (a7),a1
add.w (a7)+,a3
rts
clearGray:
clr.l d0
move.l (gray4lib::plane0),a0 ;video mem adress into a0
moveq #92,d0 ;93 lines
\clr clr.l (a0)+
clr.l (a0)+
clr.l (a0)+
clr.l (a0)+
clr.l (a0)+
lea 10(a0),a0 ;next line in the video mem
dbra d0,\clr ;repeats
rts
sprite:
dc.b %11111111,%11111111
dc.b %10000000,%00000001
dc.b %10000000,%00000001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10001111,%11110001
dc.b %10000000,%00000001
dc.b %10000000,%00000001
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %10000000,%00000001
dc.b %10000000,%00000001
dc.b %10001111,%11110001
dc.b %10001000,%00010001
dc.b %10001000,%00010001
dc.b %10001000,%00010001
dc.b %10001000,%00010001
dc.b %10001000,%00010001
dc.b %10001000,%00010001
dc.b %10001000,%00010001
dc.b %10001000,%00010001
dc.b %10001111,%11110001
dc.b %10000000,%00000001
dc.b %10000000,%00000001
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
dc.b %11111111,%11111111
bg:
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
dc.l 0
bgSprite:
dc.b %11111111,%11111111,%11111111,%11111111
dc.b %10000000,%00000000,%00000000,%00000001
dc.b %10111111,%11111111,%11111111,%11111101
dc.b %10100000,%00000000,%00000000,%00000101
dc.b %10101111,%11111111,%11111111,%11110101
dc.b %10101000,%00000000,%00000000,%00010101
dc.b %10101011,%11111111,%11111111,%11010101
dc.b %10101010,%00000000,%00000000,%01010101
dc.b %10101010,%00000000,%00000000,%01010101
dc.b %10101011,%11111111,%11111111,%11010101
dc.b %10101000,%00000000,%00000000,%00010101
dc.b %10101111,%11111111,%11111111,%11110101
dc.b %10100000,%00000000,%00000000,%00000101
dc.b %10111111,%11111111,%11111111,%11111101
dc.b %10000000,%00000000,%00000000,%00000001
dc.b %11111111,%11111111,%11111111,%11111111
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
dc.l $ffffffff
xSprite:
dc.w 0
ySprite:
dc.w 0
_comment:
dc.b "sprite & fp test",0
end
graytest.89z