[Solved] (Blit image to VRAM) sceGuCopyImage in Kernel mode?

Discuss the development of new homebrew software, tools and libraries.

Moderators: cheriff, TyRaNiD

Post Reply
User avatar
Torch
Posts: 825
Joined: Wed May 28, 2008 2:50 am

[Solved] (Blit image to VRAM) sceGuCopyImage in Kernel mode?

Post by Torch »

Is it possible?

I'm under the impression that sceGuCopyImage will handle the source pixel format and convert it for the current display mode.

I just want to copy an 8888 image to VRAM in-game using sceGuCopyImage.

If it doesn't then I assume I'll have to write code to convert the source image into the current pixel format and write it to VRAM manually? Any one have some sample code to do this?

I blitting stuff to VRAM now, but for blitting an image the pixel format becomes a problem depending on what mode the game is using, so I though the GU functions would handle that.
Last edited by Torch on Sun Nov 16, 2008 1:23 am, edited 1 time in total.
User avatar
Torch
Posts: 825
Joined: Wed May 28, 2008 2:50 am

Post by Torch »

I threw together something to blit 8888 RGBA images to VRAM, with automatic conversion to target pixel format with alpha blending. Its based off someones's screenshot plugin.

Code: Select all

//Globals
int pmode, pwidth, pheight, bufferwidth, pixelformat;
unsigned int* vram32;
unsigned short* vram16;

//Somewhere in your code
...
	sceDisplayGetMode(&pmode, &pwidth, &pheight);
	sceDisplayGetFrameBuf((void*)&vram32, &bufferwidth, &pixelformat, PSP_DISPLAY_SETBUF_IMMEDIATE);
	vram16 = (unsigned short*) vram32;
	
	drawimage(smiley, smiley_w, smiley_h, 20, 20);
...

void drawimage(unsigned char * image, unsigned int srcw, unsigned int srch, unsigned int destx, unsigned int desty)
{
	#define sbpp 4 //Source bytes-per-pixel (RGBA=4)
	unsigned int x, y, pos = 0;
	
	sceDisplayWaitVblankStart();

	for&#40;y = desty; y < desty+srch; y++&#41;&#123;
		for&#40;x = destx; x < destx+srcw; x++&#41;&#123;
			unsigned int color, offset = x + y*bufferwidth;
			unsigned char r = 0, g = 0, b = 0;
			
			switch &#40;pixelformat&#41; &#123;
				case 0&#58;	// 16-bit RGB 5&#58;6&#58;5
					color = vram16&#91;offset&#93;;
					r = &#40;color & 0x1f&#41; << 3;
					g = &#40;&#40;color >> 5&#41; & 0x3f&#41; << 2;
					b = &#40;&#40;color >> 11&#41; & 0x1f&#41; << 3;
					r = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*r + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp&#93;&#41; >> 3;
					g = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*g + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 1&#93;&#41; >> 2;
					b = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*b + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 2&#93;&#41; >> 3;
					vram16&#91;offset&#93; = &#40;b << 11&#41;|&#40;g << 5&#41;|r;
					break;
				case 1&#58;// 16-bit RGBA 5&#58;5&#58;5&#58;1
					color = vram16&#91;offset&#93;;
					r = &#40;color & 0x1f&#41; << 3;
					g = &#40;&#40;color >> 5&#41; & 0x1f&#41; << 3;
					b = &#40;&#40;color >> 10&#41; & 0x1f&#41; << 3;
					r = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*r + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp&#93;&#41; >> 3;
					g = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*g + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 1&#93;&#41; >> 3;
					b = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*b + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 2&#93;&#41; >> 3;
					vram16&#91;offset&#93; = &#40;b << 10&#41;|&#40;g << 5&#41;|r;
					break;
				case 2&#58;// 16-bit RGBA 4&#58;4&#58;4&#58;4
					color = vram16&#91;offset&#93;;
					r = &#40;color & 0xf&#41; << 4;
					g = &#40;&#40;color >> 4&#41; & 0xf&#41; << 4;
					b = &#40;&#40;color >> 8&#41; & 0xf&#41; << 4;
					r = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*r + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp&#93;&#41; >> 4;
					g = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*g + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 1&#93;&#41; >> 4;
					b = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*b + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 2&#93;&#41; >> 4;
					vram16&#91;offset&#93; = &#40;b << 8&#41;|&#40;g << 4&#41;|r;
					break;
				case 3&#58;// 32-bit RGBA 8&#58;8&#58;8&#58;8
					color = vram32&#91;offset&#93;;
					r = color & 0xff;
					g = &#40;color >> 8&#41; & 0xff;
					b = &#40;color >> 16&#41; & 0xff;
					r = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*r + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp&#93;&#41;;
					g = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*g + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 1&#93;&#41;;
					b = &#40;unsigned char&#41;&#40;&#40;&#40;255.0f - image&#91;pos*sbpp + 3&#93;&#41;/255.0f&#41;*b + &#40;image&#91;pos*sbpp + 3&#93;/255.0f&#41;*image&#91;pos*sbpp + 2&#93;&#41;;
					vram32&#91;offset&#93; = &#40;b << 16&#41;|&#40;g << 8&#41;|r;
					break;
			&#125;
			pos++;
		&#125;
	&#125;
	
	sceKernelDcacheWritebackAll&#40;&#41;;
&#125;
User avatar
Torch
Posts: 825
Joined: Wed May 28, 2008 2:50 am

Post by Torch »

Cleaned it up a bit. Made it a nice callable function with source params.
.::Albandu51::.
Posts: 12
Joined: Thu Oct 04, 2007 12:33 am

Post by .::Albandu51::. »

hi Torch !

Sorry for my language but i'm French.

Your fonction for load a image ,what type of image is loading ? Bmp , Png ?

It's BMP file , no ? I don't sure :)


Thank's
User avatar
Torch
Posts: 825
Joined: Wed May 28, 2008 2:50 am

Post by Torch »

The char * image[] should contain raw 8888 RGBA data. I'm not loading any image in my app, I've directly saved the RGBA data in the source code as an array.

You can export an image as raw data using GIMP (by choosing RAW in the Save As options).

If you have images in PNG, BMP etc, then you can use already available code to load it. Then just pass the array of the image data after loading.
.::Albandu51::.
Posts: 12
Joined: Thu Oct 04, 2007 12:33 am

Post by .::Albandu51::. »

Ok thank's !
kralyk
Posts: 114
Joined: Sun Apr 06, 2008 8:18 pm
Location: Czech Republic, central EU

Post by kralyk »

Torch wrote:Its based off someones's screenshot plugin.
What? Where? When? How? ;-)
I'd just love to see a source code of a screenshot plugin, because of my future work, do you have it or can you tell me where I can find it?
...sorry for my english...
Post Reply