; Bitmap test

RAM_Bitmap        EQU $FF8000
RAM_VDPCOMMANDS   EQU $FF1000
RAM_HCount        EQU $FF0120

DrawBitmap macro lines
;  Insert this macro in your effect loop, after all drawing and calculations are done.
;  It needs around 1 VBLANK to process. The entire active screen can therefore be used
;  for other business. Please don't touch d7, a5 or a6 in your code (Or initialise them
;  after each loop...)
   lea   (VDPCONTROL), a5
   lea   (BITMAP_DMA_TABLE), a6
   moveq  #\lines-1, d7
   move.w #$8F20, (a5)  ; Auto increment = 32
;------------------------- DMA LOOP POINT (dbf references this)
   move.l (a6)+, (a5)
   move.l (a6)+, (a5)
   move.l (a6)+, (a5)
   move.w (a6)+, (a5)
   dbf d7, *-8       
;-------------------------



;   btst #3, ($c00005)               ; Syncs to new frame
;   beq.s *-4

    lea (RAM_Bitmap), a4
    move.w #128*64/4-1, d6

@Fubar:
    move.l #0, (a4)+
    dbf d6, @fubar


   btst #3, ($C00005)               ; syncs to end of vblank
   bne.s *-4
        
   clr.b (RAM_HCount)
   move.w #$8F02, (a5)  ; switch back to Auto Increment 2
   endm

BMPVBLANK:
;  Insert this macro in your effect loop, after all drawing and calculations are done.
;  It needs around 1 VBLANK to process. The entire active screen can therefore be used
;  for other business. Please don't touch d7, a5 or a6 in your code (Or initialise them
;  after each loop...)
   lea   (VDPCONTROL), a5
   lea   (BITMAP_DMA_TABLE), a6
   moveq  #96-1, d7
   move.w #$8F20, (a5)  ; Auto increment = 32
;------------------------- DMA LOOP POINT (dbf references this)
   move.l (a6)+, (a5)
   move.l (a6)+, (a5)
   move.l (a6)+, (a5)
   move.w (a6)+, (a5)
   dbf d7, *-8       
;-------------------------
;   WaitFrame
   clr.b (RAM_HCount)
   move.w #$8F02, (a5)  ; switch back to Auto Increment 2
   rte

BITMAPTEST:

   lea      (VDPControl), a5
   SetCRAMAddr 0, a5
   move.l #$00000A00, -4(a5)
   move.l #$00A00AA2, -4(a5)
   move.l #$000B0B2B, -4(a5)
   move.l #$024A0CCC, -4(a5)
   move.l #$0EEE0E44, -4(a5)
   move.l #$04E40EE8, -4(a5)
   move.l #$044E0E4E, -4(a5)
   move.l #$06EE0666, -4(a5)

   move.w #(128*96)-1, d0 ; x coordinate
   lea (RAM_BITMAP), a4
   lea (BMPTEST), a3
@LoadBMPLoop
   move.b (a3)+, (a4)+
   dbf d0, @LoadBMPLoop


   bsr.w Bitmap_InitVDP
   bsr.w Bitmap_InitScrollMap
   bsr.w Bitmap_InitInts
   
@Loop:

;   Do Drawing and Calculations here !

   DrawBitmap        ; THat's how easy it is :D!

   bra @Loop


Blitter:
;  Let's blitter the shit ouf of this litter!
;  a0 = Source image
;  d0 = Width in bytes
;  d1 = height in bytes
;  d2 = destination x
;  d3 = destination y
   subq.b #1, d3
   lsl.w #7, d3
   add.b d2, d3
   lea (RAM_Bitmap), a1
   add.w d3, a1
   moveq #0, d4
   move.b #128, d4
   sub.b d0, d4
   moveq #0, d5



   subq #1, d0
   subq #1, d1
   
@YBlit:
   move.w d0, d5
@Xblit:   
      move.b (a0)+, (a1)+   
      dbf d5, @Xblit
   
   add.w d4, a1
   dbf d1, @YBlit
   rts


