commit
477dcb389d
87
src/tic.c
87
src/tic.c
|
@ -20,6 +20,7 @@
|
||||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
// SOFTWARE.
|
// SOFTWARE.
|
||||||
|
|
||||||
|
#include <assert.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
@ -154,7 +155,7 @@ static inline u8 mapColor(tic_mem* tic, u8 color)
|
||||||
|
|
||||||
static void setPixelDma(tic_mem* tic, s32 x, s32 y, u8 color)
|
static void setPixelDma(tic_mem* tic, s32 x, s32 y, u8 color)
|
||||||
{
|
{
|
||||||
tic_tool_poke4(tic->ram.vram.screen.data, y * TIC80_WIDTH + x, mapColor(tic, color));
|
tic_tool_poke4(tic->ram.vram.screen.data, y * TIC80_WIDTH + x, color);
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline u32* getOvrAddr(tic_mem* tic, s32 x, s32 y)
|
static inline u32* getOvrAddr(tic_mem* tic, s32 x, s32 y)
|
||||||
|
@ -169,7 +170,7 @@ static void setPixelOvr(tic_mem* tic, s32 x, s32 y, u8 color)
|
||||||
{
|
{
|
||||||
tic_machine* machine = (tic_machine*)tic;
|
tic_machine* machine = (tic_machine*)tic;
|
||||||
|
|
||||||
*getOvrAddr(tic, x, y) = *(machine->state.ovr.palette + mapColor(tic, color));
|
*getOvrAddr(tic, x, y) = *(machine->state.ovr.palette + color);
|
||||||
}
|
}
|
||||||
|
|
||||||
static u8 getPixelOvr(tic_mem* tic, s32 x, s32 y)
|
static u8 getPixelOvr(tic_mem* tic, s32 x, s32 y)
|
||||||
|
@ -197,7 +198,7 @@ static void setPixel(tic_machine* machine, s32 x, s32 y, u8 color)
|
||||||
{
|
{
|
||||||
if(x < machine->state.clip.l || y < machine->state.clip.t || x >= machine->state.clip.r || y >= machine->state.clip.b) return;
|
if(x < machine->state.clip.l || y < machine->state.clip.t || x >= machine->state.clip.r || y >= machine->state.clip.b) return;
|
||||||
|
|
||||||
machine->state.setpix(&machine->memory, x, y, color);
|
machine->state.setpix(&machine->memory, x, y, mapColor(&machine->memory, color));
|
||||||
}
|
}
|
||||||
|
|
||||||
static u8 getPixel(tic_machine* machine, s32 x, s32 y)
|
static u8 getPixel(tic_machine* machine, s32 x, s32 y)
|
||||||
|
@ -244,61 +245,73 @@ static void drawRectBorder(tic_machine* machine, s32 x, s32 y, s32 width, s32 he
|
||||||
drawVLine(machine, x + width - 1, y, height, color);
|
drawVLine(machine, x + width - 1, y, height, color);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define DRAW_TILE_BODY(INDEX_EXPR) ({\
|
||||||
|
for(s32 py=sy; py < ey; py++, y++) \
|
||||||
|
{ \
|
||||||
|
s32 xx = x; \
|
||||||
|
for(s32 px=sx; px < ex; px++, xx++) \
|
||||||
|
{ \
|
||||||
|
u8 color = mapping[tic_tool_peek4(buffer, INDEX_EXPR)]; \
|
||||||
|
if(color != 255) machine->state.setpix(&machine->memory, xx, y, color); \
|
||||||
|
} \
|
||||||
|
} \
|
||||||
|
})
|
||||||
|
|
||||||
|
#define REVERT(X) (TIC_SPRITESIZE - 1 - (X))
|
||||||
|
#define INDEX_XY(X, Y) ((Y) * TIC_SPRITESIZE + (X))
|
||||||
|
|
||||||
static void drawTile(tic_machine* machine, const tic_tile* buffer, s32 x, s32 y, u8* colors, s32 count, s32 scale, tic_flip flip, tic_rotate rotate)
|
static void drawTile(tic_machine* machine, const tic_tile* buffer, s32 x, s32 y, u8* colors, s32 count, s32 scale, tic_flip flip, tic_rotate rotate)
|
||||||
{
|
{
|
||||||
static u8 transparent[TIC_PALETTE_SIZE];
|
static u8 mapping[TIC_PALETTE_SIZE];
|
||||||
memset(transparent, 0, sizeof(transparent));
|
for (s32 i = 0; i < TIC_PALETTE_SIZE; i++) mapping[i] = tic_tool_peek4(machine->memory.ram.vram.mapping, i);
|
||||||
for (s32 i = 0; i < count; i++) transparent[colors[i]] = 1;
|
for (s32 i = 0; i < count; i++) mapping[colors[i]] = 255;
|
||||||
|
|
||||||
flip &= 0b11;
|
|
||||||
rotate &= 0b11;
|
rotate &= 0b11;
|
||||||
|
u32 orientation = flip & 0b11;
|
||||||
|
|
||||||
if (flip == 0 && rotate == 0 && scale == 1) {
|
if(rotate == tic_90_rotate) orientation ^= 0b001;
|
||||||
|
else if(rotate == tic_180_rotate) orientation ^= 0b011;
|
||||||
|
else if(rotate == tic_270_rotate) orientation ^= 0b010;
|
||||||
|
if (rotate == tic_90_rotate || rotate == tic_270_rotate) orientation |= 0b100;
|
||||||
|
|
||||||
|
if (scale == 1) {
|
||||||
// the most common path
|
// the most common path
|
||||||
s32 i = 0;
|
s32 sx, sy, ex, ey;
|
||||||
for(s32 py=0; py < TIC_SPRITESIZE; py++, y++)
|
sx = machine->state.clip.l - x; if (sx < 0) sx = 0;
|
||||||
{
|
sy = machine->state.clip.t - y; if (sy < 0) sy = 0;
|
||||||
s32 xx = x;
|
ex = machine->state.clip.r - x; if (ex > TIC_SPRITESIZE) ex = TIC_SPRITESIZE;
|
||||||
for(s32 px=0; px < TIC_SPRITESIZE; px++, xx++)
|
ey = machine->state.clip.b - y; if (ey > TIC_SPRITESIZE) ey = TIC_SPRITESIZE;
|
||||||
{
|
y += sy;
|
||||||
u8 color = tic_tool_peek4(buffer, i++);
|
x += sx;
|
||||||
if(!transparent[color]) setPixel(machine, xx, y, color);
|
switch (orientation) {
|
||||||
}
|
case 0b100: DRAW_TILE_BODY(INDEX_XY(py, px)); break;
|
||||||
|
case 0b110: DRAW_TILE_BODY(INDEX_XY(REVERT(py), px)); break;
|
||||||
|
case 0b101: DRAW_TILE_BODY(INDEX_XY(py, REVERT(px))); break;
|
||||||
|
case 0b111: DRAW_TILE_BODY(INDEX_XY(REVERT(py), REVERT(px))); break;
|
||||||
|
case 0b000: DRAW_TILE_BODY(INDEX_XY(px, py)); break;
|
||||||
|
case 0b010: DRAW_TILE_BODY(INDEX_XY(px, REVERT(py))); break;
|
||||||
|
case 0b001: DRAW_TILE_BODY(INDEX_XY(REVERT(px), py)); break;
|
||||||
|
case 0b011: DRAW_TILE_BODY(INDEX_XY(REVERT(px), REVERT(py))); break;
|
||||||
|
default: assert(!"Unknown value of orientation in drawTile");
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
s32 a = flip & tic_horz_flip ? -1 : 1;
|
|
||||||
s32 b = flip & tic_vert_flip ? -1 : 1;
|
|
||||||
|
|
||||||
if(rotate == tic_90_rotate) a = -a;
|
|
||||||
else if(rotate == tic_180_rotate) a = -a, b = -b;
|
|
||||||
else if(rotate == tic_270_rotate) b = -b;
|
|
||||||
|
|
||||||
bool swap_axis = (rotate == tic_90_rotate || rotate == tic_270_rotate);
|
|
||||||
|
|
||||||
for(s32 py=0; py < TIC_SPRITESIZE; py++, y+=scale)
|
for(s32 py=0; py < TIC_SPRITESIZE; py++, y+=scale)
|
||||||
{
|
{
|
||||||
s32 xx = x;
|
s32 xx = x;
|
||||||
for(s32 px=0; px < TIC_SPRITESIZE; px++, xx+=scale)
|
for(s32 px=0; px < TIC_SPRITESIZE; px++, xx+=scale)
|
||||||
{
|
{
|
||||||
s32 i;
|
s32 i;
|
||||||
s32 ix, iy;
|
s32 ix = orientation & 0b001 ? TIC_SPRITESIZE - px - 1: px;
|
||||||
ix = a == 1 ? px : TIC_SPRITESIZE - px - 1;
|
s32 iy = orientation & 0b010 ? TIC_SPRITESIZE - py - 1: py;
|
||||||
iy = b == 1 ? py : TIC_SPRITESIZE - py - 1;
|
if(orientation & 0b100) {
|
||||||
if(swap_axis) {
|
|
||||||
i = ix * TIC_SPRITESIZE + iy;
|
i = ix * TIC_SPRITESIZE + iy;
|
||||||
} else {
|
} else {
|
||||||
i = iy * TIC_SPRITESIZE + ix;
|
i = iy * TIC_SPRITESIZE + ix;
|
||||||
}
|
}
|
||||||
u8 color = tic_tool_peek4(buffer, i);
|
u8 color = tic_tool_peek4(buffer, i);
|
||||||
if(!transparent[color]) {
|
if(mapping[color] != 255) drawRect(machine, xx, y, scale, scale, color);
|
||||||
if (scale == 1) {
|
|
||||||
setPixel(machine, xx, y, color);
|
|
||||||
} else {
|
|
||||||
drawRect(machine, xx, y, scale, scale, color);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue