Texture::loadFromMemory()

For help with general CEGUI usage:
- Questions about the usage of CEGUI and its features, if not explained in the documentation.
- Problems with the CMAKE configuration or problems occuring during the build process/compilation.
- Errors or unexpected behaviour.

Moderators: CEGUI MVP, CEGUI Team

ares23
Just popping in
Just popping in
Posts: 10
Joined: Mon Jan 07, 2008 00:25

Texture::loadFromMemory()

Postby ares23 » Wed Jan 09, 2008 03:44

Hey!

Can somebody please explain how to create a pixel buffer to be passed to loadFromMemory()? I have a bitmap class (EasyBMP) which gives the RGB values for each pixel but I can't get the texture to render properly.

Below is the code I'm currently hacking at:

Code: Select all

BMP Image;
Image.ReadFromFile("Media/materials/textures/terrain_texture.bmp");
unsigned int *mPixelBuffer = (unsigned int *)malloc (Image.TellWidth() * Image.TellHeight());

for (int i=0; i<Image.TellWidth(); i++)
{
   for (int j=0; j<Image.TellHeight(); j++)
   {
      mPixelBuffer[i+j] = (unsigned int)((Image(i,j)->Red << 16) | (Image(i,j)->Green << 8) | (Image(i,j)->Blue << 16) |(255 << 24));
   }
}

CEGUI::Texture *txt = mguirenderer->createTexture();
txt->loadFromMemory(&mPixelBuffer, 32, 32, CEGUI::Texture::PF_RGBA);


Any help would be appreciated.

User avatar
scriptkid
Home away from home
Home away from home
Posts: 1178
Joined: Wed Jan 12, 2005 12:06
Location: The Hague, The Netherlands
Contact:

Postby scriptkid » Wed Jan 09, 2008 08:19

Hi,

i think that you index your mPixelBuffer incorrectly. Shouldn't this be:

Code: Select all

mPixelBuffer[j * Image.TellWidth() + i]


?

My 2d coding is a bit rusty though... The easiest way might be to define an index before your double loop, and increment it in the Height loop.

HTH.
Check out my released snake game using Cegui!

ares23
Just popping in
Just popping in
Posts: 10
Joined: Mon Jan 07, 2008 00:25

Postby ares23 » Wed Jan 09, 2008 20:22

Thanks again for your help scriptkid.

I updated the loop as so:

Code: Select all

BMP Image;
Image.ReadFromFile("Media/materials/textures/terrain_texture.bmp");
//unsigned int *mPixelBuffer = (unsigned int *)malloc (Image.TellWidth() * Image.TellHeight());
unsigned int *mPixelBuffer = (unsigned int *)malloc (Image.TellWidth() * Image.TellHeight() * 4);

long iBufIndex = 0;
for (int i=0; i<Image.TellWidth(); i++)

{

   for (int j=0; j<Image.TellHeight(); j++)

   {
      mPixelBuffer[iBufIndex] = (unsigned int)((Image(i,j)->Red << 16) | (Image(i,j)->Green << 8) | (Image(i,j)->Blue << 16) |(255 << 24));
      iBufIndex++;

   }

}

CEGUI::Texture *txt = mguirenderer->createTexture();
txt->loadFromMemory(&mPixelBuffer, 32, 32, CEGUI::Texture::PF_RGBA);


This didn't help though, below is how the texture actually looks (top) and how it renders from my pixel buffer (bottom) in case it helps.

Image

Image

I still don't think I'm creating the pixel buffer right. I can't find any working examples of loadFromMemory() in the samples, on google or in the forum. Does such a thing exist?

User avatar
CrazyEddie
CEGUI Project Lead
Posts: 6760
Joined: Wed Jan 12, 2005 12:06
Location: England
Contact:

Postby CrazyEddie » Wed Jan 09, 2008 21:05

Assuming that the Red, Green, Blue fields in Image are 8 bit bytes, then in this line:

Code: Select all

mPixelBuffer[iBufIndex] = (unsigned int)((Image(i,j)->Red << 16) | (Image(i,j)->Green << 8) | (Image(i,j)->Blue << 16) |(255 << 24));

