Improved on previously committed GUI engine internals docs

git-svn-id: svn+ssh://svn.code.sf.net/p/supertuxkart/code/main/trunk@5755 178a84e3-b1eb-0310-8ba1-8eac791a3b58
This commit is contained in:
auria 2010-08-18 01:38:18 +00:00
parent 8c578b19a4
commit eb52c1d4af

View File

@ -78,6 +78,8 @@
\ref code \ref code
\ref internals
\n \n
\n \n
\section widgets Widgets \section widgets Widgets
@ -459,11 +461,11 @@
similar way. similar way.
\n \n
\section Inside the GUI Engine \section internals Inside the GUI Engine
\subsection Widget Widget \subsection Widget Widget
SuperTuxKart's Widget class is a wrapper for the underlying irrlicht classes. SuperTuxKart's GUIEngine::Widget class is a wrapper for the underlying irrlicht classes.
This is needed for a couple reasons : This is needed for a couple reasons :
- irrlicht widgets do not do everything we want; so many STK widgets act as - irrlicht widgets do not do everything we want; so many STK widgets act as
composite widgets (create multiple irrlicht widgets and adds logic so they composite widgets (create multiple irrlicht widgets and adds logic so they
@ -472,50 +474,54 @@
This is simply an optimisation measure to prevent having to seek the file to disk This is simply an optimisation measure to prevent having to seek the file to disk
everytime a screen switch occurs. everytime a screen switch occurs.
Each widget contains one (or several) irr::gui::IGUIElement instances that represent Each widget contains one (or several) \c irr::gui::IGUIElement instances that represent
the irrlicht widget that is added to the IGUIEnvironment if the widget is currently the irrlicht widget that is added to the IGUIEnvironment if the widget is currently
shown; if a widget is not currently shown on screen (in irrlicht's IGUIEnvironment), shown; if a widget is not currently shown on screen (in irrlicht's \c IGUIEnvironment),
then its underlying IGUIElement pointer will be NULL but the widget continues to exist then its underlying \c IGUIElement pointer will be \c NULL but the widget continues to exist
and remains ready to re-create its underlying irrlicht widget when the screen it is and remains ready to re-create its underlying irrlicht widget when the screen it is
part of is added again. The method add() is used to tell a widget to create its irrlicht part of is added again. The method \c add() is used to tell a widget to create its irrlicht
counterpart in the IGUIEnvironment - but note that unless you start handling stuff manually counterpart in the \c IGUIEnvironment - but note that unless you start handling stuff manually
you do NOT need to invoke add() on each widget manually, since the Screen object the you do NOT need to invoke \c add() on each widget manually, since the parent GUIEngine::Screen object
widget is added to will do it automatically when it is shown. When the irrlicht IGUIEnvironment will do it automatically when it is shown. When the irrlicht \c IGUIEnvironment
is cleared (when irrlicht widgets are removed), it is very important to tell the Widgets is cleared (when irrlicht widgets are removed), it is very important to tell the Widgets
that their pointer to their IGUIElement counterpart is no more valid; this is done by calling that their pointer to their \cIGUIElement counterpart is no more valid; this is done by calling
elementRemoved() - but again unless you do manual manipulation of the widget tree, the Screen \c elementRemoved() - but again unless you do manual manipulation of the widget tree, the GUIEngine::Screen
object will take care of this for you. object will take care of this for you.
So, before trying to access the underlying irrlicht element of a GUIEngine::Widget, it is thus important to
check if the GUIEngine::Widget is currently added to the irr \c IGUIEnvironment. This can be done by
calling \c ->getIrrlichtElement() and checking if the result is \c NULL (if non-null, the widget is
currently added to the screen). Of course, in some circumstances, the check can be skipped because the
widget is known to be currently visible.
\subsection Screen Screen \subsection Screen Screen
This class holds a tree of Widget instances. It takes care of creating the tree from a This class holds a tree of GUIEngine::Widget instances. It takes care of creating the tree from
XML file upon loading (with the help of others, for instane the LayoutManager); it handles a XML file upon loading (with the help of others, for instane the GUIEngine::LayoutManager); it handles
calling add() on each of its Widget children when being added so that the corresponding calling \c add() on each of its GUIEngine::Widget children when being added - so that the corresponding
IGUIElement irrlicht widgets are added to the irrlicht scene; it also takes care of telling \c IGUIElement irrlicht widgets are added to the irrlicht scene. It also takes care of telling
its Widget children when their irrlicht IGUIElement counterpart was removed from the its GUIEngine::Widget children when their irrlicht \c IGUIElement counterpart was removed from the
IGUIEnvironment so that they don't carry dangling pointers. \c IGUIEnvironment so that they don't carry dangling pointers.
Before trying to access the underlying irrlicht element of a Widget, it is thus important to
check if the Widget is currently added to the irr IGUIEnvironment. This can be done by
calling ->getIrrlichtElement() and checking if the result is NULL (if non-null, the widget is
currently added to the screen)
The default behavior of the Screen object will be just fine for most basic purposes, but The default behavior of the GUIEngine::Screen object will be just fine for most basic purposes, but
if you want to build highly dynamic screens, you may need to get your hands dirty. Take a if you want to build highly dynamic screens, you may need to get your hands dirty. Take a
look at Screen::manualRemoveWidget() and Screen::manualAddWidget() if you wish to dynamically look at GUIEngine::Screen::manualRemoveWidget() and GUIEngine::Screen::manualAddWidget() if you wish to dynamically
modify the STK widget tree at runtime. If you get into this, be very careful about the relationship modify the STK widget tree at runtime. If you get into this, be very careful about the relationship
between the STK widget tree and the irrlicht widget tree. If you manualRemoveWidget() a STK between the STK widget tree and the irrlicht widget tree. If you \c manualRemoveWidget() a STK
widget that is currently visible on screen, this does not remove its associated irrlicht widget; widget that is currently visible on screen, this does not remove its associated irrlicht widget;
call widget->getIrrlichtElement()->remove() for that. When you removed a widget from a Screen you call \c widget->getIrrlichtElement()->remove() for that. When you removed a widget from a Screen you
are also responsible to call Widget::elementRemoved() on them to avoid dangling pointers. are also responsible to call \c Widget::elementRemoved() on them to avoid dangling pointers.
Similarly, a Widget that is not inside a Screen when the Screen is added will not have its add() Similarly, a GUIEngine::Widget that is not inside a GUIEngine::Screen when the screen is added will not
method be called automatically (so, for instance, if you manualAddWidget() a widget after a Screen have its \c add() method be called automatically (so, for instance, if you \c manualAddWidget() a widget
was shown, you will also need to call ->add() on the widget so that it is added to the irrlicht after a Screen was shown, you will also need to call \c ->add() on the widget so that it is added to the
GUI environment). irrlicht GUI environment).
As a final note, note that the Skin depends on both the irrlicht widget and the STK widget to
As a final note, note that the GUIEngine::Skin depends on both the irrlicht widget and the STK widget to
render widgets properly. So adding an irrlicht IGUIElement without having its SuperTuxKart render widgets properly. So adding an irrlicht IGUIElement without having its SuperTuxKart
Widget accessible through the current Screen may result in rendering glitches. GUIEngine::Widget accessible through the current GUIEngine::Screen (or a modal dialog) may result in
rendering glitches.
*/ */