BitmapHINT:
   move.w #$8F02, (a5)
   SetVSRAMAddr 0, a5
   tst.b (RAM_HCount)
   beq.s @its0
   clr.b (RAM_HCount)
   move.l #$0, (VDPDATA)
   move.w #$8F20, (a5)
   rte
@its0
   move.l #-1, (VDPDATA)
   addq.b #4, (RAM_HCount)
   move.w #$8F20, (a5)

   rte
BITMAPHINT_end


Bitmap_InitVDP:
   lea      (VDPControl), a5
   move.w   #$8A00, (a5)
   move.w   #$8F02, (a5) ; auto inc of 2
   move.w   #$9001, (a5) ; 32x64 planes
   move.w   #$8C81, (a5) ; 40H mode (need dat for moar DMA time)
   move.w   #$801C, (a5) ; enable HV counter
   move.w   #$8B00, (a5) ; Full screen scrolling
   move.w   #$8114, (a5) ; Disable display, disable ints.
   rts

Bitmap_InitInts:
   move.w   #$8A00, (VDPControl) ; HInt every 4 sliceamajiggers
   move  #$2700, sr
   lea (BitmapHINT), a0
   lea (RAM_HINT), a1
   move.l #((BitmapHINT_End-BitmapHINT)/2)-1,d0   
@CopyHINT:
   move.w (a0)+, (a1)+
   dbf d0, @CopyHINT   
   move.w  #$8154, (VDPControl)             ; Enable display, disable interrupts
   EnableInts
   rts

Bitmap_InitScrollMap:
; Initialise the tilemap
; $C000 for "A" buffer, $E000 for "B" buffer
   setVRAMAddr $C000, VDPControl             ; Write scroll map for Scroll A
   lea VDPData, a6
   moveq    #$0, d0
   moveq #24-1, d2
@WriteAMap:
   moveq #32-1, d1
@WriteAMap_:
   move.w   d0, (a6)
   addq.w   #2, d0
   dbf d1, @WriteAMap_
   moveq #32-1, d1
@WriteAMap__:
   move.w   #0, (a6)
   dbf d1, @WriteAMap__
   dbf d2, @WriteAMap
   
   
   setVRAMAddr $E000, VDPControl             ; Write Scrollmap for Scroll B
   moveq    #1, d0
   moveq #24-1, d2
@WriteBMap:
   moveq #32-1, d1
@WriteBMap_:
   move.w   d0, (a6)
   addq.w   #2, d0
   dbf d1, @WriteBMap_
   moveq #32-1, d1
@WriteBMap__:
   move.w   #0, (a6)
   dbf d1, @WriteBMap__
   dbf d2, @WriteBMap
   
   move.w #($8200|($C000/$400)), (VDPControl)
   move.w #($8400|($E000/$2000)), (VDPControl)
   SetVRAMAddr $F800, (VDPCONTROL)              ; HScroll
   move.l #$00000004, (VDPDATA)                 ; Write offset for Scroll B
   rts


WritePixel:
; Writes a Pixel to Bitmap buffer. This is extremely schlow so please work with
; the RAM buffer in your code directly... =P
; d0 = x coordinate
; d1 = y coordinate
; d2 = pixel data (palette ID)
; breaks nothing

   move.l   d3, -(sp)
   movem.l  d0-d1, -(sp)
   
   moveq    #0, d3
   move.b   d2, d3
   lsl.b    #4, d3         ; Shift to left 4 bits
   or.b     d3, d2         ; Double pixel width meepsphere
   
   lea      RAM_Bitmap, a0
   moveq    #0, d3
   lsl.w    #7, d1         ; Multiply d1 by $80 (num of bytes per row)
   add.w    d0, d1         ; Add to it the X offset

   move.b   d2, (a0, d1.w) ; Write to RAM buffer

   movem.l   (sp)+, d0-d1
   move.l   (sp)+, d3
   rts


BITMAP_DMA_TABLE:
   incbin "./bitmap/dmatable.bin"
   even

   bmptest: