-
Notifications
You must be signed in to change notification settings - Fork 11
Example 4: Using Images
The Irrlicht IMGUI binding allows you to use any irr::video::IImage
object to draw the image to the GUI.
In this example description we will just concentrate on the image related functions and methods. You can find the full code at the file examples/04.Images/main.cpp.
-
Create an IImage object in Irrlicht: First of all you need to create an
irr::video::IImage
object in Irrlicht. The Irrlicht library provides a lot of different methods to do this. Here we will simply load two images from media files:
irr::video::IVideoDriver * const pDriver = pDevice->getVideoDriver();
irr::video::IImage * pSoyuz = pDriver->createImageFromFile("../../media/Soyuz.jpg");
irr::video::IImage * pSpaceX = pDriver->createImageFromFile("../../media/SpaceX.jpg");
-
Create an IGUITexture object out of the image: Unfortunately you cannot use those
irr::video::IImage
object out of the box with the GUI system. Since the image is stored inside the CPU memory and not inside the GPU memory, where IMGUI expect to find them. Thus you first need to load the images into the GPU memory by creating a texture out of them.
The IrrIMGUI library allows you to creates textures of different sources with the methodGUI->createTexture(...)
from theCGUIHandle
class. This method will create anIrrIMGUI::IGUITexture
object and returns a pointer to it. This texture object contains all necessary information for displaying and managing the image.
IrrIMGUI::IGUITexture * pSoyuzTex = GUI->createTexture(pSoyuz);
IrrIMGUI::IGUITexture * pSpaceXTex = GUI->createTexture(pSpaceX);
-
Drawing the image to the screen: After creating the
IrrIMGUI::IGUITexture
object you can use it with every IMGUI image related function that expects anImTextureID
object. For example to simply draw an image to the window, just use the functionImGui::Image(ImTextureID TextureObject, ImVec2 Size)
.
The first argumentTextureObject
is the pointer or reference toIrrIMGUI::IGUITexture
. It will be casted implicitly to anImTextureID
object. The second argumentSize
is the drawing size of this image. The image will be stretched to this size, when it differs from the original size.
ImGui::Begin("Images");
ImGui::Image(pSoyuzTex, ImVec2(200.0f, 132.0f));
ImGui::Separator();
ImGui::Image(pSpaceXTex, ImVec2(200.0f, 132.0f));
ImGui::End();
-
Free-up the memory for images: When you create an
irr::video::IImage
object you need to free-up the memory, when you don't need this image object anymore. In context of the IMGUI you can free-up the memory after creating anIrrIMGUI::IGUITexture
object. Just use the methodirr::video::IImage::drop()
for deleting the object.
Furthermore also theIrrIMGUI::IGUITexture
object must be destroyed when you don't need this texture anymore for your GUI (for example after the main-loop). This can be done with theGUI->deleteTexture(IGUITexture * pGUITexture)
method of theIIMGUIHandle
class.
When you forget to delete a created texture before shut-down the IMGUI system by destroying the lastIIMGUIHandle
instance, the IrrIMGUI library will print an error message to the console.
pSoyuz->drop();
pSpaceX->drop();
GUI->deleteTexture(pSoyuzTex);
GUI->deleteTexture(pSpaceXTex);
-
Advanced Knowledge: Alternative sources of creating textures: The
IrrIMGUI::IGUITexture
class is the universal handle for using all types of images inside the GUI. TheIGUIHandle::createTexture(...)
method can also create GUI textures from anirr::video::ITexture
object from Irrlicht. Look at the API documentation to understand all possibilities of creating GUI texture objects. -
Advanced Knowledge: Updating the content of a texture object: If you want to change the image content of an GUI texture without creating a new
IrrIMGUI::IGUITexture
object you can reuse an existing object and update the image data by using the methodIGUIHandle::updateTexture(IGUITexture * pGUITexture, ...)
.
This method needs at first argument a pointer to anIrrIMGUI::IGUITexture
object, that should be updated. All further arguments are the same ones that could be used also for theIGUIHandle::createTexture(...)
method.
Attention: Basically you can call theIGUIHandle::updateTexture(IGUITexture * pGUITexture, ...)
method from the main-loop. However dependent on the original source of this texture it may take a long time to do this update. This could lead to major frame-rate drops. The original intention of this method is to update the content of an GUI texture with the content of an render target texture of Irrlicht. In this way you can draw the output of this render step directly to the GUI.
The update method will first check, if it can just reuse the existing GPU memory handle or if it needs to create a new handle. If it can reuse the existing one, the method will return very fast. If not, it may need to create a full copy of the image data inside the GPU memory.
With the Irrlicht High Level render driver of IrrIMGUI, you can update a GPU texture very fast, when you use as new source anirr::video::ITexture
object (that is also used as render target). The OpenGL native driver might not allow this and might need to copy the whole texture content every frame. That's another reason to not use the OpenGL native driver for real applications. It is just an fall-back and test-solution for the IrrIMGUI library development.