* BLiTTER BASE ADDRESS blitter equ $FF8A00 * BLiTTER REGISTER OFFSETS halftone equ 0 src_xinc equ 32 src_yinc equ 34 src_addr equ 36 endmask1 equ 40 endmask2 equ 42 endmask3 equ 44 dst_xinc equ 46 dst_yinc equ 48 dst_addr equ 50 x_count equ 54 y_count equ 56 hop equ 58 op equ 59 line_num equ 60 skew equ 61 vbl_vec: equ $70 vertflag: equ $0100 stmodes: equ $0080 overscan: equ $0040 pal: equ $0020 vga: equ $0010 tv: equ $0000 col80: equ $0008 col40: equ $0000 numcols: equ $0007 bps16: equ 4 bps8: equ 3 bps4: equ 2 bps2: equ 1 bps1: equ 0 mybit: equ %0000001000000000 mapw: equ 200 maph: equ 200 sw: equ 320 sh: equ 240 nplanes: equ 16 ***************************************************************** * Falcon Slide Demo. * * Version 1.0 * ***************************************************************** include 'fequates.s' start: move.l 4(a7),a3 base page move.l #mystack,a7 move.l $c(a3),d0 text len add.l $14(a3),d0 data len add.l $1c(a3),d0 BSS len add.l #$100,d0 basepage move.l d0,-(sp) move.l a3,-(sp) clr.w -(sp) move.w #$4a,-(sp) trap #1 shrink memory lea 12(sp),sp clr.l -(sp) ;as usual the first thing to move.w #$20,-(sp) ;do is go into supervisor mode trap #1 addq.l #6,sp move.l d0,savesp bsr putrout bsr putvbl bsr savecolors bsr setupscreen bsr clearscreens mainloop: move.w #100,d0 move.w #100,d1 * move.w mx,d2 * move.w my,d3 move.w #120,d2 move.w #120,d3 bsr linedraw bsr plotlinet bsr keyboard bra mainloop plotlinet: lea coords,a0 plll: move.w (a0)+,d0 bmi pllover move.w (a0)+,d1 move.w d0,pixelx move.w d1,pixely bsr putpixel bra plll pllover: rts linedraw: moveq #0,d7 cmp.w d1,d3 beq.s noline bge.s okdown exg d1,d3 exg d0,d2 okdown: moveq #1,d6 sub.w d1,d3 ; dy sub.w d0,d2 ; dx bge.s okright neg.w d2 neg.w d6 okright: lea coords,a0 move.w d0,d7 ;x1 move.w d3,d0 ;dy * moveq #0,d1 moveq #0,d5 lineloop: move.w d7,(a0)+ move.w d1,(a0)+ addq.w #1,d1 add.w d2,d5 test: cmp.w d3,d5 blt.s noacross sub.w d3,d5 add.w d6,d7 bra.s test noacross: dbra d0,lineloop noline: move.w #-1,(a0) rts swapnshow: move.l viewscreen1,d0 move.l viewscreen2,viewscreen1 move.l d0,viewscreen2 waitvbl: move.w #1,vblflag wvbloop: tst.w vblflag bpl wvbloop move.l viewscreen1,d0 move.l d0,d1 move.l d1,d2 lsr.l #8,d0 lsr.l #8,d0 move.w d0,vid_bh lsr.l #8,d1 and.l #$000000ff,d1 move.w d1,vid_bm and.l #$000000ff,d2 move.w d2,vid_bl rts ***************************************************************** * MAP WORLD * * This is the biggy, this will take a 100x200 strip of * * the 200x200 world map and plot it on the sphere. * ***************************************************************** mapworld: lea stretchoffsets,a6 lea stretchtable,a4 move.l b,d0 move.l d0,d7 ;counter add.l d7,d7 subq.l #1,d7 asl.l #3,d0 ;for index into table add.l (a6,d0.l),a4 ;points to stretch table for y lea stretchoffsets2,a6 lea stretchtable2,a5 lea array,a0 ;all the points and lengths mpwl: move.w (a4)+,d0 ;that is the y offset into map movem.w (a0)+,d1-d3 ;get xy start and length move.w d3,d4 ;save length asl.w #2,d4 ;*4 for index into offsets move.l a5,a2 ;copy table address add.l (a6,d4.w),a2 ;a2 is horizontal stretch table for this line bsr plotline dbf d7,mpwl rts ***************************************************************** * D0 is the y offset into map * * D1-2 is x and y on screen * D3 is the number of pixels * * A2 points to the stretch table * ***************************************************************** plotline: movem.l d0-a6,-(sp) move.l viewscreen1,a0 lea map,a1 mulu #mapw*2,d0 add.l d0,a1 ;a1 points at start of map data move.w mapx,d0 add.w d0,d0 add.w d0,a1 add.w #sw/2,d1 add.w #sh/2,d2 add.w d1,d1 add.w d1,a0 mulu #sw*2,d2 add.l d2,a0 ;a0 is screen address * subq.w #1,d3 plloop: move.w (a2)+,d0 add.w d0,d0 move.w (a1,d0.w),(a0)+ dbf d3,plloop plback: movem.l (sp)+,d0-a6 rts ***************************************************************** * test the stuff so far * ***************************************************************** drawelipse: lea array,a0 move.w #sw/2,d0 move.w #sh/2,d1 * add.l #4,a0 ;skip sig move.l b,d7 add.l d7,d7 subq.l #1,d7 pel: move.w (a0)+,d2 move.w (a0)+,d3 add.w d0,d2 ;centre it add.w d1,d3 move.w d2,pixelx move.w d3,pixely bsr putpixel add.w (a0)+,d2 move.w d2,pixelx bsr putpixel dbf d7,pel peover: rts ***************************************************************** * Arranges the table of elipse coords * * the table is as follows. * * * * x,y,dist to right point * * for the entire left side of elipse. * * coords are not shifted and are based around a 0,0 centre* ***************************************************************** arrangetable: * lea coords,a0 move.l elipseend,a0 ;the end of our coord list lea array,a1 * move.l #-1,(a1)+ ;sig start sub.l #4,a0 ;now pointing at last coord pair atl: move.w (a0),d0 ;are we at the top of the list? bmi atp1 ;yep well move on move.w 2(a0),d1 move.w d0,d2 neg.w d0 ;reflect x move.w d0,(a1)+ add.w d2,d2 neg.w d1 move.w d1,(a1)+ ;reflect y to top of elipse move.w d2,(a1)+ ;store the distance sub.l #4,a0 bra atl atp1: lea coords,a0 ;start at top this time add.l #4,a0 atl2: move.w (a0)+,d0 ;are we at the top of the list? bmi atp2 ;yep well move on move.w (a0)+,d1 move.w d0,d2 neg.w d0 ;reflect x move.w d0,(a1)+ add.w d2,d2 move.w d1,(a1)+ move.w d2,(a1)+ ;store the distance bra atl2 atp2: * move.l #-1,(a1)+ ;sig end rts ******************************************************************* a: dc.l 20 b: dc.l 199 xe: dc.l 0 ye: dc.l 0 asquare: dc.l 0 bsquare: dc.l 0 a22: dc.l 0 b22: dc.l 0 xslope: dc.l 0 yslope: dc.l 0 fmid: dc.l 0 plotelipse: lea coords,a0 move.w #-1,(a0)+ ;end of list reverse move.w #-1,(a0)+ ;end of list reverse move.l a,xe ;x=a move.l #0,ye ;y=0 move.l a,d0 mulu d0,d0 ;asquare=a*a move.l d0,asquare move.l b,d1 ;bsquare=b*b mulu d1,d1 move.l d1,bsquare add.l d0,d0 add.l d1,d1 move.l d0,a22 ;a22=asquare+asquare move.l d1,b22 ;b22=bsquare+bsquare move.l a,d2 muls.l d1,d2 move.l d2,xslope move.l #0,yslope ;yslope=0 move.l bsquare,d0 move.l a,d1 neg.l d1 muls.l d1,d0 add.l asquare,d0 move.l d0,fmid ;fmid=bsquare*(.25-a)+asquare move.l xe,d0 move.l ye,d1 move.l xslope,d2 move.l yslope,d3 move.l fmid,d4 move.l asquare,d5 move.l a22,d6 move.l b22,d7 eloop1: cmp.l d3,d2 ble beginnext * move.w d0,pixelx * move.w d1,pixely * bsr putpixel move.w d0,(a0)+ move.w d1,(a0)+ addq.l #1,d1 ;y=y+1 add.l d6,d3 tst.l d4 ;if fmid<0 bgt.s fmt1 add.l d3,d4 ;fmid=fmid+yslope+asquare add.l d5,d4 bra.s eloop1 fmt1: subq.l #1,d0 ;x=x-1 sub.l d7,d2 ;xslope=xslope-b22 sub.l d2,d4 ;fmid=fmid-xslope+yslope+asquare add.l d3,d4 add.l d5,d4 bra eloop1 beginnext: move.l d2,d5 add.l d3,d5 ;(yslope+xslope)/2 asr.l #1,d5 sub.l d5,d4 move.l bsquare,d5 eloop2: subq.l #1,d0 ;x=x-1 sub.l d7,d2 ;xslope=xslope-b22 tst.l d4 ;if fmid<0 blt.s fmt2 sub.l d2,d4 add.l d5,d4 tst.l d0 bge eloop2 move.l a0,elipseend move.w #-1,(a0)+ ;signify end of coord list rts fmt2: * move.w d0,pixelx * move.w d1,pixely * bsr putpixel move.w d0,(a0)+ ;fill, otherwise only add 1 point per y move.w d1,(a0)+ skipcoadd2: addq.l #1,d1 ;y=y+1 add.l d6,d3 ;yslope=yslope+a22 sub.l d2,d4 ;fmid=fmid-xslope+yslope+bsquare add.l d3,d4 add.l d5,d4 tst.l xe bge eloop2 move.l a0,elipseend move.w #-1,(a0)+ ;signify end of coord list rts ***************************************** * number in d0.l * * d1.l is base * * d2,x cursor * * d3,y cursor * ***************************************** prtnum: movem.l d0/d1,-(sp) lea posstring,a0 add.w #32,d3 move.b d3,2(a0) add.w #32,d2 move.b d2,3(a0) move.l a0,-(sp) move.w #9,-(sp) trap #1 addq.l #6,sp movem.l (sp)+,d0/d1 lea linebuffer,a0 clr.l (a0)+ clr.l (a0)+ clr.l (a0)+ clr.l (a0)+ clr.l (a0)+ loop1: divu d1,d0 swap d0 addi #'0',d0 cmpi.w #'9',d0 ble.s ok addq.w #7,d0 ok: move.b d0,-(a0) clr d0 swap d0 bne loop1 loop2: move.l a0,-(sp) move.w #9,-(sp) trap #1 addq.l #6,sp rts clearnums: lea clearstring,a0 add.w #32,d3 move.b d3,2(a0) * move.b d3,10(a0) add.w #32,d2 move.b d2,3(a0) * move.b d2,11(a0) move.l a0,-(sp) move.w #9,-(sp) trap #1 addq.l #6,sp rts linebuffer: ds.l 5 digits: dc.b 0 posstring: dc.b 27,'Y',0,0,0,0 clearstring: dc.b 27,'Y',0,0,' ',0,0 even syncmode: dc.w 1 waitkey: move.w #1,-(sp) trap #1 addq.l #2,sp rts keyboard: move.w #$ff,-(sp) move.w #$6,-(sp) trap #1 addq.l #4,sp tst.l d0 beq keyback swap d0 cmp.b #16,d0 *space beq exit *yes/no keyback: rts pause: move.w #7,-(sp) trap #1 addq.l #2,sp rts clearscreens: lea blitter,a6 .waitblit: btst #7,line_num(a6) bne .waitblit move.l viewscreen1,a0 move.l viewscreen2,a1 move.l a0,dst_addr(a6) move.w #2,dst_xinc(a6) move.w #2,dst_yinc(a6) move.w #sw,x_count(a6) move.w #sh,y_count(a6) move.w #-1,endmask1(a6) move.w #-1,endmask2(a6) move.w #-1,endmask3(a6) move.b #0,skew(a6) move.b #$0,op(a6) move.b #2,hop(a6) bset #6,line_num(a6) bset #7,line_num(a6) nextscreen: .waitblit: btst #7,line_num(a6) bne .waitblit move.l a1,dst_addr(a6) move.w #2,dst_xinc(a6) move.w #2,dst_yinc(a6) move.w #sw,x_count(a6) move.w #sh,y_count(a6) bset #6,line_num(a6) bset #7,line_num(a6) rts putpixel: movem.l d0/d1/a0,-(sp) moveq #0,d0 move.l d0,d1 move.w pixelx,d0 * add.w #sw/2,d0 add.l d0,d0 move.w pixely,d1 * add.w #sh/2,d1 mulu #sw*2,d1 add.l d1,d0 move.l viewscreen1,a0 add.l d0,a0 move.w #-1,(a0) * move.l #1000000,d0 *dl: * sub.l #1,d0 * bpl dl movem.l (sp)+,d0/d1/a0 rts buttondat: dc.w 0 mx: dc.w 0 my: dc.w 0 *************puts my mouse interupt in***************** putrout:move.w #34,-(sp) trap #14 addq.l #2,sp move.l d0,a0 move.l 16(a0),oldmouse move.l #myrout,16(a0) rts lastb: dc.w -1 mousehasgoneup: dc.w 0 **************my ubeut mouse interupt******************* myrout: movem.l d0-d2/a0-a1,-(sp) moveq #0,d0 move.b (a0),d0 cmpi.b #$fa,d0 bne myr1 move.w #1,buttondat bra myrxy myr1: cmpi.b #$f9,d0 bne myr2 move.w #2,buttondat bra myrxy myr2: cmpi.b #$fb,d0 bne myr3 move.w #3,buttondat bra myrxy myr3: move.w #1,mousehasgoneup move.w #0,buttondat myrxy: moveq #0,d0 move.b 1(a0),d0 ext.w d0 moveq #0,d1 move.b 2(a0),d1 ext.w d1 add.w d0,mx add.w d1,my * sub.w d1,my2 myr4: move.w mx,d0 move.w my,d1 bsr extra move.w d0,mx move.w d1,my movem.l (sp)+,d0-d2/a0-a1 rts extra: cmpi.w #mminx,d0 bge extra1 move.w #mminx,d0 bra extra2 extra1: cmpi.w #mmaxx,d0 ble extra2 move.w #mmaxx,d0 extra2: cmpi.w #mminy,d1 bge extra3 move.w #mminy,d1 bra extra4 extra3: cmpi.w #mmaxy,d1 ble extra4 move.w #mmaxy,d1 extra4: rts mminx: equ 20 mmaxx: equ sw mminy: equ 20 mmaxy: equ sh putvbl: move.l vbl_vec,vblt+2 ;set up vbl handler move.l vbl_vec,oldvblvec move.l #vbl_handler,vbl_vec rts halfframe: dc.w 0 ddl: dc.w -1 vbl_handler: move.w #-1,vblflag vblt: jmp $0.L savecolors: pea savedcolors move.w #16,-(sp) move.w #0,-(sp) move.w #94,-(sp) trap #14 add.l #10,sp rts restorecolors: pea savedcolors ;color array move.w #16,-(sp) ;number to set move.w #0,-(sp) ;index to start at move.w #93,-(sp) trap #14 add.l #10,sp rts exit: move.w #34,-(sp) trap #14 addq.l #2,sp move.l d0,a0 move.l oldmouse,16(a0) lea memlist,a6 demem: move.l (a6)+,d0 bmi nomoremem beq demem bsr deallocate bra demem nomoremem: move.l oldvblvec,vbl_vec move.w savemode,-(sp) move.w #3,-(sp) move.l savescreen,-(sp) move.l savescreen,-(sp) move.w #5,-(sp) trap #14 add.l #14,sp bsr restorecolors move.l savesp,-(sp) move.w #$20,-(sp) trap #1 addq.l #6,sp clr.w -(sp) trap #1 deallocate: move.l d0,-(sp) move.w #$49,-(sp) trap #1 addq.l #6,sp rts clearmem: move.l #(sw*sh),d0 subq.l #1,d0 moveq #0,d1 cml: move.w d1,(a0)+ subq.l #1,d0 bpl cml rts ********************************************************* * One call does it all * * Allocates memory for 3 screens * * targa load/hold area is internal. * * Then sets all the hardware stuff to create * * a 384*480 16bit screen * ********************************************************* setupscreen: move.l #(((sw/16)*nplanes*sh)*2)+8,-(sp) ;thats 1 screen size move.w #$48,-(sp) trap #1 addq.l #6,sp tst.l d0 bmi exit move.l d0,savemem1 and.l #$fffffffc,d0 move.l d0,viewscreen1 move.l d0,a0 bsr clearmem move.l #(((sw/16)*nplanes*sh)*2)+8,-(sp) ;thats 1 screen size move.w #$48,-(sp) trap #1 addq.l #6,sp tst.l d0 bmi exit move.l d0,savemem2 and.l #$fffffffc,d0 move.l d0,viewscreen2 move.w #2,-(sp) trap #14 addq.l #2,sp move.l d0,savescreen move.w #-1,-(sp) move.w #88,-(sp) trap #14 addq.l #4,sp move.w d0,savemode move.w #vertflag|vga|col40|bps16,-(sp) move.w #3,-(sp) move.l viewscreen1,-(sp) move.l viewscreen1,-(sp) move.w #5,-(sp) trap #14 add.l #14,sp * move.w #2,-(sp) * trap #14 * addq.l #2,sp * move.l d0,savescreen2 rts ********************************************************* * copy whole screen with blitter * * set screen to copy to in a1 * ********************************************************* copywhole: move.l savescreen2,a0 * move.l viewscreen,a1 lea blitter,a6 .waitblit: btst #7,line_num(a6) bne .waitblit move.l a0,src_addr(a6) move.l a1,dst_addr(a6) move.w #2,src_xinc(a6) move.w #2,dst_xinc(a6) move.w #2,src_yinc(a6) move.w #2,dst_yinc(a6) move.w #sw,x_count(a6) move.w #sh,y_count(a6) move.w #-1,endmask1(a6) move.w #-1,endmask2(a6) move.w #-1,endmask3(a6) move.b #0,skew(a6) move.b #$3,op(a6) move.b #2,hop(a6) bset #6,line_num(a6) bset #7,line_num(a6) rts doscreens: * lea scrnback,a0 * move.l savescreen2,a1 * jsr ice_unpack * move.l viewscreen1,a1 * bsr copywhole * move.l viewscreen2,a1 * bsr copywhole * rts ;********************************************* Unpackroutine von ICE-PACK ; assemble with Devpac or any other Assembler ; length of this unpacking routine: 294 bytes ; a0 = address of packed data ; a1 = address of unpacked data ice_unpack: movem.l d0-a6,-(sp) bsr ice04 cmpi.l #'Ice!',d0 ; Is file packed? bne ice03 ; no, leave this routine bsr ice04 lea -8(a0,d0.l),a5 bsr ice04 * move.l d0,(sp) movea.l a1,a4 movea.l a1,a6 adda.l d0,a6 movea.l a6,a3 move.b -(a5),d7 bsr ice06 ice03: movem.l (sp)+,d0-a6 rts ice04: moveq #3,d1 ice05: lsl.l #8,d0 move.b (a0)+,d0 dbra d1,ice05 rts ice06: bsr ice0a bcc ice09 moveq #0,d1 bsr ice0a bcc ice08 lea ice17(pc),a1 moveq #4,d3 ice07: move.l -(a1),d0 bsr ice0c swap d0 cmp.w d0,d1 dbne d3,ice07 add.l 20(a1),d1 ice08: move.b -(a5),-(a6) dbra d1,ice08 ice09: cmpa.l a4,a6 bgt ice0f rts ice0a: add.b d7,d7 bne ice0b move.b -(a5),d7 addx.b d7,d7 ice0b: rts ice0c: moveq #0,d1 ice0d: add.b d7,d7 bne ice0e move.b -(a5),d7 addx.b d7,d7 ice0e: addx.w d1,d1 dbra d0,ice0d rts ice0f: lea ice18(pc),a1 moveq #3,d2 ice10: bsr ice0a dbcc d2,ice10 moveq #0,d4 moveq #0,d1 move.b 1(a1,d2.w),d0 ext.w d0 bmi ice11 bsr ice0c ice11: move.b 6(a1,d2.w),d4 add.w d1,d4 beq ice13 lea ice19(pc),a1 moveq #1,d2 ice12: bsr ice0a dbcc d2,ice12 moveq #0,d1 move.b 1(a1,d2.w),d0 ext.w d0 bsr ice0c add.w d2,d2 add.w 6(a1,d2.w),d1 bpl ice15 sub.w d4,d1 bra ice15 ice13: moveq #0,d1 moveq #5,d0 moveq #-1,d2 bsr ice0a bcc ice14 moveq #8,d0 moveq #$3f,d2 ice14: bsr ice0c add.w d2,d1 ice15: lea 2(a6,d4.w),a1 adda.w d1,a1 move.b -(a1),-(a6) ice16: move.b -(a1),-(a6) dbra d4,ice16 bra ice06 DC.B $7f,$ff,$00,$0e,$00,$ff,$00,$07 DC.B $00,$07,$00,$02,$00,$03,$00,$01 DC.B $00,$03,$00,$01 ice17: DC.B $00,$00,$01,$0d,$00,$00,$00,$0e DC.B $00,$00,$00,$07,$00,$00,$00,$04 DC.B $00,$00,$00,$01 ice18: DC.B $09,$01,$00,$ff,$ff,$08,$04,$02 DC.B $01,$00 ice19: DC.B $0b,$04,$07,$00,$01,$1f,$ff,$ff DC.B $00,$1f even section data viewscreen2: dc.l -1 viewscreen1: dc.l -1 memlist: savemem1: dc.l 0 savemem2: dc.l 0 savemem3: dc.l 0 dc.l -1 ;end of mem list flag soundmem: dc.l 0 howlong: dc.l 0 handles: dc.w 0 map: incbin 'map.img' stretchoffsets: incbin 'st200.off' stretchtable: incbin 'st200.tab' stretchoffsets2: incbin 'st100.off' stretchtable2: incbin 'st100.tab' even SECTION BSS ds.l 1000 mystack: ds.w 1 ;stacks go backwards savedcolors: ds.w 256*3 dummy: ds.w 1 color: ds.w 1 pixelx: ds.w 1 pixely: ds.w 1 savesp: ds.l 1 time: ds.l 1 frames: ds.l 1 blitx: ds.l 1 blity: ds.l 1 picsource: ds.l 1 expansion: ds.w 1 oldmouse: ds.l 1 whichpic: ds.l 1 frame: ds.l 1 whicheffect: ds.l 1 oldvblvec: ds.l 1 vblflag: ds.w 1 savescreen: ds.l 1 savescreen2: ds.l 1 savemode: ds.w 1 save114: ds.l 1 mastervol: ds.w 1 bufferword: ds.w 1 elipseend: ds.l 1 mapx: ds.w 1 mapy: ds.w 1 coords: ds.w 2000 array: ds.w 8000