massive improvements to looks of options and help menus

git-svn-id: svn+ssh://svn.code.sf.net/p/supertuxkart/code/main/branches/irrlicht@3456 178a84e3-b1eb-0310-8ba1-8eac791a3b58
This commit is contained in:
auria 2009-05-03 16:16:11 +00:00
parent 99c171e3f4
commit 720bbbaee0
14 changed files with 565 additions and 430 deletions

BIN
data/gui/glass_section.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.8 KiB

View File

@ -8,7 +8,7 @@
<icon-button id="page3" width="128" height="128" icon="gui/mode_ftl.png" text="Game Modes"/>
</tabs>
<spacer proportion="1" width="10" proportion="1"/>
<box proportion="1" width="100%" layout="vertical-row">
<label align="center" text="Make your rivals bite dust!"/>
@ -17,19 +17,22 @@
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="textures/bonusblock2.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="Collect blue boxes : they will give you weapons or other powerups"/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="Collect blue boxes : they will give you weapons or other powerups"/>
</div>
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="textures/nitro-particle.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="Collecting nitro allows you to get speed boosts whenever you wish by pressing the appropriate key. You can see your current level of nitro in the bar at the right of the game screen."/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="Collecting nitro allows you to get speed boosts whenever you wish by pressing the appropriate key. You can see your current level of nitro in the bar at the right of the game screen."/>
</div>
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="textures/gui_lock.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="If you see a button with a lock like this one, you need to complete a challenge to unlock it."/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="If you see a button with a lock like this one, you need to complete a challenge to unlock it."/>
</div>
<label align="left" word_wrap="true" width="100%" proportion="1" text="The 'sharp turn' key allows you to do sharp turns and have better control in tight curves"/>
@ -38,6 +41,7 @@
<label align="center" text="* Current key bindings can be seen/changed in menu Options"/>
</box>
<spacer width="50" height="45" />
</div>

View File

@ -8,8 +8,7 @@
<icon-button id="page3" width="128" height="128" icon="gui/mode_ftl.png" text="Game Modes"/>
</tabs>
<spacer proportion="1" width="10" proportion="1"/>
<box proportion="1" width="100%" layout="vertical-row">
<label align="center" text="To help you win, there are some powerups you can collect :"/>
<spacer height="25" width="10"/>
@ -23,7 +22,8 @@
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="textures/cake-icon.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="Cake - thrown at the closest rival, best on short ranges and long straights"/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="Cake - thrown at the closest rival, best on short ranges and long straights"/>
</div>
<div width="100%" proportion="1" layout="horizontal-row">
@ -35,7 +35,8 @@
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="textures/bowling-icon.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="Bowling Ball - bounces off walls. If you are looking back,\nit will be thrown backwards."/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="Bowling Ball - bounces off walls. If you are looking back,\nit will be thrown backwards."/>
</div>
<div width="100%" proportion="1" layout="horizontal-row">
@ -50,7 +51,7 @@
<label proportion="1" height="100%" align="left" word_wrap="true" text="Anchor - slows down greatly the kart in the first position"/>
</div>
</box>
<spacer width="50" height="45" />
</div>
<button id="back" x="20" y="-40" width="250" height="35" align="left" text="Back to main menu"/>

View File

