132 lines
		
	
	
		
			2.2 KiB
		
	
	
	
		
			PHP
		
	
	
	
	
	
			
		
		
	
	
			132 lines
		
	
	
		
			2.2 KiB
		
	
	
	
		
			PHP
		
	
	
	
	
	
| CopyRange:
 | |
|   ; hl is source
 | |
|   ; de is destination
 | |
|   ; bc is length to copy
 | |
|   ld a, b 
 | |
|   or a, c
 | |
|   ret z
 | |
| .loop
 | |
|   ld a, [hl+]
 | |
|   ld [de], a
 | |
|   inc de
 | |
|   dec bc
 | |
|   ld a, b
 | |
|   or a, c ; check if bc is zero
 | |
|   jr nz, .loop
 | |
|   
 | |
|   ret
 | |
| 
 | |
| CopyRangeBy8s:
 | |
|   ; hl is source
 | |
|   ; de is destination
 | |
|   ; bc is length to copy
 | |
|   ld a, b 
 | |
|   or a, c
 | |
|   ret z
 | |
| .loop
 | |
|   rept 8
 | |
|     ld a, [hl+]
 | |
|     ld [de], a
 | |
|     inc de
 | |
|     dec bc
 | |
|   endr
 | |
|   ld a, b
 | |
|   or a, c ; check if bc is zero
 | |
|   jr nz, .loop
 | |
|   
 | |
|   ret
 | |
| 
 | |
| CopyOneTileData:
 | |
|   di
 | |
|   rept 16
 | |
|     ld a, [hl+]
 | |
|     ld [de], a 
 | |
|     inc de
 | |
|   endr
 | |
|   reti
 | |
| 
 | |
| CopyRangeOfTilesButRotated:
 | |
|   ld a, b
 | |
|   or a, c
 | |
|   ret z
 | |
| .loop
 | |
|   push bc ; save bc so we can use it in the loop
 | |
|   
 | |
|   ; add 15 to e, we're writing to the destination in reverse order
 | |
|   ld a, e
 | |
|   add a, 16
 | |
|   ld e, a 
 | |
|   ld a, d
 | |
|   adc a, 0
 | |
|   ld d, a 
 | |
|   
 | |
|   rept 8 ; copy 8 tiles
 | |
|     dec de
 | |
|     dec de ; step back two bytes (one tile) 
 | |
|     
 | |
|     
 | |
|     ; copy half the tile (one byte)
 | |
|     ld a, [hl+]
 | |
|     call ReverseBits ; reverse the order of a
 | |
|     ld [de], a 
 | |
|     inc de ; step forward because we want to preserve the order of each pair
 | |
|     
 | |
|     ; copy the second half of the tile (one byte)
 | |
|     ld a, [hl+]
 | |
|     call ReverseBits
 | |
|     ld [de], a 
 | |
|     dec de ; step backwards to be ready for the next pair
 | |
|     
 | |
|   endr
 | |
|   
 | |
|   pop bc ; restore bc to be the count to copy, and decrement it by 16
 | |
|   ld a, c 
 | |
|   sub a, 16
 | |
|   ld c, a 
 | |
|   ld a, b 
 | |
|   sbc a, 0
 | |
|   ld b, a 
 | |
|   
 | |
|   ; add 16 to properly increment the destination to be for the next tile
 | |
|   ld a, e 
 | |
|   add a, 16
 | |
|   ld e, a 
 | |
|   ld a, d 
 | |
|   adc a, 0
 | |
|   ld d, a 
 | |
|   
 | |
|   ld a, b
 | |
|   or a, c
 | |
|   jp nz, .loop
 | |
|   
 | |
|   ret
 | |
|   
 | |
| ReverseBits: ; overwrites bc and a, and reverses the bits of a. thanks to https://stackoverflow.com/a/2602885 for the algo 
 | |
|   swap a ; swap high nibble with low nibble
 | |
|   
 | |
|   ; swap 0b11001100 with 0b00110011
 | |
|   ld b, a 
 | |
|   and a, 0b11001100 ; select upper half of nibbles
 | |
|   srl a ; swap the upper half to the lower half
 | |
|   srl a
 | |
|   ld c, a ; c now holds the upper half and lower half swapped
 | |
|   ld a, b ; get back the whole byte
 | |
|   and a, 0b00110011 ; select lower halves of nibbles
 | |
|   sla a 
 | |
|   sla a ; swap the lower half to the upper half
 | |
|   or a, c 
 | |
|   
 | |
|   ; swap 0b10101010 with 0b01010101
 | |
|   ld b, a 
 | |
|   and a, 0b10101010
 | |
|   srl a 
 | |
|   ld c, a 
 | |
|   ld a, b
 | |
|   and a, 0b01010101
 | |
|   sla a 
 | |
|   or a, c
 | |
|   
 | |
|   ret
 | |
|   
 | |
|  
 |