Author Topic: Any examples of how to shift pixel data before drawing it?  (Read 1169 times)

0 Members and 1 Guest are viewing this topic.

Offline endangermice

  • Supporter
  • CPC6128
  • *
  • Posts: 235
  • Country: gb
    • endangermice
  • Liked: 56
  • Likes Given: 14
In my previous Sprite routine, I used two copies of each sprite, a shifted one and an un-shifted one so I could move across the screen with pixel accuracy. Obviously needed two copies or each image in mode 0 isn't too much of a hassle but in mode 1, this goes up to 4 and eight in mode 2. If I'm animating the graphics too, I can see this quickly adding up to a lot of memory!


Kev (arnoldemu) mentioned that you can use a lookup table to calculate how to shift the data before drawing it. I've been looking around but can't find any obvious examples of how this can be done, clearly it's not a simple bit shift since that would mess with colour data etc.


Does anyone have an example of how to bit shift pixels for mode 0 (and maybe the other modes too)..?
For all the latest Starquake remake news check out my website - www.endangermice.co.uk

Offline arnoldemu

  • Supporter
  • 6128 Plus
  • *
  • Posts: 5.336
  • Country: gb
    • Unofficial Amstrad WWW Resource
  • Liked: 2278
  • Likes Given: 3478
You can do it without a table and this works for mode 0:

Code: [Select]

;; 2 bytes wide
;; a b c

draw_char_shifted:

dcsh1:
push bc
push hl


dcsw1:
push bc
;; ab
ld a,(de)
rrca
and &55
;; 0a
ld c,a

ld a,(hl)
and &aa
or c
ld (hl),a
inc hl

ld a,(de)
rlca
and &aa
ld c,a
ld a,(hl)
and &55
or c
ld (hl),a
inc de
pop bc
dec c
jr nz,dcsw1
pop hl
call scr_next_line
pop bc
djnz dcsh1

ret

the idea being rrca and rlca can be used to shift the pixels, you then have to mask and combine with previous values.

that's ok for all modes if you want a single pixel movement.

if you want more, you need lookup tables.

1 for mode 0,
3 for mode 1,
7 for mode 2.

so you can draw unshifted, or shifted.
I've got one somewhere for mode 1 that does it with the tables.
I'll dig it out.

problem is that shifted sprite drawing takes extra time, best is pre-shifted sprites if you have the ram free.
My games. My Games
My website with coding examples: Unofficial Amstrad WWW Resource

Offline endangermice

  • Supporter
  • CPC6128
  • *
  • Posts: 235
  • Country: gb
    • endangermice
  • Liked: 56
  • Likes Given: 14
That's great thank you once again!


I figured that drawing shifted shapes might take more time - as always with the power available everything is a trade-off. I assumed that games with quite a lot of animation frames e.g. Jet Set Willy might use shift tables since nothing else too complex is going on and there are a lot of shapes in that game which in Mode 1 equates to quite a lot more data which has to fit into 64K on the 464.


I shall study your routine and figure out how it works. I cannot overstate how useful this all is!!


 
For all the latest Starquake remake news check out my website - www.endangermice.co.uk

Offline Prodatron

  • 6128 Plus
  • ******
  • Posts: 833
  • Country: de
  • Back on the Z80
    • index.php?action=treasury
    • SymbOS SYmbiosis Multitasking Based Operating System
  • Liked: 1061
  • Likes Given: 556
if you want more, you need lookup tables.

1 for mode 0,
3 for mode 1,
7 for mode 2.

Using multiple RLCA/RRCA + self-modified JR-instructions, which jump to the correct RLCA/RRCA position, would be an alternative. But yes, lookup tables would be the fastest methode, as you save two AND instructions per byte and can rollup the X-loop.

CU,
Prodatron

GRAPHICAL Z80 MULTITASKING OPERATING SYSTEM

Offline endangermice

  • Supporter
  • CPC6128
  • *
  • Posts: 235
  • Country: gb
    • endangermice
  • Liked: 56
  • Likes Given: 14
Thanks for the responses guys, really helpful!


I had an epiphany earlier and realised that I actually can do animation and store all of the images without having to duplicate anything due to bit shifting. I realised that as long as my animation has a number of frames that is divisible by the number of shifts I have to do and in the case where the animation isn't long enough to move to a non shifted address I just extend it - I can actually not worry about programmatic shifting at all, just store my animation with some frames shifted and others not - hopefully this makes sense, I just need to ensure that the animation is exact and is only incremented when the sprite moves and everything should sync beautifully!


Right now it's time to learn the art of Pixel masking - some very promising examples on this site so I'm off to read and learn!
For all the latest Starquake remake news check out my website - www.endangermice.co.uk