diff --git a/008.shift_blit/Makefile b/008.shift_blit/Makefile new file mode 100644 index 0000000..6a3777b --- /dev/null +++ b/008.shift_blit/Makefile @@ -0,0 +1,22 @@ +MODULE=shift_blit.s +FLOPPY=bin/shift_blit.adf +IMAGEDATA=out/image-palette.s out/image.bin +IMAGEFILE=../assets/mission-beach.png +BOB_BASE=out/emoji +BOB_IMAGEDATA=$(BOB_BASE).bin $(BOB_BASE)-mask.bin +BOB_IMAGEFILE=../assets/emoji.png +EXTRA=$(IMAGEDATA) $(BOB_IMAGEDATA) +SHARED_PALETTE_BASE=out/shared-palette +SHARED_PALETTE=$(SHARED_PALETTE_BASE).pal + +include ../shared/base.mk + +$(SHARED_PALETTE): $(IMAGEFILE) $(BOB_IMAGEFILE) + $(IMAGECON) --input $(IMAGEFILE),$(BOB_IMAGEFILE) --output $(SHARED_PALETTE_BASE) --colors 32 --quantize --output-palette + +$(IMAGEDATA): $(IMAGECON) $(IMAGEFILE) $(SHARED_PALETTE) + $(IMAGECON) --input $(IMAGEFILE) --output out/image --output-bitplanes --output-palette-asm --use-palette $(SHARED_PALETTE) + +$(BOB_IMAGEDATA): $(IMAGECON) $(BOB_IMAGEFILE) $(SHARED_PALETTE) + $(IMAGECON) --input $(BOB_IMAGEFILE) --output $(BOB_BASE) --output-bitplanes --use-palette $(SHARED_PALETTE) + $(IMAGECON) --input $(BOB_IMAGEFILE) --output $(BOB_BASE) --output-mask --quantize diff --git a/008.shift_blit/README.md b/008.shift_blit/README.md new file mode 100644 index 0000000..3c5a17c --- /dev/null +++ b/008.shift_blit/README.md @@ -0,0 +1,26 @@ +perform a shifted blit +====================== + +Extending [007.masked_blit](../007.masked_blit), we now add the capability to blit to non word aligned columns. + +The blitter can only address word aligned screen positions. This makes drawing something on a non word aligned boundary slightly more complex. + +So the algorithm for drawing to non word aligned boundaries is as follows: + 1. The destination address is the word aligned address to the left of the desired position. + 2. Command the blitter to blit an extra word to the right of our blitter object. + 3. We mask the trailing word of each line to prevent the extra word from being blit. + 4. We shift the data by the difference in bits between the desired column and the word aligned column from (1). + 5. We make the line modulos #-2 so blitter object data is correctly fetched. + + + +[Download disk image](bin/shift_blit.adf?raw=true) + +Screenshot: + +![Screenshot](screenshot.png?raw=true) + +Masked blit screenshot for reference: + +![Screenshot](../007.masked_blit/screenshot.png?raw=true) + diff --git a/008.shift_blit/bin/shift_blit.adf b/008.shift_blit/bin/shift_blit.adf new file mode 100644 index 0000000..cacf0a7 Binary files /dev/null and b/008.shift_blit/bin/shift_blit.adf differ diff --git a/008.shift_blit/screenshot.png b/008.shift_blit/screenshot.png new file mode 100644 index 0000000..c2d923f Binary files /dev/null and b/008.shift_blit/screenshot.png differ diff --git a/008.shift_blit/shift_blit.s b/008.shift_blit/shift_blit.s new file mode 100644 index 0000000..efd2933 --- /dev/null +++ b/008.shift_blit/shift_blit.s @@ -0,0 +1,166 @@ + include "../include/registers.i" + include "hardware/dmabits.i" + include "hardware/intbits.i" + +LVL3_INT_VECTOR equ $6c +SCREEN_WIDTH equ 320 +SCREEN_HEIGHT equ 256 +SCREEN_WIDTH_BYTES equ (SCREEN_WIDTH/8) +SCREEN_BIT_DEPTH equ 5 +SCREEN_RES equ 8 ; 8=lo resolution, 4=hi resolution +RASTER_X_START equ $81 ; hard coded coordinates from hardware manual +RASTER_Y_START equ $2c +RASTER_X_STOP equ RASTER_X_START+SCREEN_WIDTH +RASTER_Y_STOP equ RASTER_Y_START+SCREEN_HEIGHT + +BOB_WIDTH equ 64+16 ; Must blit extra word to allow shifting +BOB_HEIGHT equ 64 +BOB_WIDTH_BYTES equ BOB_WIDTH/8 +BOB_WIDTH_WORDS equ BOB_WIDTH/16 +BOB_XPOS equ 16 +BOB_YPOS equ 16 +BOB_XPOS_BYTES equ (BOB_XPOS)/8 + + +entry: + ;; custom chip base globally in a6 + lea CUSTOM,a6 + + move #$7ff,DMACON(a6) ; disable all dma + move #$7fff,INTENA(a6) ; disable all interrupts + + include "out/image-palette.s" + if 0 + ;; reset color registers to white to prevent startup flicker + move.l #32,d0 + lea COLOR00(a6),a0 +.loop: + move.w #$FFF,(a0) + addq #2,a0 + dbra d0,.loop + endif + + ;; set up playfield + move.w #(RASTER_Y_START<<8)|RASTER_X_START,DIWSTRT(a6) + move.w #((RASTER_Y_STOP-256)<<8)|(RASTER_X_STOP-256),DIWSTOP(a6) + + move.w #(RASTER_X_START/2-SCREEN_RES),DDFSTRT(a6) + move.w #(RASTER_X_START/2-SCREEN_RES)+(8*((SCREEN_WIDTH/16)-1)),DDFSTOP(a6) + + move.w #(SCREEN_BIT_DEPTH<<12)|$200,BPLCON0(a6) + move.w #SCREEN_WIDTH_BYTES*SCREEN_BIT_DEPTH-SCREEN_WIDTH_BYTES,BPL1MOD(a6) + move.w #SCREEN_WIDTH_BYTES*SCREEN_BIT_DEPTH-SCREEN_WIDTH_BYTES,BPL2MOD(a6) + + ;; poke bitplane pointers + lea bitplanes(pc),a1 + lea copper(pc),a2 + moveq #SCREEN_BIT_DEPTH-1,d0 +.bitplaneloop: + move.l a1,d1 + move.w d1,2(a2) + swap d1 + move.w d1,6(a2) + lea SCREEN_WIDTH_BYTES(a1),a1 ; bit plane data is interleaved + addq #8,a2 + dbra d0,.bitplaneloop + + ;; install copper list, then enable dma and selected interrupts + lea copper(pc),a0 + move.l a0,COP1LC(a6) + move.w COPJMP1(a6),d0 + move.w #(DMAF_BLITTER|DMAF_SETCLR!DMAF_COPPER!DMAF_RASTER!DMAF_MASTER),DMACON(a6) + move.w #(INTF_SETCLR|INTF_INTEN|INTF_EXTER),INTENA(a6) + + bsr.s doblit + +.mainLoop: + move.w #$02a,d0 ;wait for EOFrame + bsr.s waitRaster + bra.s .mainLoop + +waitRaster: ;wait for rasterline d0.w. Modifies d0-d2/a0. + move.l #$1ff00,d2 + lsl.l #8,d0 + and.l d2,d0 + lea $dff004,a0 +.wr: move.l (a0),d1 + and.l d2,d1 + cmp.l d1,d0 + bne.s .wr + rts + +blitWait: + tst DMACONR(a6) ;for compatibility +.waitblit: + btst #6,DMACONR(a6) + bne.s .waitblit + rts + +;; BLTCON? configuration +;; http://amigadev.elowar.com/read/ADCD_2.1/Hardware_Manual_guide/node011C.html +;; blitter logic function minterm truth table +;; fill in D column for desired function +;; A(mask) B(bob) C(bg) D(dest) +;; - - - - +;; 0 0 0 0 +;; 0 0 1 1 +;; 0 1 0 0 +;; 0 1 1 1 +;; 1 0 0 0 +;; 1 0 1 0 +;; 1 1 0 1 +;; 1 1 1 1 +;; read D column from bottom up = 11001010 = $ca +;; this is used in the LF? bits +BLIT_LF_MINTERM equ $ca +BLIT_A_SOURCE_SHIFT equ 8 ; number of pixels from BOB_XPOS to move the bob right +BLIT_B_SOURCE_SHIFT equ 8 ; number of pixels from BOB_XPOS to move the bob right +BLIT_DEST equ $100 +BLIT_SRCC equ $200 +BLIT_SRCB equ $400 +BLIT_SRCA equ $800 +BLIT_ASHIFTSHIFT equ 12 ;Bit index of ASH? bits +BLIT_BLTCON1 equ BLIT_B_SOURCE_SHIFT<