The fact that you shift both Red and Blue left by 16 bits looks wrong (should Blue not remain unshifted?

The only other thing that could be an issue is that when allocating the buffer you're getting sizes from the image, but then pass 32 explicitly when calling "loadFromMemory" - while it may or may not be an issue in this case - picking one way or another would eliminate any unforeseen anomalies.

No examples as such, but the Font code does use this function - so I guess you could look in there for an example :) CEGUIFreeTypeFont.cpp:315 (in FreeTypeFont::rasterize) is one instance you could look at.

HTH

CE.

ares23
Just popping in
Just popping in
Posts: 10
Joined: Mon Jan 07, 2008 00:25

Postby ares23 » Thu Jan 10, 2008 01:58

Hey Eddie,

Thanks for the help, you made some good points but I'm still hitting a brick wall. Here is the current incarnation of the code:

Code: Select all

BMP Image;
Image.ReadFromFile("Media/materials/textures/terrain_texture.bmp");
unsigned int *mPixelBuffer = new unsigned int[Image.TellWidth() * Image.TellHeight()];
memset (mPixelBuffer, 0, Image.TellWidth() * Image.TellHeight() * sizeof (unsigned int));

long iBufIndex = 0;
for (int i=0; i<Image.TellWidth(); i++)

{

   for (int j=0; j<Image.TellHeight(); j++)

   {
      mPixelBuffer[iBufIndex] = (unsigned int)((Image(i,j)->Blue << 0) | (Image(i,j)->Green << 8) | (Image(i,j)->Red << 16) |(255 << 24));
      iBufIndex++;

   }

}

CEGUI::Texture *txt = mguirenderer->createTexture();
txt->loadFromMemory(&mPixelBuffer, Image.TellWidth(), Image.TellHeight(), CEGUI::Texture::PF_RGBA);


The texture graphic is 512x512 and at the moment the above code crashed on the mguirenderer->createTexture(); line. If I bring the texture graphics down in size to 32x32 there is no crash but it renders the same as before. Any size larger than 32x32 causes a crash.

In case it helps, below is a copy of the backtrace from gdb:

Code: Select all

#0  0xb77e1cbc in memcpy () from /lib/tls/i686/cmov/libc.so.6
#1  0xb7c636fa in Ogre::MemoryDataStream::read (this=0x88fb228, buf=0xb323a008, count=1048576) at OgreDataStream.cpp:294
#2  0xb7cc1baa in Ogre::Image::loadRawData (this=0xbfb603c0, stream=@0xbfb60570, uWidth=512, uHeight=512, uDepth=1, eFormat=Ogre::PF_A8R8G8B8, numFaces=1,
    numMipMaps=0) at OgreImage.cpp:290
#3  0xb7e82179 in Ogre::Texture::loadRawData (this=0x8479ce8, stream=@0xbfb60570, uWidth=512, uHeight=512, eFormat=Ogre::PF_A8R8G8B8)
    at ../../OgreMain/include/OgreImage.h:250
#4  0xb7e85192 in Ogre::TextureManager::loadRawData (this=0x82f6fa0, name=@0xbfb6058c, group=@0xbfb60588, stream=@0xbfb60570, uWidth=512, uHeight=512,
    format=Ogre::PF_A8R8G8B8, texType=Ogre::TEX_TYPE_2D, numMipmaps=0, gamma=1) at OgreTextureManager.cpp:111
#5  0xb78cd0ba in CEGUI::OgreCEGUITexture::loadFromMemory (this=0x9c6ad98, buffPtr=0xbfb609b8, buffWidth=<value optimized out>,
    buffHeight=<value optimized out>, pixelFormat=CEGUI::Texture::PF_RGBA) at OgreCEGUITexture.cpp:172
#6  0x08053eaf in MiniMap (this=0x9bcc848, sceneManager=0x8299b20, mguirenderer=0x8571918) at MiniMap.h:44


I feel like I'm _almost_ there and appreciate the continued help. I'm producing an Ogre/CEGUI minimap which I'll happily share with the community (since one doesn't exist yet afaik) if I can get it working.

User avatar
CrazyEddie
CEGUI Project Lead
Posts: 6760
Joined: Wed Jan 12, 2005 12:06
Location: England
Contact:

Postby CrazyEddie » Thu Jan 10, 2008 09:25

I'm going to have to think about this some more, since I have no real ideas at the moment, but could you let us know what the crash is - such as a segfault or whatever.

Cheers,

CE.

Rackle
CEGUI Team (Retired)
Posts: 534
Joined: Mon Jan 16, 2006 11:59
Location: Montréal

Postby Rackle » Thu Jan 10, 2008 12:26

I don't know if you're aware of this code from the Ogre wiki: CEGUIBuildDialog. It may provide some hints.

ares23
Just popping in
Just popping in
Posts: 10
Joined: Mon Jan 07, 2008 00:25

Postby ares23 » Thu Jan 10, 2008 13:14

Crazy Eddie - It is a segmentation fault.

User avatar
CrazyEddie
CEGUI Project Lead
Posts: 6760
Joined: Wed Jan 12, 2005 12:06
Location: England
Contact:

Postby CrazyEddie » Thu Jan 10, 2008 14:20

This is something of a wild guess / long shot, because after looking at CEGUI and Ogre code nothing makes a lot of sense as to why you should get a seg where you do.

So... Do you think it could be somehow affected by threading? (CEGUI is not especially thread safe).

ares23
Just popping in
Just popping in
Posts: 10
Joined: Mon Jan 07, 2008 00:25

Postby ares23 » Thu Jan 10, 2008 15:01

I'm not threading at all, just a standard game loop. This would be so much simplier if CEGUI::Texture had writetomemory() also... :(

User avatar
CrazyEddie
CEGUI Project Lead
Posts: 6760
Joined: Wed Jan 12, 2005 12:06
Location: England
Contact:

Postby CrazyEddie » Thu Jan 10, 2008 19:40

Hi :)

I'm going to have to run some test code and try and reproduce the issue - though I'll not have time to do that until the weekend.

ares23 wrote:This would be so much simplier if CEGUI::Texture had writetomemory() also... :(

Please do submit a feature request on mantis - you never know what may appear in the future :)

ares23
Just popping in
Just popping in
Posts: 10
Joined: Mon Jan 07, 2008 00:25

Postby ares23 » Thu Jan 10, 2008 23:07

Ok will do, thanks CE.

Pompei2
Home away from home
Home away from home
Posts: 489
Joined: Tue May 23, 2006 16:31

Postby Pompei2 » Thu Jan 10, 2008 23:39

Hi,

I do use the loadFromMemory method in a very similar way to you, without any problem. Unfortunately i don't see your two images anymore so i don't know whats up, but about the crash for bigger images, probably it is not a crash but an unhandled exception. Anyways i HIGHLY recommend you to put a try/catch block around all cegui calls you make ! I know it is annoying, but it helps :)

Code: Select all

try {
    // Your cegui code here.
} catch(CEGUI::Exception & e) {
    fprintf(stderr, "CEGUI error: %s", e.getMessage().c_str());
    //Optionally: return -1;
}


and always take a quick look into the CEGUI.log file.

ares23
Just popping in
Just popping in
Posts: 10
Joined: Mon Jan 07, 2008 00:25

Postby ares23 » Fri Jan 11, 2008 00:34

Hi Pompei2 - Thanks for the advice, I'll start wrapping my CEGUI code in a try/catch clause.

Could I see your loadFromMemory() code as a point of reference? If you're doing the same as me then comparing them might highlight my problem.

User avatar
CrazyEddie
CEGUI Project Lead
Posts: 6760
Joined: Wed Jan 12, 2005 12:06
Location: England
Contact:

Postby CrazyEddie » Sat Jan 12, 2008 09:54

Man I should have spotted this one the other day!

This:

Code: Select all

txt->loadFromMemory(&mPixelBuffer, Image.TellWidth(), Image.TellHeight(), CEGUI::Texture::PF_RGBA);


Should be:

Code: Select all

txt->loadFromMemory(mPixelBuffer, Image.TellWidth(), Image.TellHeight(), CEGUI::Texture::PF_RGBA);


Make your cheque payable to: Paul D. Turner

CE.


Return to “Help”

Who is online

Users browsing this forum: No registered users and 23 guests