mirror of
https://github.com/libretro/RetroArch
synced 2024-12-28 09:29:16 +00:00
(PSP) split up video frame in smaller tiles for faster rendering.
This commit is contained in:
parent
4ae95e98c8
commit
5d3bd08b9d
@ -61,9 +61,8 @@
|
|||||||
|
|
||||||
typedef struct __attribute__((packed)) psp1_vertex
|
typedef struct __attribute__((packed)) psp1_vertex
|
||||||
{
|
{
|
||||||
int16_t u,v;
|
float u,v;
|
||||||
uint16_t color;
|
float x,y,z;
|
||||||
int16_t x,y,z;
|
|
||||||
|
|
||||||
} psp1_vertex_t;
|
} psp1_vertex_t;
|
||||||
|
|
||||||
@ -78,7 +77,7 @@ typedef struct psp1_menu_frame
|
|||||||
{
|
{
|
||||||
void* dList;
|
void* dList;
|
||||||
void* frame;
|
void* frame;
|
||||||
psp1_sprite_t* frame_coords;
|
psp1_sprite_t* frame_coords;
|
||||||
|
|
||||||
bool active;
|
bool active;
|
||||||
|
|
||||||
@ -112,6 +111,67 @@ typedef struct psp1_video
|
|||||||
|
|
||||||
} psp1_video_t;
|
} psp1_video_t;
|
||||||
|
|
||||||
|
// both row and column count need to be a power of 2
|
||||||
|
#define PSP_FRAME_ROWS_COUNT 4
|
||||||
|
#define PSP_FRAME_COLUMNS_COUNT 16
|
||||||
|
#define PSP_FRAME_SLICE_COUNT (PSP_FRAME_ROWS_COUNT * PSP_FRAME_COLUMNS_COUNT)
|
||||||
|
#define PSP_FRAME_VERTEX_COUNT (PSP_FRAME_SLICE_COUNT * 2)
|
||||||
|
|
||||||
|
static inline void psp_set_screen_coords (psp1_sprite_t* framecoords, int x, int y, int width, int height)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
int current_column = 0;
|
||||||
|
|
||||||
|
float x0 = x;
|
||||||
|
float y0 = y;
|
||||||
|
float step_x = ((float) width) / PSP_FRAME_COLUMNS_COUNT;
|
||||||
|
float step_y = ((float) height) / PSP_FRAME_ROWS_COUNT;
|
||||||
|
|
||||||
|
for (i=0; i < PSP_FRAME_SLICE_COUNT; i++)
|
||||||
|
{
|
||||||
|
framecoords[i].v0.x = x0;
|
||||||
|
framecoords[i].v0.y = y0;
|
||||||
|
|
||||||
|
x0 += step_x;
|
||||||
|
|
||||||
|
framecoords[i].v1.x = x0;
|
||||||
|
framecoords[i].v1.y = y0 + step_y;
|
||||||
|
|
||||||
|
if (++current_column == PSP_FRAME_COLUMNS_COUNT)
|
||||||
|
{
|
||||||
|
x0 = x;
|
||||||
|
y0 += step_y;
|
||||||
|
current_column = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void psp_set_tex_coords (psp1_sprite_t* framecoords, int width, int height)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
int current_column = 0;
|
||||||
|
|
||||||
|
float u0 = 0;
|
||||||
|
float v0 = 0;
|
||||||
|
float step_u = ((float) width) / PSP_FRAME_COLUMNS_COUNT;
|
||||||
|
float step_v = ((float) height) / PSP_FRAME_ROWS_COUNT;
|
||||||
|
|
||||||
|
for (i=0; i < PSP_FRAME_SLICE_COUNT; i++)
|
||||||
|
{
|
||||||
|
framecoords[i].v0.u = u0;
|
||||||
|
framecoords[i].v0.v = v0;
|
||||||
|
u0+=step_u;
|
||||||
|
framecoords[i].v1.u = u0;
|
||||||
|
framecoords[i].v1.v = v0 + step_v;
|
||||||
|
|
||||||
|
if (++current_column == PSP_FRAME_COLUMNS_COUNT)
|
||||||
|
{
|
||||||
|
u0 = 0;
|
||||||
|
v0 += step_v;
|
||||||
|
current_column = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
static void psp_update_frame_coords(psp1_video_t* psp);
|
static void psp_update_frame_coords(psp1_video_t* psp);
|
||||||
static void psp_update_viewport(psp1_video_t* psp);
|
static void psp_update_viewport(psp1_video_t* psp);
|
||||||
|
|
||||||
@ -150,11 +210,11 @@ static void *psp_init(const video_info_t *video,
|
|||||||
psp->frame_dList = memalign(64, 256);
|
psp->frame_dList = memalign(64, 256);
|
||||||
psp->menu.dList = memalign(64, 256);
|
psp->menu.dList = memalign(64, 256);
|
||||||
psp->menu.frame = memalign(16, 2 * 480 * 272);
|
psp->menu.frame = memalign(16, 2 * 480 * 272);
|
||||||
psp->frame_coords = memalign(64, 16 * sizeof(psp1_sprite_t));
|
psp->frame_coords = memalign(64, (((PSP_FRAME_SLICE_COUNT * sizeof(psp1_sprite_t)) + 63) & ~63));
|
||||||
psp->menu.frame_coords = memalign(64, 16 * sizeof(psp1_sprite_t));
|
psp->menu.frame_coords = memalign(64, (((PSP_FRAME_SLICE_COUNT * sizeof(psp1_sprite_t)) + 63) & ~63));
|
||||||
|
|
||||||
memset(psp->frame_coords , 0, 16 * sizeof(psp1_sprite_t));
|
memset(psp->frame_coords , 0, PSP_FRAME_SLICE_COUNT * sizeof(psp1_sprite_t));
|
||||||
memset(psp->menu.frame_coords , 0, 16 * sizeof(psp1_sprite_t));
|
memset(psp->menu.frame_coords , 0, PSP_FRAME_SLICE_COUNT * sizeof(psp1_sprite_t));
|
||||||
sceKernelDcacheWritebackInvalidateAll();
|
sceKernelDcacheWritebackInvalidateAll();
|
||||||
psp->frame_coords = TO_UNCACHED_PTR(psp->frame_coords);
|
psp->frame_coords = TO_UNCACHED_PTR(psp->frame_coords);
|
||||||
psp->menu.frame_coords = TO_UNCACHED_PTR(psp->menu.frame_coords);;
|
psp->menu.frame_coords = TO_UNCACHED_PTR(psp->menu.frame_coords);;
|
||||||
@ -263,7 +323,7 @@ static void *psp_init(const video_info_t *video,
|
|||||||
sceGuEnable(GU_BLEND);
|
sceGuEnable(GU_BLEND);
|
||||||
|
|
||||||
sceGuBlendFunc(GU_ADD, GU_FIX, GU_FIX, 0x0000FF00, 0xFFFFFFFF); // green only
|
sceGuBlendFunc(GU_ADD, GU_FIX, GU_FIX, 0x0000FF00, 0xFFFFFFFF); // green only
|
||||||
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_16BIT | GU_COLOR_4444 | GU_VERTEX_16BIT | GU_TRANSFORM_2D, 2, NULL, (void*)(psp->frame_coords));
|
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_32BITF | GU_VERTEX_32BITF | GU_TRANSFORM_2D, PSP_FRAME_VERTEX_COUNT, NULL, (void*)(psp->frame_coords));
|
||||||
sceGuBlendFunc(GU_ADD, GU_FIX, GU_FIX, 0xFFFFFFFF, 0xFFFFFFFF); // restore
|
sceGuBlendFunc(GU_ADD, GU_FIX, GU_FIX, 0xFFFFFFFF, 0xFFFFFFFF); // restore
|
||||||
|
|
||||||
sceGuTexMode(lut_pixel_format, 0, 0, GU_FALSE);
|
sceGuTexMode(lut_pixel_format, 0, 0, GU_FALSE);
|
||||||
@ -271,11 +331,11 @@ static void *psp_init(const video_info_t *video,
|
|||||||
sceGuClutMode(pixel_format, red_shift, color_mask, 0);
|
sceGuClutMode(pixel_format, red_shift, color_mask, 0);
|
||||||
sceGuClutLoad(lut_block_count, LUT_r);
|
sceGuClutLoad(lut_block_count, LUT_r);
|
||||||
|
|
||||||
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_16BIT | GU_COLOR_4444 | GU_VERTEX_16BIT | GU_TRANSFORM_2D, 2, NULL, (void*)(psp->frame_coords));
|
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_32BITF | GU_VERTEX_32BITF | GU_TRANSFORM_2D, PSP_FRAME_VERTEX_COUNT, NULL, (void*)(psp->frame_coords));
|
||||||
|
|
||||||
sceGuClutMode(pixel_format, 0, color_mask, 0);
|
sceGuClutMode(pixel_format, 0, color_mask, 0);
|
||||||
sceGuClutLoad(lut_block_count, LUT_b);
|
sceGuClutLoad(lut_block_count, LUT_b);
|
||||||
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_16BIT | GU_COLOR_4444 | GU_VERTEX_16BIT | GU_TRANSFORM_2D, 2, NULL, (void*)(psp->frame_coords));
|
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_32BITF | GU_VERTEX_32BITF | GU_TRANSFORM_2D, PSP_FRAME_VERTEX_COUNT, NULL, (void*)(psp->frame_coords));
|
||||||
|
|
||||||
sceGuFinish();
|
sceGuFinish();
|
||||||
|
|
||||||
@ -347,10 +407,6 @@ static bool psp_frame(void *data, const void *frame,
|
|||||||
|
|
||||||
psp->vblank_not_reached = true;
|
psp->vblank_not_reached = true;
|
||||||
|
|
||||||
RARCH_PERFORMANCE_INIT(psp_frame_run);
|
|
||||||
RARCH_PERFORMANCE_START(psp_frame_run);
|
|
||||||
|
|
||||||
|
|
||||||
#ifdef DISPLAY_FPS
|
#ifdef DISPLAY_FPS
|
||||||
frames++;
|
frames++;
|
||||||
sceRtcGetCurrentTick(¤tTick);
|
sceRtcGetCurrentTick(¤tTick);
|
||||||
@ -369,14 +425,14 @@ static bool psp_frame(void *data, const void *frame,
|
|||||||
psp->draw_buffer = FROM_GU_POINTER(sceGuSwapBuffers());
|
psp->draw_buffer = FROM_GU_POINTER(sceGuSwapBuffers());
|
||||||
g_extern.frame_count++;
|
g_extern.frame_count++;
|
||||||
|
|
||||||
|
|
||||||
|
RARCH_PERFORMANCE_INIT(psp_frame_run);
|
||||||
|
RARCH_PERFORMANCE_START(psp_frame_run);
|
||||||
|
|
||||||
if (psp->should_resize)
|
if (psp->should_resize)
|
||||||
psp_update_viewport(psp);
|
psp_update_viewport(psp);
|
||||||
|
|
||||||
// psp->frame_coords->v0.u = 0;
|
psp_set_tex_coords(psp->frame_coords, width, height);
|
||||||
// psp->frame_coords->v0.v = 0;
|
|
||||||
|
|
||||||
psp->frame_coords->v1.u = width;
|
|
||||||
psp->frame_coords->v1.v = height;
|
|
||||||
|
|
||||||
sceGuStart(GU_DIRECT, psp->main_dList);
|
sceGuStart(GU_DIRECT, psp->main_dList);
|
||||||
|
|
||||||
@ -384,7 +440,7 @@ static bool psp_frame(void *data, const void *frame,
|
|||||||
sceGuClear(GU_COLOR_BUFFER_BIT);
|
sceGuClear(GU_COLOR_BUFFER_BIT);
|
||||||
|
|
||||||
if (psp->hw_render) // frame in VRAM ? texture/palette was set in core so draw directly
|
if (psp->hw_render) // frame in VRAM ? texture/palette was set in core so draw directly
|
||||||
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_16BIT | GU_COLOR_4444 | GU_VERTEX_16BIT | GU_TRANSFORM_2D, 2, NULL, (void*)(psp->frame_coords));
|
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_32BITF | GU_VERTEX_32BITF | GU_TRANSFORM_2D, PSP_FRAME_VERTEX_COUNT, NULL, (void*)(psp->frame_coords));
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (frame!=NULL)
|
if (frame!=NULL)
|
||||||
@ -470,34 +526,16 @@ static void psp_set_texture_frame(void *data, const void *frame, bool rgb32,
|
|||||||
rarch_assert((width*height) < (480 * 272)); // psp->menu.frame buffer size is (480 * 272)*2 Bytes
|
rarch_assert((width*height) < (480 * 272)); // psp->menu.frame buffer size is (480 * 272)*2 Bytes
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// rendering the menu frame as a single sprite is slow
|
psp_set_screen_coords(psp->menu.frame_coords, 0, 0, SCEGU_SCR_WIDTH, SCEGU_SCR_HEIGHT);
|
||||||
// so we render it as 16 vertical stripes instead
|
psp_set_tex_coords(psp->menu.frame_coords, width, height);
|
||||||
|
|
||||||
for (i=0;i<16;i++)
|
sceKernelDcacheWritebackRange(frame, width * height * 2);
|
||||||
{
|
|
||||||
psp->menu.frame_coords[i].v0.x = (i) * SCEGU_SCR_WIDTH / 16 ;
|
|
||||||
psp->menu.frame_coords[i].v1.x = (i+1) * SCEGU_SCR_WIDTH / 16 ;
|
|
||||||
|
|
||||||
//psp->menu.frame_coords[i].v0.y = 0;
|
|
||||||
psp->menu.frame_coords[i].v1.y = SCEGU_SCR_HEIGHT ;
|
|
||||||
|
|
||||||
|
|
||||||
psp->menu.frame_coords[i].v0.u = (i) * width / 16 ;
|
|
||||||
psp->menu.frame_coords[i].v1.u = (i+1) * width / 16 ;
|
|
||||||
|
|
||||||
//psp->menu.frame_coords[i].v0.v = 0;
|
|
||||||
psp->menu.frame_coords[i].v1.v = height;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
sceKernelDcacheWritebackRange(frame,width * height * 2);
|
|
||||||
|
|
||||||
sceGuStart(GU_DIRECT, psp->main_dList);
|
sceGuStart(GU_DIRECT, psp->main_dList);
|
||||||
sceGuCopyImage(GU_PSM_4444, 0, 0, width, height, width, (void*)frame, 0, 0, width, psp->menu.frame);
|
sceGuCopyImage(GU_PSM_4444, 0, 0, width, height, width, (void*)frame, 0, 0, width, psp->menu.frame);
|
||||||
sceGuFinish();
|
sceGuFinish();
|
||||||
|
|
||||||
sceGuStart(GU_SEND, psp->menu.dList);
|
sceGuStart(GU_SEND, psp->menu.dList);
|
||||||
sceGuTexSync();
|
|
||||||
sceGuTexMode(GU_PSM_4444, 0, 0, GU_FALSE);
|
sceGuTexMode(GU_PSM_4444, 0, 0, GU_FALSE);
|
||||||
sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGB);
|
sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGB);
|
||||||
sceGuTexFilter(GU_LINEAR, GU_LINEAR);
|
sceGuTexFilter(GU_LINEAR, GU_LINEAR);
|
||||||
@ -507,7 +545,7 @@ static void psp_set_texture_frame(void *data, const void *frame, bool rgb32,
|
|||||||
// sceGuBlendFunc(GU_ADD, GU_SRC_ALPHA, GU_ONE_MINUS_SRC_ALPHA, 0, 0); // default blending
|
// sceGuBlendFunc(GU_ADD, GU_SRC_ALPHA, GU_ONE_MINUS_SRC_ALPHA, 0, 0); // default blending
|
||||||
sceGuBlendFunc(GU_ADD, GU_FIX, GU_FIX, 0xF0F0F0F0, 0x0F0F0F0F);
|
sceGuBlendFunc(GU_ADD, GU_FIX, GU_FIX, 0xF0F0F0F0, 0x0F0F0F0F);
|
||||||
;
|
;
|
||||||
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_16BIT | GU_COLOR_4444 | GU_VERTEX_16BIT | GU_TRANSFORM_2D, 32, NULL, psp->menu.frame_coords);
|
sceGuDrawArray(GU_SPRITES, GU_TEXTURE_32BITF | GU_VERTEX_32BITF | GU_TRANSFORM_2D, PSP_FRAME_VERTEX_COUNT, NULL, psp->menu.frame_coords);
|
||||||
sceGuFinish();
|
sceGuFinish();
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -521,34 +559,37 @@ static void psp_set_texture_enable(void *data, bool state, bool full_screen)
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void psp_update_frame_coords(psp1_video_t* psp)
|
static inline void psp_update_frame_coords(psp1_video_t* psp)
|
||||||
{
|
{
|
||||||
psp1_vertex_t *v0, *v1;
|
// psp1_vertex_t *v0, *v1;
|
||||||
|
|
||||||
if (psp->rotation & 0x2)
|
// if (psp->rotation & 0x2)
|
||||||
{
|
// {
|
||||||
v0 = &psp->frame_coords->v1;
|
// v0 = &psp->frame_coords->v1;
|
||||||
v1 = &psp->frame_coords->v0;
|
// v1 = &psp->frame_coords->v0;
|
||||||
}
|
// }
|
||||||
else
|
// else
|
||||||
{
|
// {
|
||||||
v0 = &psp->frame_coords->v0;
|
// v0 = &psp->frame_coords->v0;
|
||||||
v1 = &psp->frame_coords->v1;
|
// v1 = &psp->frame_coords->v1;
|
||||||
}
|
// }
|
||||||
|
|
||||||
if (psp->rotation & 0x1)
|
// if (psp->rotation & 0x1)
|
||||||
{
|
// {
|
||||||
v0->x = psp->vp.x + psp->vp.width;
|
// v0->x = psp->vp.x + psp->vp.width;
|
||||||
v1->x = psp->vp.x;
|
// v1->x = psp->vp.x;
|
||||||
}
|
// }
|
||||||
else
|
// else
|
||||||
{
|
// {
|
||||||
v0->x = psp->vp.x;
|
// v0->x = psp->vp.x;
|
||||||
v1->x = psp->vp.x + psp->vp.width;
|
// v1->x = psp->vp.x + psp->vp.width;
|
||||||
}
|
// }
|
||||||
|
|
||||||
v0->y = psp->vp.y;
|
// v0->y = psp->vp.y;
|
||||||
v1->y = psp->vp.y + psp->vp.height;
|
// v1->y = psp->vp.y + psp->vp.height;
|
||||||
|
|
||||||
|
// no rotation for now
|
||||||
|
psp_set_screen_coords(psp->frame_coords, psp->vp.x, psp->vp.y, psp->vp.width, psp->vp.height);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void psp_update_viewport(psp1_video_t* psp)
|
static void psp_update_viewport(psp1_video_t* psp)
|
||||||
|
Loading…
Reference in New Issue
Block a user