21 #include "../../SDL_internal.h" 23 #if SDL_VIDEO_RENDER_PSP 26 #include "../SDL_sysrender.h" 28 #include <pspkernel.h> 29 #include <pspdisplay.h> 102 .num_texture_formats = 4,
108 .max_texture_width = 512,
109 .max_texture_height = 512,
113 #define PSP_SCREEN_WIDTH 480 114 #define PSP_SCREEN_HEIGHT 272 116 #define PSP_FRAME_BUFFER_WIDTH 512 117 #define PSP_FRAME_BUFFER_SIZE (PSP_FRAME_BUFFER_WIDTH*PSP_SCREEN_HEIGHT) 119 static unsigned int __attribute__((aligned(16))) DisplayList[262144];
122 #define COL5650(r,g,b,a) ((r>>3) | ((g>>2)<<5) | ((b>>3)<<11)) 123 #define COL5551(r,g,b,a) ((r>>3) | ((g>>3)<<5) | ((b>>3)<<10) | (a>0?0x7000:0)) 124 #define COL4444(r,g,b,a) ((r>>4) | ((g>>4)<<4) | ((b>>4)<<8) | ((a>>4)<<12)) 125 #define COL8888(r,g,b,a) ((r) | ((g)<<8) | ((b)<<16) | ((a)<<24)) 138 unsigned int currentColor;
139 int currentBlendMode;
150 unsigned int textureWidth;
151 unsigned int textureHeight;
175 TextureNextPow2(
unsigned int w)
210 if(data->displayListAvail)
213 sceGuStart(GU_DIRECT, DisplayList);
219 TextureSwizzle(PSP_TextureData *psp_texture)
221 if(psp_texture->swizzled)
224 int bytewidth = psp_texture->textureWidth*(psp_texture->bits>>3);
225 int height = psp_texture->size / bytewidth;
227 int rowblocks = (bytewidth>>4);
228 int rowblocksadd = (rowblocks-1)<<7;
229 unsigned int blockaddress = 0;
230 unsigned int *
src = (
unsigned int*) psp_texture->data;
237 for(j = 0; j <
height; j++, blockaddress += 16)
241 block = (
unsigned int*)&
data[blockaddress];
245 for(i = 0; i < rowblocks; i++)
255 blockaddress += rowblocksadd;
258 free(psp_texture->data);
259 psp_texture->data =
data;
264 int TextureUnswizzle(PSP_TextureData *psp_texture)
266 if(!psp_texture->swizzled)
271 int bytewidth = psp_texture->textureWidth*(psp_texture->bits>>3);
272 int height = psp_texture->size / bytewidth;
274 int widthblocks = bytewidth/16;
275 int heightblocks = height/8;
277 int dstpitch = (bytewidth - 16)/4;
278 int dstrow = bytewidth * 8;
280 unsigned int *src = (
unsigned int*) psp_texture->data;
289 sceKernelDcacheWritebackAll();
293 unsigned char *ydst = (
unsigned char *)
data;
295 for(blocky = 0; blocky < heightblocks; ++blocky)
297 unsigned char *xdst = ydst;
299 for(blockx = 0; blockx < widthblocks; ++blockx)
303 block = (
unsigned int*)xdst;
305 for(j = 0; j < 8; ++
j)
307 *(block++) = *(src++);
308 *(block++) = *(src++);
309 *(block++) = *(src++);
310 *(block++) = *(src++);
320 free(psp_texture->data);
322 psp_texture->data =
data;
334 PSP_RenderData *
data;
342 data = (PSP_RenderData *)
SDL_calloc(1,
sizeof(*data));
344 PSP_DestroyRenderer(renderer);
368 renderer->
info = PSP_RenderDriver.
info;
389 data->frontbuffer = (
unsigned int *)(PSP_FRAME_BUFFER_SIZE<<1);
390 data->backbuffer = (
unsigned int *)(0);
392 data->psm = pixelformat;
395 data->frontbuffer = (
unsigned int *)(PSP_FRAME_BUFFER_SIZE<<2);
396 data->backbuffer = (
unsigned int *)(0);
398 data->psm = GU_PSM_8888;
404 sceGuStart(GU_DIRECT, DisplayList);
405 sceGuDrawBuffer(data->psm, data->frontbuffer, PSP_FRAME_BUFFER_WIDTH);
406 sceGuDispBuffer(PSP_SCREEN_WIDTH, PSP_SCREEN_HEIGHT, data->backbuffer, PSP_FRAME_BUFFER_WIDTH);
409 sceGuOffset(2048 - (PSP_SCREEN_WIDTH>>1), 2048 - (PSP_SCREEN_HEIGHT>>1));
410 sceGuViewport(2048, 2048, PSP_SCREEN_WIDTH, PSP_SCREEN_HEIGHT);
412 data->frontbuffer = vabsptr(data->frontbuffer);
413 data->backbuffer = vabsptr(data->backbuffer);
416 sceGuScissor(0, 0, PSP_SCREEN_WIDTH, PSP_SCREEN_HEIGHT);
417 sceGuEnable(GU_SCISSOR_TEST);
420 sceGuFrontFace(GU_CCW);
421 sceGuEnable(GU_CULL_FACE);
424 sceGuEnable(GU_TEXTURE_2D);
425 sceGuShadeModel(GU_SMOOTH);
426 sceGuTexWrap(GU_REPEAT, GU_REPEAT);
429 sceGuEnable(GU_BLEND);
430 sceGuBlendFunc(GU_ADD, GU_SRC_ALPHA, GU_ONE_MINUS_SRC_ALPHA, 0, 0);
432 sceGuTexFilter(GU_LINEAR,GU_LINEAR);
436 sceDisplayWaitVblankStartCB();
437 sceGuDisplay(GU_TRUE);
453 PSP_TextureData* psp_texture = (PSP_TextureData*)
SDL_calloc(1,
sizeof(*psp_texture));
459 psp_texture->width = texture->
w;
460 psp_texture->height = texture->
h;
461 psp_texture->textureHeight = TextureNextPow2(texture->
h);
462 psp_texture->textureWidth = TextureNextPow2(texture->
w);
463 psp_texture->format = PixelFormatToPSPFMT(texture->
format);
465 switch(psp_texture->format)
470 psp_texture->bits = 16;
474 psp_texture->bits = 32;
482 psp_texture->size = psp_texture->textureHeight*psp_texture->pitch;
483 psp_texture->data =
SDL_calloc(1, psp_texture->size);
485 if(!psp_texture->data)
504 PSP_TextureData *psp_texture = (PSP_TextureData *) texture->
driverdata;
508 if (texture->
w >= 16 || texture->
h >= 16)
510 TextureSwizzle(psp_texture);
513 sceGuEnable(GU_TEXTURE_2D);
514 sceGuTexWrap(GU_REPEAT, GU_REPEAT);
515 sceGuTexMode(psp_texture->format, 0, 0, psp_texture->swizzled);
516 sceGuTexFilter(scaleMode, scaleMode);
518 sceGuTexImage(0, psp_texture->textureWidth, psp_texture->textureHeight, psp_texture->textureWidth, psp_texture->data);
519 sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGBA);
533 PSP_LockTexture(renderer, texture,rect,(
void **)&dst, &dpitch);
535 if (length == pitch && length == dpitch) {
538 for (row = 0; row < rect->
h; ++
row) {
545 sceKernelDcacheWritebackAll();
551 const SDL_Rect * rect,
void **pixels,
int *pitch)
553 PSP_TextureData *psp_texture = (PSP_TextureData *) texture->
driverdata;
556 (
void *) ((
Uint8 *) psp_texture->data + rect->
y * psp_texture->pitch +
558 *pitch = psp_texture->pitch;
565 PSP_TextureData *psp_texture = (PSP_TextureData *) texture->
driverdata;
573 PSP_UpdateTexture(renderer, texture, &rect, psp_texture->data, psp_texture->pitch);
594 PSP_RenderData *data = (PSP_RenderData *) renderer->
driverdata;
595 if (blendMode != data-> currentBlendMode) {
598 sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGBA);
599 sceGuDisable(GU_BLEND);
602 sceGuTexFunc(GU_TFX_MODULATE , GU_TCC_RGBA);
603 sceGuEnable(GU_BLEND);
604 sceGuBlendFunc(GU_ADD, GU_SRC_ALPHA, GU_ONE_MINUS_SRC_ALPHA, 0, 0 );
607 sceGuTexFunc(GU_TFX_MODULATE , GU_TCC_RGBA);
608 sceGuEnable(GU_BLEND);
609 sceGuBlendFunc(GU_ADD, GU_SRC_ALPHA, GU_FIX, 0, 0x00FFFFFF );
612 sceGuTexFunc(GU_TFX_MODULATE , GU_TCC_RGBA);
613 sceGuEnable(GU_BLEND);
614 sceGuBlendFunc( GU_ADD, GU_FIX, GU_SRC_COLOR, 0, 0);
627 StartDrawing(renderer);
628 int color = renderer->
a << 24 | renderer->
b << 16 | renderer->
g << 8 | renderer->
r;
629 sceGuClearColor(color);
631 sceGuClear(GU_COLOR_BUFFER_BIT|GU_DEPTH_BUFFER_BIT|GU_FAST_CLEAR_BIT);
640 int color = renderer->
a << 24 | renderer->
b << 16 | renderer->
g << 8 | renderer->
r;
642 StartDrawing(renderer);
643 VertV* vertices = (VertV*)sceGuGetMemory(count*
sizeof(VertV));
645 for (i = 0; i <
count; ++
i) {
646 vertices[
i].x = points[
i].
x;
647 vertices[
i].y = points[
i].
y;
648 vertices[
i].z = 0.0f;
650 sceGuDisable(GU_TEXTURE_2D);
652 sceGuShadeModel(GU_FLAT);
653 sceGuDrawArray(GU_POINTS, GU_VERTEX_32BITF|GU_TRANSFORM_2D, count, 0, vertices);
654 sceGuShadeModel(GU_SMOOTH);
655 sceGuEnable(GU_TEXTURE_2D);
664 int color = renderer->
a << 24 | renderer->
b << 16 | renderer->
g << 8 | renderer->
r;
666 StartDrawing(renderer);
667 VertV* vertices = (VertV*)sceGuGetMemory(count*
sizeof(VertV));
669 for (i = 0; i <
count; ++
i) {
670 vertices[
i].x = points[
i].
x;
671 vertices[
i].y = points[
i].
y;
672 vertices[
i].z = 0.0f;
675 sceGuDisable(GU_TEXTURE_2D);
677 sceGuShadeModel(GU_FLAT);
678 sceGuDrawArray(GU_LINE_STRIP, GU_VERTEX_32BITF|GU_TRANSFORM_2D, count, 0, vertices);
679 sceGuShadeModel(GU_SMOOTH);
680 sceGuEnable(GU_TEXTURE_2D);
689 int color = renderer->
a << 24 | renderer->
b << 16 | renderer->
g << 8 | renderer->
r;
691 StartDrawing(renderer);
693 for (i = 0; i <
count; ++
i) {
695 VertV* vertices = (VertV*)sceGuGetMemory((
sizeof(VertV)<<1));
696 vertices[0].
x = rect->
x;
697 vertices[0].y = rect->
y;
698 vertices[0].z = 0.0f;
700 vertices[1].x = rect->
x + rect->
w;
701 vertices[1].y = rect->
y + rect->
h;
702 vertices[1].z = 0.0f;
704 sceGuDisable(GU_TEXTURE_2D);
706 sceGuShadeModel(GU_FLAT);
707 sceGuDrawArray(GU_SPRITES, GU_VERTEX_32BITF|GU_TRANSFORM_2D, 2, 0, vertices);
708 sceGuShadeModel(GU_SMOOTH);
709 sceGuEnable(GU_TEXTURE_2D);
716 #define PI 3.14159265358979f 718 #define radToDeg(x) ((x)*180.f/PI) 719 #define degToRad(x) ((x)*PI/180.f) 721 float MathAbs(
float x)
727 "vabs.s S000, S000\n" 734 void MathSincos(
float r,
float *
s,
float *
c)
738 "vcst.s S003, VFPU_2_PI\n" 739 "vmul.s S002, S002, S003\n" 740 "vrot.p C000, S002, [s, c]\n" 743 :
"=r"(*s),
"=r"(*c):
"r"(
r));
746 void Swap(
float *
a,
float *
b)
768 u1 = srcrect->
x + srcrect->
w;
769 v1 = srcrect->
y + srcrect->
h;
773 StartDrawing(renderer);
774 TextureActivate(texture);
775 PSP_SetBlendMode(renderer, renderer->
blendMode);
779 sceGuTexFunc(GU_TFX_MODULATE, GU_TCC_RGBA);
780 sceGuColor(GU_RGBA(255, 255, 255, alpha));
782 sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGBA);
783 sceGuColor(0xFFFFFFFF);
786 if((MathAbs(u1) - MathAbs(u0)) < 64.0
f)
788 VertTV* vertices = (VertTV*)sceGuGetMemory((
sizeof(VertTV))<<1);
798 vertices[1].x = x +
width;
799 vertices[1].y = y +
height;
802 sceGuDrawArray(GU_SPRITES, GU_TEXTURE_32BITF|GU_VERTEX_32BITF|GU_TRANSFORM_2D, 2, 0, vertices);
809 float endX = x +
width;
811 float ustep = (u1 - u0)/width * slice;
816 for(start = 0, end = width; start <
end; start += slice)
818 VertTV* vertices = (VertTV*)sceGuGetMemory((
sizeof(VertTV))<<1);
820 float polyWidth = ((curX + slice) > endX) ? (endX - curX) : slice;
821 float sourceWidth = ((curU + ustep) > u1) ? (u1 - curU) : ustep;
823 vertices[0].u = curU;
825 vertices[0].x = curX;
832 vertices[1].u = curU;
834 vertices[1].x = curX;
835 vertices[1].y = (y +
height);
838 sceGuDrawArray(GU_SPRITES, GU_TEXTURE_32BITF|GU_VERTEX_32BITF|GU_TRANSFORM_2D, 2, 0, vertices);
843 sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGBA);
849 Uint32 pixel_format,
void * pixels,
int pitch)
864 float centerx, centery;
873 u1 = srcrect->
x + srcrect->
w;
874 v1 = srcrect->
y + srcrect->
h;
881 StartDrawing(renderer);
882 TextureActivate(texture);
883 PSP_SetBlendMode(renderer, renderer->
blendMode);
887 sceGuTexFunc(GU_TFX_MODULATE, GU_TCC_RGBA);
888 sceGuColor(GU_RGBA(255, 255, 255, alpha));
890 sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGBA);
891 sceGuColor(0xFFFFFFFF);
901 MathSincos(degToRad(angle), &s, &c);
914 VertTV* vertices = (VertTV*)sceGuGetMemory(
sizeof(VertTV)<<2);
918 vertices[0].x = x - cw + sh;
919 vertices[0].y = y - sw - ch;
924 vertices[1].x = x - cw - sh;
925 vertices[1].y = y - sw + ch;
930 vertices[2].x = x + cw - sh;
931 vertices[2].y = y + sw + ch;
936 vertices[3].x = x + cw + sh;
937 vertices[3].y = y + sw - ch;
941 Swap(&vertices[0].
v, &vertices[2].v);
942 Swap(&vertices[1].
v, &vertices[3].v);
945 Swap(&vertices[0].u, &vertices[2].u);
946 Swap(&vertices[1].u, &vertices[3].u);
949 sceGuDrawArray(GU_TRIANGLE_FAN, GU_TEXTURE_32BITF|GU_VERTEX_32BITF|GU_TRANSFORM_2D, 4, 0, vertices);
952 sceGuTexFunc(GU_TFX_REPLACE, GU_TCC_RGBA);
959 PSP_RenderData *data = (PSP_RenderData *) renderer->
driverdata;
960 if(!data->displayListAvail)
968 sceDisplayWaitVblankStart();
970 data->backbuffer = data->frontbuffer;
971 data->frontbuffer = vabsptr(sceGuSwapBuffers());
978 PSP_RenderData *renderdata = (PSP_RenderData *) renderer->
driverdata;
979 PSP_TextureData *psp_texture = (PSP_TextureData *) texture->
driverdata;
995 PSP_RenderData *data = (PSP_RenderData *) renderer->
driverdata;
997 if (!data->initialized)
1000 StartDrawing(renderer);
int(* RenderDrawLines)(SDL_Renderer *renderer, const SDL_FPoint *points, int count)
GLdouble GLdouble GLdouble r
int(* RenderDrawPoints)(SDL_Renderer *renderer, const SDL_FPoint *points, int count)
int(* LockTexture)(SDL_Renderer *renderer, SDL_Texture *texture, const SDL_Rect *rect, void **pixels, int *pitch)
int(* RenderReadPixels)(SDL_Renderer *renderer, const SDL_Rect *rect, Uint32 format, void *pixels, int pitch)
GLint GLint GLint GLint GLint x
GLuint GLuint GLsizei count
SDL_RenderDriver PSP_RenderDriver
#define SDL_BYTESPERPIXEL(X)
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
int(* RenderFillRects)(SDL_Renderer *renderer, const SDL_FRect *rects, int count)
GLenum GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const void * bits
int(* RenderClear)(SDL_Renderer *renderer)
GLfloat GLfloat GLfloat alpha
void(* DestroyRenderer)(SDL_Renderer *renderer)
GLint GLint GLsizei width
GLfixed GLfixed GLint GLint GLfixed points
static SDL_BlendMode blendMode
GLint GLint GLsizei GLsizei GLsizei GLint GLenum format
int(* UpdateTexture)(SDL_Renderer *renderer, SDL_Texture *texture, const SDL_Rect *rect, const void *pixels, int pitch)
int(* SetTextureColorMod)(SDL_Renderer *renderer, SDL_Texture *texture)
GLenum GLenum GLuint texture
int SDL_RecreateWindow(SDL_Window *window, Uint32 flags)
static SDL_Renderer * renderer
return Display return Display Bool Bool int int int return Display XEvent Bool(*) XPointer return Display return Display Drawable _Xconst char unsigned int unsigned int return Display Pixmap Pixmap XColor XColor unsigned int unsigned int return Display _Xconst char char int char return Display Visual unsigned int int int char unsigned int unsigned int int in j)
GLubyte GLubyte GLubyte GLubyte w
void(* UnlockTexture)(SDL_Renderer *renderer, SDL_Texture *texture)
SDL_Renderer *(* CreateRenderer)(SDL_Window *window, Uint32 flags)
GLint GLint GLint GLint GLint GLint y
int(* SetRenderTarget)(SDL_Renderer *renderer, SDL_Texture *texture)
int(* UpdateViewport)(SDL_Renderer *renderer)
GLint GLint GLsizei GLsizei GLsizei GLint GLenum GLenum const GLvoid * pixels
SDL_RendererFlip
Flip constants for SDL_RenderCopyEx.
return Display return Display Bool Bool int int int return Display XEvent Bool(*) XPointer return Display return Display Drawable _Xconst char unsigned int unsigned int return Display Pixmap Pixmap XColor XColor unsigned int unsigned int return Display _Xconst char char int char return Display Visual unsigned int int int char unsigned int unsigned int in i)
int(* RenderCopy)(SDL_Renderer *renderer, SDL_Texture *texture, const SDL_Rect *srcrect, const SDL_FRect *dstrect)
Window state change event data (event.window.*)
#define SDL_OutOfMemory()
GLint GLint GLsizei GLsizei height
int(* RenderCopyEx)(SDL_Renderer *renderer, SDL_Texture *texture, const SDL_Rect *srcquad, const SDL_FRect *dstrect, const double angle, const SDL_FPoint *center, const SDL_RendererFlip flip)
EGLSurface EGLNativeWindowType * window
The type used to identify a window.
#define SDL_GetWindowPixelFormat
void(* WindowEvent)(SDL_Renderer *renderer, const SDL_WindowEvent *event)
void(* DestroyTexture)(SDL_Renderer *renderer, SDL_Texture *texture)
int(* CreateTexture)(SDL_Renderer *renderer, SDL_Texture *texture)
void(* RenderPresent)(SDL_Renderer *renderer)
EGLSurface EGLint * rects
GLuint GLsizei GLsizei * length
GLboolean GLboolean GLboolean GLboolean a
GLboolean GLboolean GLboolean b
#define SDL_Unsupported()
A rectangle, with the origin at the upper left.