Extracting values from a surface

Started by
5 comments, last by flip_mo_kid 18 years, 10 months ago
Hi I've been able to extract colour values from a D3DFMT_A8R8G8B8 texture as there is a lot of code available that demonstrates how to do it. However, I'm having difficult extracting colour values from D3DFMT_A16B16G16R16F textures. Can anyone tell me how to do this, for D3DFMT_A8R8G8B8 textures I use the following code:

 			D3DLOCKED_RECT lockedRect;
			tempSurface->LockRect(
								&lockedRect,	// pointer to receive locked data
								0,				// lock entire surface
								0);				// no lock flags specified

			float* dataHolder = textureInfo[j];
			memset(dataHolder, 0, sizeof(float)*Pixels*Pixels*3);

			// Iterate through each pixel in the surface and set it to red.
			BYTE *bytePointer=(BYTE*)lockedRect.pBits;			
			for (DWORD y=0;y<desc.Height;y++)
			{
				for (DWORD x=0;x<desc.Width;x++)
				{
					DWORD index=(x*4+(y*(lockedRect.Pitch)));
				       
					// Blue
					BYTE r=bytePointer[index];
					dataHolder[y*desc.Width*3 + x*3 + 2] = (float)r; 

					// Green
					BYTE g=bytePointer[index+1];
					dataHolder[y*desc.Width*3 + x*3 + 1] = (float)g; 

					// Red
					BYTE b=bytePointer[index+2];
					dataHolder[y*desc.Width*3 + x*3 + 0] = (float)b; 

					// Alpha
				//	BYTE a=bytePointer[index+3];  
				}
			}

			tempSurface->UnlockRect();

			tempSurface->Release();
I've tried using D3DXFLOAT16 *bytePointer=(D3DXFLOAT16*)lockedRect.pBits; and D3DXFLOAT16 r=bytePointer[index]; but I get memory exceptions and to be honest I don't really know what I'm doign :D Thanks
Advertisement
If your current D3DFMT_A8R8G8B8 code is working, it should also work fine for the D3DFMT_A16B16G16R16F format. Just use a 16 bit pointer instead of 8 bits. Be aware of the pitch value though. lockedRect.Pitch is in bytes, so you'll need to divide that by 2 if you're working with a 16-bit pointer. And that is assuming the pitch is divisible by 2.

edit: Err, umm, also, I failed to realize that the data is BGR instead of RGB. So you'll have to reverse the way you read that.
Hi,

If my texture is 1x1 then am I right in assuming I don't need to worry about the pitch?
Quote:If my texture is 1x1 then am I right in assuming I don't need to worry about the pitch?

Yeppers

edit: Do you mean you're getting memory exceptions with the 1x1 texture?
Actually, I looked at what was happening deeper and it appears that the lock_rect method call is failing.

I tried D3DFMT_A8R8G8B8 format and getting DirectX to autogenerate all mipmaps. I have a 64x64 texture and its creating 7 levels. When I try to access any of the levels the lock_rect method always fails.

By the way, my texture is a rendertarget, is that a problem? Also, if it is then is the only way to lock and read the values of the texture to copy it to another texture that isn't a render target?
I haven't messed with render targets much. Have you tried enabling Direct3D-debug mode with full output? It might tell you what the problem is there.

Sorry, wish I could be more helpful.
Actually, I found out you can't lock rendertargets which is sad. Thanks for the help, I appreciate it a lot!

This topic is closed to new replies.

Advertisement