#include "accelerant.h"
#include "3dfx.h"
static const uint32 fmtColorDepth[] = {
0x10000,
0x30000,
0x50000,
0x50000
};
void
TDFX_FillRectangle(engine_token* et, uint32 color, fill_rect_params* list,
uint32 count)
{
(void)et;
DisplayModeEx& mode = gInfo.sharedInfo->displayMode;
uint32 fmt = mode.bytesPerRow | fmtColorDepth[mode.bytesPerPixel - 1];
TDFX_WaitForFifo(3);
OUTREG32(DST_FORMAT, fmt);
OUTREG32(COLOR_BACK, color);
OUTREG32(COLOR_FORE, color);
while (count--) {
int x = list->left;
int y = list->top;
int w = list->right - x + 1;
int h = list->bottom - y + 1;
TDFX_WaitForFifo(3);
OUTREG32(DST_SIZE, w | (h << 16));
OUTREG32(DST_XY, x | (y << 16));
OUTREG32(CMD_2D, RECTANGLE_FILL | CMD_2D_GO | (ROP_COPY << 24));
list++;
}
}
void
TDFX_FillSpan(engine_token* et, uint32 color, uint16* list, uint32 count)
{
(void)et;
DisplayModeEx& mode = gInfo.sharedInfo->displayMode;
uint32 fmt = mode.bytesPerRow | fmtColorDepth[mode.bytesPerPixel - 1];
TDFX_WaitForFifo(3);
OUTREG32(DST_FORMAT, fmt);
OUTREG32(COLOR_BACK, color);
OUTREG32(COLOR_FORE, color);
while (count--) {
int y = *list++;
int x = *list++;
int w = *list++ - x + 1;
if (w <= 0)
continue;
TDFX_WaitForFifo(3);
OUTREG32(DST_SIZE, w | (1 << 16));
OUTREG32(DST_XY, x | (y << 16));
OUTREG32(CMD_2D, RECTANGLE_FILL | CMD_2D_GO | (ROP_COPY << 24));
}
}
void
TDFX_InvertRectangle(engine_token* et, fill_rect_params* list, uint32 count)
{
(void)et;
DisplayModeEx& mode = gInfo.sharedInfo->displayMode;
uint32 fmt = mode.bytesPerRow | fmtColorDepth[mode.bytesPerPixel - 1];
TDFX_WaitForFifo(1);
OUTREG32(DST_FORMAT, fmt);
while (count--) {
int x = list->left;
int y = list->top;
int w = list->right - x + 1;
int h = list->bottom - y + 1;
TDFX_WaitForFifo(3);
OUTREG32(DST_SIZE, w | (h << 16));
OUTREG32(DST_XY, x | (y << 16));
OUTREG32(CMD_2D, RECTANGLE_FILL | CMD_2D_GO | (ROP_INVERT << 24));
list++;
}
}
void
TDFX_ScreenToScreenBlit(engine_token* et, blit_params* list, uint32 count)
{
(void)et;
DisplayModeEx& mode = gInfo.sharedInfo->displayMode;
uint32 fmt = mode.bytesPerRow | fmtColorDepth[mode.bytesPerPixel - 1];
TDFX_WaitForFifo(2);
OUTREG32(DST_FORMAT, fmt);
OUTREG32(SRC_FORMAT, fmt);
while (count--) {
int src_x = list->src_left;
int src_y = list->src_top;
int dest_x = list->dest_left;
int dest_y = list->dest_top;
int width = list->width;
int height = list->height;
uint32 cmd = SCRN_TO_SCRN_BLIT | CMD_2D_GO | (ROP_COPY << 24);
if (src_x <= dest_x) {
cmd |= X_RIGHT_TO_LEFT;
src_x += width;
dest_x += width;
}
if (src_y <= dest_y) {
cmd |= Y_BOTTOM_TO_TOP;
src_y += height;
dest_y += height;
}
TDFX_WaitForFifo(4);
OUTREG32(SRC_XY, src_x | (src_y << 16));
OUTREG32(DST_SIZE, (width + 1) | ((height + 1) << 16));
OUTREG32(DST_XY, dest_x | (dest_y << 16));
OUTREG32(CMD_2D, cmd);
list++;
}
}