mirror of https://github.com/nmlgc/ReC98.git
113 lines
3.1 KiB
C++
113 lines
3.1 KiB
C++
#include "th01/sprites/ileave_m.hpp"
|
||
#include "th01/hardware/palette.h"
|
||
#include "th01/hardware/ptrans.hpp"
|
||
|
||
// Combines the pixels from both VRAM pages in the 8×8 square starting at
|
||
// (⌊left/8⌋*8, top), using one of the interlace masks. The resulting square
|
||
// is blitted to VRAM page 0.
|
||
void graph_interleave_pages_8x8_8(screen_x_t left, vram_y_t top, int mask_id)
|
||
{
|
||
const interleave_masks_t masks = sINTERLEAVE_MASKS;
|
||
|
||
vram_offset_t vram_offset = vram_offset_divmul(left, top);
|
||
dots8_t dots;
|
||
for(char y = 0; y < INTERLEAVE_H; y++) {
|
||
#define mask masks.dots[mask_id][y]
|
||
|
||
#define snap(plane, vram_offset) \
|
||
VRAM_CHUNK(plane, vram_offset, 8)
|
||
|
||
#define interleave(plane, vram_offset) \
|
||
graph_accesspage_func(1); dots = ~mask & snap(plane, vram_offset); \
|
||
graph_accesspage_func(0); dots |= mask & snap(plane, vram_offset); \
|
||
graph_accesspage_func(0); VRAM_PUT(plane, vram_offset, dots, 8);
|
||
|
||
interleave(B, vram_offset);
|
||
interleave(R, vram_offset);
|
||
interleave(G, vram_offset);
|
||
interleave(E, vram_offset);
|
||
vram_offset += ROW_SIZE;
|
||
|
||
#undef interleave
|
||
#undef snap
|
||
#undef mask
|
||
}
|
||
}
|
||
|
||
void pagetrans_diagonal_8x8(unsigned int step_ms)
|
||
{
|
||
pagetrans_diagonal_8x8_with_palette(step_ms, z_Palettes, z_Palettes);
|
||
}
|
||
|
||
static const int FRAME_COUNT = (
|
||
(RES_X / INTERLEAVE_W) + (RES_Y / INTERLEAVE_H)
|
||
);
|
||
|
||
void pagetrans_diagonal_8x8_with_palette(
|
||
unsigned int step_ms, Palette4 &pal_cur, const Palette4 &pal_target
|
||
)
|
||
{
|
||
int comp;
|
||
int col;
|
||
screen_x_t from_topleft_left = 0;
|
||
vram_y_t from_topleft_top = 0;
|
||
screen_x_t from_bottomright_left = (RES_X - INTERLEAVE_W);
|
||
vram_y_t from_bottomright_top = (RES_Y - INTERLEAVE_H);
|
||
screen_x_t tip_left;
|
||
vram_y_t tip_top;
|
||
|
||
for(int frame = 0; frame < FRAME_COUNT; frame++) {
|
||
tip_left = from_topleft_left;
|
||
tip_top = from_topleft_top;
|
||
while((from_topleft_left >= 0) && (from_topleft_top <= (RES_Y - 1))) {
|
||
graph_interleave_pages_8x8_8(
|
||
from_topleft_left, from_topleft_top, 1
|
||
);
|
||
from_topleft_left -= INTERLEAVE_W;
|
||
from_topleft_top += INTERLEAVE_H;
|
||
}
|
||
|
||
from_topleft_left = (tip_left < (RES_X - INTERLEAVE_W))
|
||
? (tip_left + INTERLEAVE_W)
|
||
: tip_left;
|
||
from_topleft_top = (tip_left < (RES_X - INTERLEAVE_W))
|
||
? 0
|
||
: (tip_top + INTERLEAVE_H);
|
||
|
||
if((frame % (FRAME_COUNT / COLOR_COUNT)) == 0) {
|
||
// Not identical to the ramping loop in z_palette_fade_from()!
|
||
palette_foreach(col, comp, {
|
||
if(pal_cur[col].v[comp] != pal_target[col].v[comp]) {
|
||
pal_cur.colors[col].v[comp] +=
|
||
(pal_cur[col].v[comp] > pal_target[col].v[comp])
|
||
? -1
|
||
: 1;
|
||
}
|
||
});
|
||
z_palette_set_all_show(pal_cur);
|
||
}
|
||
|
||
tip_left = from_bottomright_left;
|
||
tip_top = from_bottomright_top;
|
||
while(
|
||
(from_bottomright_left >= 0) &&
|
||
(from_bottomright_top <= (RES_Y - 1))
|
||
) {
|
||
graph_interleave_pages_8x8_8(
|
||
from_bottomright_left, from_bottomright_top, 2
|
||
);
|
||
from_bottomright_left -= INTERLEAVE_W;
|
||
from_bottomright_top += INTERLEAVE_H;
|
||
}
|
||
|
||
from_bottomright_left = (tip_top > 0)
|
||
? (RES_X - INTERLEAVE_W)
|
||
: (tip_left - INTERLEAVE_W);
|
||
from_bottomright_top = (tip_top > 0)
|
||
? (tip_top - INTERLEAVE_H)
|
||
: tip_top;
|
||
|
||
delay(step_ms);
|
||
}
|
||
}
|