Skip to content

Space Harrier II graphics compression #27

@DevsArchive

Description

@DevsArchive

Space Harrier 2 has an interesting, but simple graphics compression algorithm.

It has a 32 byte decompression buffer for holding decompressed tile data. For each tile, it'll use a list of bitfields that describe the places in the decompression buffer to copy a field's corresponding byte into. It is then finished off with a string of bytes that then fill up the rest of the unwritten to spots. The buffer is then copied to VRAM and it loops. It does this until it hits a termination flag.

; ---------------------------------------------------------------------------
; Space Harrier II graphics decompression
; VDP write command should be set before calling this
; ---------------------------------------------------------------------------
; PARAMETERS:
;	a0.l - Pointer to compressed art
; ---------------------------------------------------------------------------

SH2GfxDecomp:
		lea	$FFF2C0.w,a3		; Decompression buffer
		moveq	#0,d0			; Buffer write flags

		moveq	#0,d2			; Get number of bitfield copies for this tile
		move.b	(a0)+,d2
		beq.w	.CopyRest		; If there are none, branch
		bmi.w	.End			; If this is the end of the compressed data, branch
		subq.w	#1,d2			; Subtract 1 for dbf

; ---------------------------------------------------------------------------

.GetCopyPattern:
		lea	$FFF2C0.w,a2		; Decompression buffer
		movea.l a2,a3

		move.b	(a0)+,d3		; Get byte to copy
		move.b	(a0)+,d4		; Get copy pattern
		lsl.w	#8,d4
		move.b	(a0)+,d4
		lsl.l	#8,d4
		move.b	(a0)+,d4
		lsl.l	#8,d4
		move.b	(a0)+,d4
		or.l	 d4,d0			; Mark spots in pattern as written to

		moveq	#32-1,d7		; Start checking which places in buffer to copy byte into

.CopyByteLoop:
		lsl.l	#1,d4			; Shift copy pattern and get MSB
		bcc.w	.AdvanceCopy		; If the byte shouldn't be written to this spot, branch
		move.b	d3,(a2)			; If it should, write it

.AdvanceCopy:
		addq.l	#1,a2			; Go to next byte in buffer
		dbf	d7,.CopyByteLoop	; Loop until the whole copy pattern is scanned
		dbf	d2,.GetCopyPattern	; Loop until all copy patterns are scanned for this tile

; ---------------------------------------------------------------------------

		moveq	#$FFFFFFFF,d1		; Is the whole buffer filled up?
		eor.l	d0,d1
		beq.w	.CopyToVRAM		; If so, branch

.CopyRest:
		moveq	#32-1,d7		; Start copying the rest of the tile data

.CopyRestLoop:
		lsl.l	#1,d0			; Shift remaining pattern and get MSB
		bcs.w	.AdvanceRest		; If the next byte shouldn't be written to this spot, branch
		move.b	(a0)+,(a3)		; Copy byte and advance

.AdvanceRest:
		addq.l	#1,a3			; Go to next byte in buffer
		dbf	d7,.CopyRestLoop	; Loop until the rest of the buffer is filled up

; ---------------------------------------------------------------------------

.CopyToVRAM:
		lea	$FFF2C0.w,a6		; Copy buffer to VRAM
		lea	$C00000,a5
		move.l	(a6)+,(a5)
		move.l	(a6)+,(a5)
		move.l	(a6)+,(a5)
		move.l	(a6)+,(a5)
		move.l	(a6)+,(a5)
		move.l	(a6)+,(a5)
		move.l	(a6)+,(a5)
		move.l	(a6)+,(a5)

		bra.s	SH2GfxDecomp		; Loop back to start for next tile

.End:
		rts

Metadata

Metadata

Assignees

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions