Drawing an image onto a texture

If you are a new Irrlicht Engine user, and have a newbie-question, this is the forum for you. You may also post general programming questions here.
Post Reply
xDan
Competition winner
Posts: 673
Joined: Thu Mar 30, 2006 1:23 pm
Location: UK
Contact:

Drawing an image onto a texture

Post by xDan »

Hi,

I can see I *could* do this with the lock() functions and making my own drawing function but before I try it are there any functions hidden away to do this? Or has anyone already wrote code to do it?

This sort of thing:
drawOnTexture(texture, image, position, rotation, scale)

Thanks
LLDD
Posts: 43
Joined: Fri May 11, 2007 9:50 am

Post by LLDD »

Look at the RTT (render to texture) example.

Basically you have to do:

1) Create a render texture:

Code: Select all

ITexture *RT = driver->createRenderTargetTexture(dimension2d<s32>(X,Y));
2) Set the texture as render target:

Code: Select all

driver->setRenderTarget(RT, true, true, SColor(0,0,0,0)); 
3) Draw calls.
________
NEVADA MARIJUANA DISPENSARIES
Last edited by LLDD on Sun Feb 20, 2011 7:49 am, edited 1 time in total.
hybrid
Admin
Posts: 14143
Joined: Wed Apr 19, 2006 9:20 pm
Location: Oldenburg(Oldb), Germany
Contact:

Post by hybrid »

If you want to use the 2d or 3d drawing method of Irrlicht you have to use the render target textures. If you just want to do some bitmap copying you should look into CColorConvert. There are routines to copy portions of images into others. So you have to lock both images/textures and call those methods until all lines (typically used, otherwise you need the same pitch in both images) are copied. The next release will have a method where you can specify the source and destination image formats to get the correct basic method automatically.
xDan
Competition winner
Posts: 673
Joined: Thu Mar 30, 2006 1:23 pm
Location: UK
Contact:

Post by xDan »

Render to texture looks like the thing I need. Thanks!
xDan
Competition winner
Posts: 673
Joined: Thu Mar 30, 2006 1:23 pm
Location: UK
Contact:

Post by xDan »

Hi again!

I call this code every time I click the mouse:

Code: Select all

            driver->setRenderTarget(rt);
            driver->beginScene(false, false, video::SColor(0,0,0,0));
            driver->draw2DImage(texture, core::position2d<s32>(rand()%512,rand()%512));
            driver->endScene();
            driver->setRenderTarget(0);
The desired behaviour is that the drawn texture remains after each click (for a decal sort of effect). But instead the render target texture is cleared to black before each rendering (so just the most recent decal is shown).

I thought setting the "clear the backBuffer" to false is what I needed but seems not. How can I fix this?
xDan
Competition winner
Posts: 673
Joined: Thu Mar 30, 2006 1:23 pm
Location: UK
Contact:

Post by xDan »

OK so I've done this by having two RTTs and swapping them:

initialisation

Code: Select all

    wallRTT1 = driver->createRenderTargetTexture(core::dimension2d<s32>(512,512));
    wallRTT2 = driver->createRenderTargetTexture(core::dimension2d<s32>(512,512));
    driver->setRenderTarget(wallRTT1);
    driver->beginScene(true, true, video::SColor(0,0,0,0));
    // render original texture to RTT1
    driver->draw2DImage(wallsSceneNode->getMaterial(0).Textures[0], core::position2d<s32>(0,0));
    driver->endScene();
    driver->setRenderTarget(0);
    // set wall texture to RTT
    wallsSceneNode->getMaterial(0).Textures[0] = wallRTT1;
drawing onto it

Code: Select all

    // swap RTTs
    video::ITexture *tempRTT = wallRTT1;
    wallRTT1 = wallRTT2;
    wallRTT2 = tempRTT;
    // rendering
    driver->setRenderTarget(wallRTT1);
    driver->beginScene(false, false, video::SColor(0,0,0,0));
    // draw old render
    driver->draw2DImage(wallRTT2, core::position2d<s32>(0,0));
    // render blood splat with transparency
    int w = texture->getOriginalSize().Width;
    int h = texture->getOriginalSize().Height;
    int x = rand()%512;
    int y = rand()%512;
    driver->draw2DImage(texture,
        core::rect<s32>(x,y,x+w,y+h),
        core::rect<s32>(0,0,w,h),
        0,0,true);
    driver->endScene();
    driver->setRenderTarget(0);
    // set to new RTT
    wallsSceneNode->getMaterial(0).Textures[0] = wallRTT1;
EDIT: Note, there should only be one begin/endScene pair called per frame. So put any rendering to textures within the same block you do the rest of your drawing.
Post Reply