Getting started
Installing
Download the latest version of the library and unzip it to a
directory of your choosing. This article assumes you unzipped it to
/Libraries/UI.
Directory structure
The following directory structure is used in the source distrubution.
-
library/IncludeThe include directory contains all the source code of the GUI library. It has six sub directories which also correspond with the namespaces used in the GUI library.
-
library/Include/borderThe border directory contains all files related to rendering borders.
-
library/Include/componentThe component directory contains all widgets, such as Buttons, Labels and MenuItems.
Please note that while all other directories have corresponding namespaces, the classes in the component directory are members of the ui namespace, and thus do not have a seperate ui::component namespace.
-
library/Include/eventThe event directory contains all event and listener interfaces in the library.
-
library/Include/layoutThe layout directory contains all layout managers.
-
library/Include/themeThe theme directory contains the default and basic themes. Alternative themes do not have to be placed in the same directory.
-
library/Include/utilThe util directory contains utility classes required for the GUI library, such as classes to represent points, rectangles and colors.
-
library/libContains the prebuilt (Windows) static library files.
Setting up your environment
You have to add the GUI library to the "include" and "library" directories of your compiler so that it can find the header files and static libraries to link against. An alternative is to place the GUI library in a subfolder of your project, but I recommend against this, because it makes upgrading to newer versions more difficult.
If you use Microsoft Visual Studio .NET
2003 or above, this is quite easy. Open up the IDE and go to the
"Tools" menu. From there, select "Options". In the dialog box that pops
up, open the "Projects" folder in the tree view and select "VC++
Directories". Using the "Show directories for: " dropdown box in the
upper right corner, select "Include folders" and create a new field for
C:\Libraries\UI\Library\Include. Do the same for
"Library files", but refer to
C:\Libraries\UI\Library\Lib. Hit OK and you're
done.
If you're using XCode (Mac OS X) it is even easier. Download the
framework distribution and unzip it to
/Library/Frameworks/ or
~/Library/Frameworks/. In XCode, use the "add
existing framework" option to add the library to your project. Also add
the framework to your "copy" and "link" action in your application's
target. That's all.
For other IDE's and compilers, consult the manual of your compiler or IDE on how to do this.
Compiling
If you need to change something in the library, or wish to compile it on a different compiler, you'll need to read this chapter. You might also want to rebuild the static libraries if you want to use different C++ runtime libraries; for example, the single-threaded runtime.The prebuilt static libraries use the multi-threaded DLL runtime, which is required for projects that use the Simple Directmedia Layer library (SDL). This is only required if you actually use SDL in your program, the GUI library itself does not require it.
Requirements
The requirements for compiling depend on which package you downloaded, both packages however require the following:
-
A recent C++ compiler.
The library has been tested and developed on MSVC7.1, MSVC8.0 and XCode 2.1(GCC 4.0). Other compilers might work as well, as no exotic C++ constructs or features are used. If you get it working on other compilers, please let me know.
-
A good standard template library implementation.
This usually comes with your C++ compiler (as it is part of C++), but not all implementations are adhering to the standard (MSVC6.X comes to mind). STLPort is a good alternative if the implementation that comes with your compiler does not work properly.
-
An OpenGL 1.1 or higher implementation.
The library uses OpenGL to render to the screen and thus requires OpenGL to be present on your system. The library only uses standard OpenGL 1.1 functions, no extensions are required.
-
Simple Directmedia Layer (SDL).
The UIDemo application requires SDL 1.2.X installed, as it is used to set up the window and handle input.
-
Simple Directmedia Layer image library.
The SDL_image library is used to load the font image and is thus required for compiling the UIDemo application. Please note that the SDL_image library should be compiled for the SDL version you are using (incompatible versions will result in errors.)
-
Simple Directmedia Layer (SDL).
The UIDemo application requires SDL 1.2.X installed, as it is used to set up the window and handle input.
-
Freetype 2.
Freetype 2 is used for font rendering in the UITest application and is thus required for compiling.
Compiling with Microsoft Visual Studio .NET 2003
If you have Microsoft Visual Studio .NET 2003 or above, you can
simply open the solution in the root directory
(/Libraries/UI) and hit compile. This should
compile the library.
Compiling with XCode 2.1
There is an XCode project included in the source distribution, which should work with XCode 2.1 or above.
Compiling with other compilers
Since there are no project files for other IDE's, you'll have to
create these yourself. To do this, create a new, empty project in your
IDE of choice and mimic the folder structure in
/Libraries/UI/Library/Include. Also add all the
header (*.h) and C++ (*.cpp) files to it.
Next, set the output directory of the static libraries to
/Libaries/UI/Lib/Release and
/Libraries/UI/Lib/Debug. Set the output filename of
the Release build to UI.lib and the Debug build to
UId.lib (the appended 'd' indicates it is a build
containing debug information.) Add a post-build macro (or something
similar) that moves the libraries to the
/Libraries/UI/Lib directory after they are
compiled, and you're done.
Note that you don't actually have to stick to this directory structure. If you know what you're doing, you're free to change the structure or place the libraries wherever you please.
Building a simple application
This chapter outlines the basics for building a simple application
using the GUI library, or integrating it with an existing application. The
code for this can be found in the UIDemo demo application. To start, link
the release build of your program with the UI.lib,
and the debug build with UId.lib static library
files.
Setting up your application
Create an instance of the Gui class. There
should only be one Gui instance in your whole
program, as it provides a single entry point for communication with the
library. Having only one Gui instance does not
mean you can only have one user interface in your program; you can have
multiple Frame instances, which are in essence
root nodes for user interfaces.
To make the library work correctly you need to pass several input
parameters to the Gui instance so that all user
interfaces in your program receive mouse and keyboard input and timing
information. Assuming you have created an instance of
Gui, named guiInstance you
should pass parameters like so:
// send frame delta time
guiInstance->importUpdate(deltaTime);
// send mouse x and y coordinates
guiInstance->importMouseMotion(x,y);These two import methods need to be called and updated every frame. The delta time is the time between the last and current frame in milliseconds, and is used to correctly calculate animations and interpolations in the GUI. The mouse coordinates are simply the current X and Y mouse coordinates. Besides these two methods, there are four other import methods related to mouse and keyboard events that need to be called, but only when their respective events occur.
// send mouse button released events
guiInstance->importMouseReleased(button);
// send mouse button pressed events
guiInstance->importMousePressed(button);
//send key release event
guiInstance->importKeyReleased(key,modifier);
// send key pressed event
guiInstance->importKeyPressed(key,modifier);The mouse related import methods only take one parameter, the
button that was pressed. Valid values are
MOUSE_BUTTON1, MOUSE_BUTTON2,
MOUSE_BUTTON3, MOUSE_SCROLL_UP and
MOUSE_SCROLL_DOWN and can be found in
event/MouseEvent.h. For a right handed mouse this
translates into the left mouse button, the right mouse button, and
optionally a third button, scroll wheel up and scroll wheel down
respectively.
The key related import methods both take two parameters, the key
code and modifier code. The key code is the code of the key that was
pressed or released and the modifier code the modifier that was active
while that key was pressed (such as shift or
ctrl.) Valid values can be found in
event/KeyEvent.h. Note that most key codes
correspond to the official ASCII key codes, which should simplify
sending key events from your application.
There are a few other important methods you need to call in order to use the library, such as the paint method which will be discussed in the next section. There are also several methods related to the font engine. Writing and setting up a font engine is required for components that render text to the screen (which almost all components do) and is discussed in a seperate article.
The last two methods of the GUI class are
addFrame and
removeFrame. Using these two methods you can
add or remove Frame instances to your user interface. Adding a Frame
ensures that it receives all user input and gets rendered in the proper
order. Removing it stops all user input and rendering for that
Frame. If you wish to disable an user interface,
it is preferred to disable it by calling the
hide method on it. This will hide the
Frame, but does not remove it from the
Gui instance. Note that a
Frame is initially hidden so you'll have to call
the show method for it to display.
Setting up OpenGL
To render the GUI, you'll need to set up OpenGL before calling the
paint method of your Gui instance. This is as
simple as switching to orthographic mode and calling the paint method,
as shown in the example below.
// go to orthographic mode
glMatrixMode(GL_PROJECTION);
glPushMatrix();
glLoadIdentity();
gluOrtho2D(0,width,height,0);
glMatrixMode(GL_MODELVIEW);
// paint the Gui
guiInstance->paint();
// switch back to perspective mode
glMatrixMode(GL_PROJECTION);
glPopMatrix();
glMatrixMode(GL_MODELVIEW);Especially note the gluOrtho2D call,
which is slightly unusual in that it sets up the 0,0 point in the upper
left corner, instead of the OpenGL default of having the 0,0 point in
the lower left corner. This is because the GUI uses the upper left
corner as its 0,0 point. This also means that any custom painting in the
GUI or derived classes have to take this into account.
If you are using glOrtho instead of gluOrtho2D make sure that the depth range is from -1 to 1, as this is required for the GUI to operate correctly.
In order for blending to work (which is used by most font engines
and the default theme of the Menu component) you might also wish to set
the blending function to GL_SRC_ALPHA,
GL_ONE_MINUS_SRC_ALPHA using
glBlendFunc. Your GUI should now render and
function properly.