@ -8,8 +8,7 @@
<icon-button id="page3" width="128" height="128" icon="gui/mode_ftl.png" text="Game Modes"/>
</tabs>
<spacer proportion="1" width="10" proportion="1"/>
<box proportion="1" width="100%" layout="vertical-row">
<label align="center" text="SuperTuxKart features several game modes (TO BE UPDATED FOR NEW GUI LAYOUT!!)"/>
<spacer height="25" width="10"/>
@ -17,31 +16,36 @@
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="gui/mode_normal.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="Regular Race (TODO - find a better name :( ) - all blows allowed, so catch weapons and make clever use of them!"/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="Regular Race (TODO - find a better name :( ) - all blows allowed, so catch weapons and make clever use of them!"/>
</div>
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="gui/mode_tt.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="Time Trial: Contains no powerups, so only your driving skills matter!"/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="Time Trial: Contains no powerups, so only your driving skills matter!"/>
</div>
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="gui/mode_ftl.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="Follow the leader: run for second place, as the last kart will be disqualified every time the counter hits zero. Beware : going in front of the leader will get you eliminated too!"/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="Follow the leader: run for second place, as the last kart will be disqualified every time the counter hits zero. Beware : going in front of the leader will get you eliminated too!"/>
</div>
<div width="100%" proportion="1" layout="horizontal-row">
<icon align="center" icon="gui/mode_3strikes.png"/>
<spacer width="25" height="25"/>
<label proportion="1" height="100%" align="left" word_wrap="true" text="3 Strikes Battle : only in multiplayer games. Hit others with weapons until they lose all their lives."/>
<label proportion="1" height="100%" align="left" word_wrap="true"
text="3 Strikes Battle : only in multiplayer games. Hit others with weapons until they lose all their lives."/>
</div>
<label proportion="1" width="100%" align="left" word_wrap="true" text="* Most of these game modes can also be played in a Grand Prix fashion : instead of playing a single race, you play many in a row. The better you rank, the more points you get. In the end, the player with the most points wins the cup."/>
</box>
<spacer width="50" height="45" />
</div>

View File

@ -1,4 +1,4 @@
<div x="5%" y="2%" width="90%" height="96%" layout="vertical-row" >
<div x="2%" y="2%" width="96%" height="96%" layout="vertical-row" >
<label align="center" text="SuperTuxKart Options"/>
@ -8,7 +8,9 @@
<icon-button id="controls" width="128" height="128" icon="gui/options_input.png" text="Controls"/>
</tabs>
<spacer height="25" width="10"/>
<box proportion="1" width="100%" layout="vertical-row">
<spacer height="15" width="10"/>
<div width="75%" height="40" layout="horizontal-row" >
<label proportion="2" height="100%" text="Music"/>
@ -21,7 +23,7 @@
<gauge id="music_volume" proportion="1" height="100%"/>
</div>
<spacer height="25" width="10"/>
<spacer height="15" width="10"/>
<div width="75%" height="40" layout="horizontal-row" >
<label proportion="2" height="100%" text="Sound Effects"/>
@ -35,7 +37,7 @@
</div>
<spacer proportion="1" width="10"/>
<spacer height="20" width="10"/>
<div width="75%" height="40" layout="horizontal-row" >
@ -45,8 +47,13 @@
<label proportion="1" height="100%" text="Fullscreen"/>
</div>
<scrollable_ribbon id="resolutions" proportion="2" text="all" width="100%" square_items="false" align="center" child_width="128" child_height="128" />
<scrollable_ribbon id="resolutions" proportion="2" text="all" width="100%" square_items="false"
align="center" child_width="128" child_height="128" max_height="150" />
<button id="apply_resolution" width="20%" height="30" text="Apply video changes" />
</box>
<spacer height="15" width="10"/>
</div>

View File

@ -1,4 +1,4 @@
<div x="5%" y="2%" width="90%" height="96%" layout="vertical-row" >
<div x="2%" y="2%" width="96%" height="96%" layout="vertical-row" >
<label align="center" text="SuperTuxKart Options"/>
@ -8,7 +8,7 @@
<icon-button id="controls" width="128" height="128" icon="gui/options_input.png" text="Controls"/>
</tabs>
<spacer height="15" width="10" />
<box proportion="1" width="100%" layout="vertical-row">
<scrollable_ribbon id="devices" proportion="3" text="all" width="100%" square_items="false" align="center" child_width="256" child_height="128" />
@ -76,5 +76,8 @@
<button id="binding_look_back" proportion="1" height="100%" text="[none]"/>
</div>
</box>
<spacer height="15" width="10"/>
</div>

View File

@ -1,4 +1,4 @@
<div x="5%" y="2%" width="90%" height="96%" layout="vertical-row" >
<div x="2%" y="2%" width="96%" height="96%" layout="vertical-row" >
<label align="center" text="SuperTuxKart Options"/>
@ -8,8 +8,12 @@
<icon-button id="controls" width="128" height="128" icon="gui/options_input.png" text="Controls"/>
</tabs>
<spacer proportion="1" width="10" proportion="1"/>
<box proportion="1" width="100%" layout="vertical-row">
<spacer width="20" height="20"/>
<list id="players" proportion="5" width="75%" align="center"/>
<spacer width="20" height="20"/>
</box>
<spacer height="15" width="10"/>
</div>

View File

@ -12,7 +12,7 @@
namespace GUIEngine
{
IGUIEnvironment* g_env;
IGUISkin* g_skin = NULL;
Skin* g_skin = NULL;
IGUIFont* g_font;
IrrlichtDevice* g_device;
irr::video::IVideoDriver* g_driver;
@ -173,16 +173,19 @@ void init(IrrlichtDevice* device_a, IVideoDriver* driver_a, void (*eventCallback
//g_skin->setFont(g_env->getBuiltInFont(), EGDF_TOOLTIP);
}
// -----------------------------------------------------------------------------
/** transmit event to user event callback (out of encapsulated GUI module) */
void transmitEvent(Widget* widget, std::string& name)
{
assert(g_event_callback != NULL);
g_event_callback(widget, name);
}
// -----------------------------------------------------------------------------
void render(float elapsed_time)
{
GUIEngine::dt = elapsed_time;
// ---- background image
// on one end, making these static is not too clean.
// on another end, these variables are really only used locally,
// and making them static avoids doing the same stupid computations every frame
@ -224,6 +227,10 @@ void render(float elapsed_time)
//GUIEngine::getDriver()->draw2DRectangle( SColor(255, 0, 150, 0), rect );
// ---- render sections (bounding boxes)
g_skin->renderSections();
// ---- let irrLicht do the rest (the Skin object will be called for further render)
g_env->drawAll();
}

View File

@ -23,6 +23,8 @@ namespace GUIEngine
class Screen : public IEventReceiver
{
friend class Skin;
bool m_loaded;
std::string m_filename;
ptr_vector<Widget, HOLD> m_widgets;

View File

@ -38,6 +38,13 @@ void parseScreenFileDiv(irr::io::IrrXMLReader* xml, ptr_vector<Widget>& append_t
type = WTYPE_DIV;
append_to.push_back(new Widget());
}
else if (!strcmp("box", xml->getNodeName()))
{
type = WTYPE_DIV;
Widget* w = new Widget();
w->m_show_bounding_box = true;
append_to.push_back(w);
}
else if (!strcmp("ribbon", xml->getNodeName()))
{
type = WTYPE_RIBBON;
@ -162,6 +169,8 @@ if(prop_name != NULL) widget.m_properties[prop_flag] = prop_name; else widget.m_
// we're done parsing this 'div', return one step back in the recursive call
if (!strcmp("div", xml->getNodeName()))
return;
if (!strcmp("box", xml->getNodeName()))
return;
// we're done parsing this 'ribbon', return one step back in the recursive call
if (!strcmp("ribbon", xml->getNodeName()) ||

View File

@ -38,6 +38,8 @@ Skin::Skin(IGUISkin* fallback_skin)
m_tex_fcheckbox = GUIEngine::getDriver()->getTexture( (file_manager->getGUIDir() + "/glasscheckbox_focus.png").c_str() );
m_tex_dcheckbox = GUIEngine::getDriver()->getTexture( (file_manager->getGUIDir() + "/glasscheckbox_checked.png").c_str() );
m_tex_dfcheckbox = GUIEngine::getDriver()->getTexture( (file_manager->getGUIDir() + "/glasscheckbox_checked_focus.png").c_str() );
m_tex_section = GUIEngine::getDriver()->getTexture( (file_manager->getGUIDir() + "/glass_section.png").c_str() );
}
Skin::~Skin()
@ -46,12 +48,35 @@ Skin::~Skin()
}
void Skin::drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture* source,
const int left_border, const int right_border,
const int top_border, const int bottom_border,
const bool preserve_h_aspect_ratios,
const float border_out_portion, int areas, const bool vertical_flip)
/** load default values */
BoxRenderParams::BoxRenderParams()
{
left_border = 0;
right_border = 0;
top_border = 0;
bottom_border = 0;
preserve_h_aspect_ratios = false;
hborder_out_portion = 0.5;
vborder_out_portion = 1.0;
areas = BODY | LEFT | RIGHT | TOP | BOTTOM;
vertical_flip = false;
}
void Skin::drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture* source, const BoxRenderParams& params)
{
const int left_border = params.left_border;
const int right_border = params.right_border;
const int top_border = params.top_border;
const int bottom_border = params.bottom_border;
const bool preserve_h_aspect_ratios = params.preserve_h_aspect_ratios;
const float hborder_out_portion = params.hborder_out_portion;
const float vborder_out_portion = params.vborder_out_portion;
int areas = params.areas;
const bool vertical_flip = params.vertical_flip;
// FIXME? - lots of things here will be re-calculated every frame, which is useless since
// widgets won't move, so they'd only need to be calculated once.
const int texture_w = source->getSize().Width;
@ -95,7 +120,7 @@ void Skin::drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture
/*
The dest area is split this way. Borders can go a bit beyond the given area so
components inside don't go over the borders
(how much it exceeds horizontally is specified in 'border_out_portion'. vertically is always the totality)
(how much it exceeds horizontally is specified in 'hborder_out_portion'. vertically is always the totality)
a----b--------------------c----+
| | | |
@ -132,27 +157,21 @@ void Skin::drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture
int dest_top_border = (int)(top_border *std::min<float>(yscale, 1.0));
int dest_bottom_border = (int)(bottom_border*std::min<float>(yscale, 1.0));
/*
if(vertical_flip)
{
int temp = dest_bottom_border;
dest_bottom_border = dest_top_border;
dest_top_border = temp;
}*/
const float border_in_portion = 1 - border_out_portion;
const float hborder_in_portion = 1 - hborder_out_portion;
const float vborder_in_portion = 1 - vborder_out_portion;
const int ax = (int)(dest_x - dest_left_border*border_out_portion);
const int ay = dest_y - dest_top_border;
const int ax = (int)(dest_x - dest_left_border*hborder_out_portion);
const int ay = (int)(dest_y - dest_top_border*vborder_out_portion);
const int bx = (int)(dest_x + dest_left_border*border_in_portion);
const int bx = (int)(dest_x + dest_left_border*hborder_in_portion);
const int by = ay;
const int cx = (int)(dest_x2 - dest_right_border*border_in_portion);
const int cx = (int)(dest_x2 - dest_right_border*hborder_in_portion);
const int cy = ay;
const int dx = ax;
const int dy = dest_y;
const int dy = (int)(dest_y + dest_top_border*vborder_in_portion);
const int ex = bx;
const int ey = dy;
@ -160,11 +179,11 @@ void Skin::drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture
const int fx = cx;
const int fy = dy;
const int gx = (int)(dest_x2 + dest_right_border*border_out_portion);
const int gx = (int)(dest_x2 + dest_right_border*hborder_out_portion);
const int gy = dy;
const int hx = ax;
const int hy = dest_y2;
const int hy = (int)(dest_y2 - dest_bottom_border*vborder_in_portion);
const int ix = bx;
const int iy = hy;
@ -176,7 +195,7 @@ void Skin::drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture
const int ky = hy;
const int lx = bx;
const int ly = dest_y2 + dest_bottom_border;
const int ly = (int)(dest_y2 + dest_bottom_border*vborder_out_portion);
const int mx = cx;
const int my = ly;
@ -235,51 +254,51 @@ X.LowerRightCorner.Y = y1;}
#undef FLIP_Y
}
if((areas & LEFT) != 0)
if((areas & BoxRenderParams::LEFT) != 0)
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_left, source_area_left,
0 /* no clipping */, 0, true /* alpha */);
}
if((areas & BODY) != 0)
if((areas & BoxRenderParams::BODY) != 0)
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_center, source_area_center,
0 /* no clipping */, 0, true /* alpha */);
}
if((areas & RIGHT) != 0)
if((areas & BoxRenderParams::RIGHT) != 0)
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_right, source_area_right,
0 /* no clipping */, 0, true /* alpha */);
}
if((areas & TOP) != 0)
if((areas & BoxRenderParams::TOP) != 0)
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_top, source_area_top,
0 /* no clipping */, 0, true /* alpha */);
}
if((areas & BOTTOM) != 0)
if((areas & BoxRenderParams::BOTTOM) != 0)
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_bottom, source_area_bottom,
0 /* no clipping */, 0, true /* alpha */);
}
if( ((areas & LEFT) != 0) && ((areas & TOP) != 0) )
if( ((areas & BoxRenderParams::LEFT) != 0) && ((areas & BoxRenderParams::TOP) != 0) )
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_top_left, source_area_top_left,
0 /* no clipping */, 0, true /* alpha */);
}
if( ((areas & RIGHT) != 0) && ((areas & TOP) != 0) )
if( ((areas & BoxRenderParams::RIGHT) != 0) && ((areas & BoxRenderParams::TOP) != 0) )
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_top_right, source_area_top_right,
0 /* no clipping */, 0, true /* alpha */);
}
if( ((areas & LEFT) != 0) && ((areas & BOTTOM) != 0) )
if( ((areas & BoxRenderParams::LEFT) != 0) && ((areas & BoxRenderParams::BOTTOM) != 0) )
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_bottom_left, source_area_bottom_left,
0 /* no clipping */, 0, true /* alpha */);
}
if( ((areas & RIGHT) != 0) && ((areas & BOTTOM) != 0) )
if( ((areas & BoxRenderParams::RIGHT) != 0) && ((areas & BoxRenderParams::BOTTOM) != 0) )
{
GUIEngine::getDriver()->draw2DImage(source, dest_area_bottom_right, source_area_bottom_right,
0 /* no clipping */, 0, true /* alpha */);
@ -290,15 +309,17 @@ X.LowerRightCorner.Y = y1;}
void Skin::drawButton(const core::rect< s32 > &rect, const bool pressed, const bool focused)
{
// FIXME - move these numbers to a config file
const int left_border = 80;
const int right_border = 80;
const int border_above = 0;
const int border_below = 36;
static BoxRenderParams params;
drawBoxFromStretchableTexture(rect, (focused ? m_tex_fbutton : m_tex_button),
left_border, right_border,
border_above, border_below, true /* horizontal aspect ratio kept */);
// FIXME - move these numbers to a config file
params.left_border = 80;
params.right_border = 80;
params.top_border = 0;
params.bottom_border = 36;
params.preserve_h_aspect_ratios = true;
drawBoxFromStretchableTexture(rect, (focused ? m_tex_fbutton : m_tex_button), params);
}
void Skin::drawRibbon(const core::rect< s32 > &rect, const Widget* widget, const bool pressed, bool focused)
@ -344,11 +365,12 @@ void Skin::drawRibbonChild(const core::rect< s32 > &rect, const Widget* widget,
{
// ribbons containing buttons are actually tabs
static BoxRenderParams params;
// FIXME - specify in file, don't hardcode
int left_border = 75;
int right_border = 75;
int border_above = 0;
int border_below = 15;
params.left_border = 75;
params.right_border = 75;
params.top_border = 0;
params.bottom_border = 15;
// automatically guess from position on-screen if tabs go up or down
const bool vertical_flip = rect.UpperLeftCorner.Y < GUIEngine::getDriver()->getCurrentRenderTargetSize().Height/2;
@ -362,6 +384,8 @@ void Skin::drawRibbonChild(const core::rect< s32 > &rect, const Widget* widget,
core::rect< s32 > rect2 = rect;
params.hborder_out_portion = portion_out;
params.vertical_flip = vertical_flip;
if (mark_selected)
{
@ -371,10 +395,7 @@ void Skin::drawRibbonChild(const core::rect< s32 > &rect, const Widget* widget,
else
rect2.LowerRightCorner.Y += 10;
drawBoxFromStretchableTexture(rect2, (focused || parent_focused ? m_tex_ftab : m_tex_dtab),
left_border, right_border,
border_above, border_below, false /* horizontal aspect ratio not kept */, portion_out,
BODY | LEFT | RIGHT | TOP | BOTTOM, vertical_flip);
drawBoxFromStretchableTexture(rect2, (focused || parent_focused ? m_tex_ftab : m_tex_dtab), params);
/*
GUIEngine::getDriver()->draw2DLine( core::position2d< s32 >(rect2.UpperLeftCorner.X,rect2.LowerRightCorner.Y),
@ -388,10 +409,7 @@ void Skin::drawRibbonChild(const core::rect< s32 > &rect, const Widget* widget,
}
else
{
drawBoxFromStretchableTexture(rect2, m_tex_tab,
left_border, right_border,
border_above, border_below, false /* horizontal aspect ratio not kept */, portion_out,
BODY | LEFT | RIGHT | TOP | BOTTOM, vertical_flip);
drawBoxFromStretchableTexture(rect2, m_tex_tab, params);
}
}
@ -471,10 +489,14 @@ void Skin::drawRibbonChild(const core::rect< s32 > &rect, const Widget* widget,
core::rect<s32> source_area = core::rect<s32>(0, 0, texture_w, texture_h);
drawBoxFromStretchableTexture(rect, m_tex_squarefocus,
6 /* left border */, 6 /* rightborder */,
6 /* top border */, 6 /* bottom border */,
false /* horizontal aspect ratio not kept */, 1);
static BoxRenderParams params;
params.left_border = 6;
params.right_border = 6;
params.top_border = 6;
params.bottom_border = 6;
params.hborder_out_portion = 1.0;
drawBoxFromStretchableTexture(rect, m_tex_squarefocus, params);
}
} // end if mark_selected
@ -484,12 +506,6 @@ void Skin::drawRibbonChild(const core::rect< s32 > &rect, const Widget* widget,
void Skin::drawSpinnerBody(const core::rect< s32 > &rect, const Widget* widget, const bool pressed, bool focused)
{
// FIXME - move these numbers to a config file
const int left_border = 110;
const int right_border = 110;
const int border_above = 0;
const int border_below = 36;
if(!focused)
{
IGUIElement* focused_widget = GUIEngine::getGUIEnv()->getFocus();
@ -505,18 +521,22 @@ void Skin::drawSpinnerBody(const core::rect< s32 > &rect, const Widget* widget,
}
}
drawBoxFromStretchableTexture(rect, (focused || pressed ? m_tex_fspinner : m_tex_spinner),
left_border, right_border,
border_above, border_below, true /* horizontal aspect ratio kept */, 0);
static BoxRenderParams params;
// FIXME - move these numbers to a config file
params.left_border = 110;
params.right_border = 110;
params.top_border = 0;
params.bottom_border = 36;
params.preserve_h_aspect_ratios = true;
params.hborder_out_portion = 0.0f;
drawBoxFromStretchableTexture(rect, (focused || pressed ? m_tex_fspinner : m_tex_spinner), params);
}
void Skin::drawSpinnerChild(const core::rect< s32 > &rect, Widget* widget, const bool pressed, bool focused)
{
// FIXME - move these numbers to a config file
const int left_border = 110;
const int right_border = 110;
const int border_above = 0;
const int border_below = 36;
if(pressed)
{
@ -525,19 +545,26 @@ void Skin::drawSpinnerChild(const core::rect< s32 > &rect, Widget* widget, const
//std::cout << "drawing spinner child " << widget->m_properties[PROP_ID].c_str() << std::endl;
if (widget->m_properties[PROP_ID] == "left") areas = LEFT;
else if (widget->m_properties[PROP_ID] == "right") areas = RIGHT;
if (widget->m_properties[PROP_ID] == "left") areas = BoxRenderParams::LEFT;
else if (widget->m_properties[PROP_ID] == "right") areas = BoxRenderParams::RIGHT;
else return;
core::rect< s32 > rect2 = core::rect< s32 >( spinner->x, spinner->y,
spinner->x + spinner->w,
spinner->y + spinner->h );
drawBoxFromStretchableTexture(rect2, m_tex_dspinner,
left_border, right_border,
border_above, border_below,
true /* horizontal aspect ratio kept */,
0, areas);
static BoxRenderParams params;
// FIXME - move these numbers to a config file
params.left_border = 110;
params.right_border = 110;
params.top_border = 0;
params.bottom_border = 36;
params.preserve_h_aspect_ratios = true;
params.hborder_out_portion = 0.0f;
params.areas = areas;
drawBoxFromStretchableTexture(rect2, m_tex_dspinner, params);
}
@ -545,16 +572,16 @@ void Skin::drawSpinnerChild(const core::rect< s32 > &rect, Widget* widget, const
void Skin::drawGauge(const core::rect< s32 > &rect, Widget* widget, bool focused)
{
static BoxRenderParams params;
// FIXME - move these numbers to a config file
const int left_border = 110;
const int right_border = 110;
const int border_above = 0;
const int border_below = 36;
params.left_border = 110;
params.right_border = 110;
params.top_border = 0;
params.bottom_border = 36;
drawBoxFromStretchableTexture(rect, (focused ? m_tex_fspinner : m_tex_spinner),
left_border, right_border,
border_above, border_below,
false /* horizontal aspect ratio kept */, -0.9);
params.hborder_out_portion = -0.9;
drawBoxFromStretchableTexture(rect, (focused ? m_tex_fspinner : m_tex_spinner), params);
}
void Skin::drawGaugeFill(const core::rect< s32 > &rect, Widget* widget, bool focused)
{
@ -608,6 +635,57 @@ void Skin::drawCheckBox(const core::rect< s32 > &rect, Widget* widget, bool focu
}
}
/** recusrive function to render all sections (recursion allows to easily travesre the tree of children and sub-children) */
void Skin::renderSections(ptr_vector<Widget>* within_vector)
{
if(within_vector == NULL) within_vector = &getCurrentScreen()->m_widgets;
const unsigned short widgets_amount = within_vector->size();
for(int n=0; n<widgets_amount; n++)
{
Widget& widget = (*within_vector)[n];
if(widget.m_type == WTYPE_DIV)
{
if(widget.m_show_bounding_box)
{
core::rect< s32 > rect = core::rect<s32>( widget.x, widget.y, widget.x + widget.w, widget.y + widget.h );
//getDriver()->draw2DImage(g_skin->m_tex_section, rect, source_area,
// 0 /* no clipping */, 0, true /* alpha */);
static BoxRenderParams params;
params.left_border = 15;
params.right_border = 15;
params.top_border = 15;
params.bottom_border = 15;
params.hborder_out_portion = 1.0;
params.vborder_out_portion = 0.2;
drawBoxFromStretchableTexture( rect, m_tex_section, params );
/*
void drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture* source,
const int left_border, const int right_border,
const int top_border, const int bottom_border,
const bool preserve_h_aspect_ratios=false,
const float hborder_out_portion = 0.5,
int areas = BODY | LEFT | RIGHT | TOP | BOTTOM,
const bool vertical_flip=false);
*/
}
else
{
renderSections( &widget.m_children );
}
}
} // next
}
#if 0
#pragma mark -
#pragma mark irrlicht skin functions

View File

@ -2,6 +2,8 @@
#define HEADER_SKIN_HPP
#include <irrlicht.h>
#include "ptr_vector.hpp"
using namespace irr;
using namespace core;
using namespace scene;
@ -14,12 +16,26 @@ namespace GUIEngine
class Widget;
// areas
const int BODY = 1;
const int LEFT = 2;
const int RIGHT = 4;
const int TOP = 8;
const int BOTTOM = 16;
/** class containing render params for the 'drawBoxFromStretchableTexture' function */
class BoxRenderParams
{
public:
int left_border, right_border, top_border, bottom_border;
bool preserve_h_aspect_ratios;
float hborder_out_portion, vborder_out_portion;
bool vertical_flip;
/** bitmap containing which areas to render */
int areas;
// possible values in areas
static const int BODY = 1;
static const int LEFT = 2;
static const int RIGHT = 4;
static const int TOP = 8;
static const int BOTTOM = 16;
BoxRenderParams();
};
class Skin : public IGUISkin
{
@ -47,15 +63,12 @@ class Skin : public IGUISkin
void drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture* source,
const int left_border, const int right_border,
const int top_border, const int bottom_border,
const bool preserve_h_aspect_ratios=false,
const float border_out_portion = 0.5,
int areas = BODY | LEFT | RIGHT | TOP | BOTTOM,
const bool vertical_flip=false);
void drawBoxFromStretchableTexture(const core::rect< s32 > &dest, ITexture* source, const BoxRenderParams& params);
public:
ITexture* m_tex_section;
Skin(IGUISkin* fallback_skin);
~Skin();
@ -70,6 +83,8 @@ public:
void drawGaugeFill(const core::rect< s32 > &rect, Widget* widget, bool focused);
void drawCheckBox(const core::rect< s32 > &rect, Widget* widget, bool focused);
void renderSections(ptr_vector<Widget>* within_vector=NULL);
// irrlicht's callbacks
virtual void draw2DRectangle (IGUIElement *element, const video::SColor &color, const core::rect< s32 > &pos, const core::rect< s32 > *clip);
virtual void draw3DButtonPanePressed (IGUIElement *element, const core::rect< s32 > &rect, const core::rect< s32 > *clip);

View File

@ -43,6 +43,7 @@ Widget::Widget()
m_type = WTYPE_NONE;
m_selected = false;
m_event_handler = NULL;
m_show_bounding_box = false;
}
// -----------------------------------------------------------------------------
/**

View File

@ -108,8 +108,11 @@ namespace GUIEngine
static bool convertToCoord(std::string& x, int* absolute, int* percentage);
public:
Widget();
virtual ~Widget() {}
bool m_show_bounding_box;
/**
* If this widget has any children, they go here. Children can be either
* specified in the XML file (e.g. Ribbon or Div children), or can also
@ -139,9 +142,6 @@ namespace GUIEngine
/** A map that holds values for all specified widget properties (in the XML file)*/
std::map<Property, std::string> m_properties;
Widget();
static void resetIDCounters();
bool isSelected() const { return m_selected; }