Added YET more files I forgot in earlier commits xD
git-svn-id: svn+ssh://svn.code.sf.net/p/supertuxkart/code/main/trunk@5748 178a84e3-b1eb-0310-8ba1-8eac791a3b58
This commit is contained in:
parent
4e48bbd66b
commit
e3fa74187d
228
src/guiengine/abstract_top_level_container.cpp
Normal file
228
src/guiengine/abstract_top_level_container.cpp
Normal file
@ -0,0 +1,228 @@
|
||||
// SuperTuxKart - a fun racing game with go-kart
|
||||
// Copyright (C) 2010 Marianne Gagnon
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU General Public License
|
||||
// as published by the Free Software Foundation; either version 3
|
||||
// of the License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
|
||||
#include "graphics/irr_driver.hpp"
|
||||
#include "guiengine/abstract_top_level_container.hpp"
|
||||
#include "guiengine/engine.hpp"
|
||||
#include "guiengine/scalable_font.hpp"
|
||||
#include "guiengine/widget.hpp"
|
||||
#include "io/file_manager.hpp"
|
||||
#include "utils/ptr_vector.hpp"
|
||||
#include <sstream>
|
||||
|
||||
using namespace GUIEngine;
|
||||
|
||||
#include "irrlicht.h"
|
||||
using namespace irr;
|
||||
using namespace core;
|
||||
using namespace scene;
|
||||
using namespace video;
|
||||
using namespace io;
|
||||
using namespace gui;
|
||||
|
||||
void AbstractTopLevelContainer::addWidgetsRecursively(ptr_vector<Widget>& widgets, Widget* parent)
|
||||
{
|
||||
const unsigned short widgets_amount = widgets.size();
|
||||
|
||||
// ------- add widgets
|
||||
for (int n=0; n<widgets_amount; n++)
|
||||
{
|
||||
if (widgets[n].getType() == WTYPE_DIV)
|
||||
{
|
||||
widgets[n].add(); // Will do nothing, but will maybe reserve an ID
|
||||
addWidgetsRecursively(widgets[n].m_children, &widgets[n]);
|
||||
}
|
||||
else
|
||||
{
|
||||
// warn if widget has no dimensions (except for ribbons and icons, where it is normal since it
|
||||
// adjusts to its contents)
|
||||
if ((widgets[n].m_w < 1 || widgets[n].m_h < 1) &&
|
||||
widgets[n].getType() != WTYPE_RIBBON &&
|
||||
widgets[n].getType() != WTYPE_ICON_BUTTON)
|
||||
{
|
||||
std::cerr << "/!\\ Warning /!\\ : widget " << widgets[n].m_properties[PROP_ID].c_str() << " has no dimensions" << std::endl;
|
||||
}
|
||||
|
||||
if (widgets[n].m_x == -1 || widgets[n].m_y == -1)
|
||||
{
|
||||
std::cerr << "/!\\ Warning /!\\ : widget " << widgets[n].m_properties[PROP_ID].c_str() << " has no position" << std::endl;
|
||||
}
|
||||
|
||||
widgets[n].add();
|
||||
}
|
||||
|
||||
} // next widget
|
||||
|
||||
} // addWidgetsRecursively
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
bool isMyChildHelperFunc(const ptr_vector<Widget>* within, const Widget* widget)
|
||||
{
|
||||
if (within->size() == 0) return false;
|
||||
|
||||
if (within->contains(widget))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
const int count = within->size();
|
||||
for (int n=0; n<count; n++)
|
||||
{
|
||||
if (isMyChildHelperFunc(&within->getConst(n)->getChildren(), widget))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool AbstractTopLevelContainer::isMyChild(Widget* widget) const
|
||||
{
|
||||
return isMyChildHelperFunc(&m_widgets, widget);
|
||||
}
|
||||
|
||||
|
||||
|
||||
Widget* AbstractTopLevelContainer::getWidget(const char* name)
|
||||
{
|
||||
return getWidget(name, &m_widgets);
|
||||
} // getWidget
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
Widget* AbstractTopLevelContainer::getWidget(const int id)
|
||||
{
|
||||
return getWidget(id, &m_widgets);
|
||||
} // getWidget
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
Widget* AbstractTopLevelContainer::getWidget(const char* name, ptr_vector<Widget>* within_vector)
|
||||
{
|
||||
const unsigned short widgets_amount = within_vector->size();
|
||||
|
||||
for(int n=0; n<widgets_amount; n++)
|
||||
{
|
||||
Widget& widget = (*within_vector)[n];
|
||||
|
||||
if (widget.m_properties[PROP_ID] == name) return &widget;
|
||||
|
||||
if (widget.searchInsideMe() && widget.m_children.size() > 0)
|
||||
{
|
||||
Widget* el = getWidget(name, &(widget.m_children));
|
||||
if(el != NULL) return el;
|
||||
}
|
||||
} // next
|
||||
|
||||
return NULL;
|
||||
} // getWidget
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
Widget* AbstractTopLevelContainer::getWidget(const int id, ptr_vector<Widget>* within_vector)
|
||||
{
|
||||
const unsigned short widgets_amount = within_vector->size();
|
||||
|
||||
for (int n=0; n<widgets_amount; n++)
|
||||
{
|
||||
Widget& widget = (*within_vector)[n];
|
||||
|
||||
if (widget.m_element != NULL && widget.getIrrlichtElement()->getID() == id) return &widget;
|
||||
|
||||
if (widget.searchInsideMe() && widget.getChildren().size() > 0)
|
||||
{
|
||||
// std::cout << "widget = <" << widget.m_properties[PROP_ID].c_str()
|
||||
// << "> widget.m_children.size()=" << widget.m_children.size() << std::endl;
|
||||
Widget* el = getWidget(id, &(widget.m_children));
|
||||
if(el != NULL) return el;
|
||||
}
|
||||
} // next
|
||||
|
||||
return NULL;
|
||||
} // getWidget
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
Widget* AbstractTopLevelContainer::getFirstWidget(ptr_vector<Widget>* within_vector)
|
||||
{
|
||||
if (m_first_widget != NULL) return m_first_widget;
|
||||
if (within_vector == NULL) within_vector = &m_widgets;
|
||||
|
||||
for (int i = 0; i < within_vector->size(); i++)
|
||||
{
|
||||
if (!within_vector->get(i)->m_focusable) continue;
|
||||
|
||||
// if container, also checks children (FIXME: don't hardcode which types to avoid descending into)
|
||||
if (within_vector->get(i)->m_children.size() > 0 &&
|
||||
within_vector->get(i)->getType() != WTYPE_RIBBON &&
|
||||
within_vector->get(i)->getType() != WTYPE_SPINNER)
|
||||
{
|
||||
Widget* w = getFirstWidget(&within_vector->get(i)->m_children);
|
||||
if (w != NULL) return w;
|
||||
}
|
||||
|
||||
Widget* item = within_vector->get(i);
|
||||
if (item->getIrrlichtElement() == NULL ||
|
||||
item->getIrrlichtElement()->getTabOrder() == -1 ||
|
||||
item->getIrrlichtElement()->getTabOrder() >= 1000 /* non-tabbing items are given such IDs */ ||
|
||||
!item->m_focusable)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
return item;
|
||||
}
|
||||
return NULL;
|
||||
} // getFirstWidget
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
Widget* AbstractTopLevelContainer::getLastWidget(ptr_vector<Widget>* within_vector)
|
||||
{
|
||||
if (m_last_widget != NULL) return m_last_widget;
|
||||
if (within_vector == NULL) within_vector = &m_widgets;
|
||||
|
||||
for (int i = within_vector->size()-1; i >= 0; i--)
|
||||
{
|
||||
if (!within_vector->get(i)->m_focusable) continue;
|
||||
|
||||
// if container, also checks children
|
||||
if (within_vector->get(i)->getChildren().size() > 0 &&
|
||||
within_vector->get(i)->getType() != WTYPE_RIBBON &&
|
||||
within_vector->get(i)->getType() != WTYPE_SPINNER)
|
||||
{
|
||||
Widget* w = getLastWidget(&within_vector->get(i)->m_children);
|
||||
if (w != NULL) return w;
|
||||
}
|
||||
|
||||
Widget* item = within_vector->get(i);
|
||||
if (item->getIrrlichtElement() == NULL ||
|
||||
item->getIrrlichtElement()->getTabOrder() == -1 ||
|
||||
item->getIrrlichtElement()->getTabOrder() >= 1000 /* non-tabbing items are given such IDs */ ||
|
||||
!item->m_focusable)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
return item;
|
||||
}
|
||||
return NULL;
|
||||
} // getLastWidget
|
||||
|
||||
// ----------------------------------------------------------------------------
|
90
src/guiengine/abstract_top_level_container.hpp
Normal file
90
src/guiengine/abstract_top_level_container.hpp
Normal file
@ -0,0 +1,90 @@
|
||||
// SuperTuxKart - a fun racing game with go-kart
|
||||
// Copyright (C) 2009 Marianne Gagnon
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU General Public License
|
||||
// as published by the Free Software Foundation; either version 3
|
||||
// of the License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
|
||||
#ifndef __TOP_LEVEL_CONT_HPP__
|
||||
#define __TOP_LEVEL_CONT_HPP__
|
||||
|
||||
#include <cstring> // for NULL
|
||||
#include "utils/ptr_vector.hpp"
|
||||
|
||||
#include "guiengine/widget.hpp"
|
||||
|
||||
namespace GUIEngine
|
||||
{
|
||||
class Widget;
|
||||
|
||||
class AbstractTopLevelContainer
|
||||
{
|
||||
protected:
|
||||
/** the widgets in this screen */
|
||||
ptr_vector<Widget, HOLD> m_widgets;
|
||||
|
||||
/**
|
||||
* AbstractTopLevelContainer is generally able to determine its first widget just fine,
|
||||
* but in highly complex screens (e.g. multiplayer kart selection) you can help it by
|
||||
* providing the first widget manually.
|
||||
*/
|
||||
Widget* m_first_widget;
|
||||
|
||||
/**
|
||||
* AbstractTopLevelContainer is generally able to determine its last widget just fine,
|
||||
* but in highly complex screens (e.g. multiplayer kart selection) you can help it by
|
||||
* providing the first widget manually.
|
||||
*/
|
||||
Widget* m_last_widget;
|
||||
|
||||
void addWidgetsRecursively(ptr_vector<Widget>& widgets, Widget* parent=NULL);
|
||||
|
||||
|
||||
public:
|
||||
virtual ~AbstractTopLevelContainer() {}
|
||||
|
||||
virtual int getWidth() = 0;
|
||||
virtual int getHeight() = 0;
|
||||
|
||||
/** \return an object by name, or NULL if not found */
|
||||
Widget* getWidget(const char* name);
|
||||
|
||||
/** \return an object by irrlicht ID, or NULL if not found */
|
||||
Widget* getWidget(const int id);
|
||||
|
||||
/** \return an object by name, casted to specified type, or NULL if not found/wrong type */
|
||||
template <typename T> T* getWidget(const char* name)
|
||||
{
|
||||
Widget* out = getWidget(name);
|
||||
T* outCasted = dynamic_cast<T*>( out );
|
||||
if (out != NULL && outCasted == NULL)
|
||||
{
|
||||
fprintf(stderr, "Screen::getWidget : Widget '%s' of type '%s' cannot be casted to "
|
||||
"requested type '%s'!\n", name, typeid(*out).name(), typeid(T).name());
|
||||
abort();
|
||||
}
|
||||
return outCasted;
|
||||
}
|
||||
|
||||
static Widget* getWidget(const char* name, ptr_vector<Widget>* within_vector);
|
||||
static Widget* getWidget(const int id, ptr_vector<Widget>* within_vector);
|
||||
|
||||
Widget* getFirstWidget(ptr_vector<Widget>* within_vector=NULL);
|
||||
Widget* getLastWidget(ptr_vector<Widget>* within_vector=NULL);
|
||||
|
||||
bool isMyChild(Widget* widget) const;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
Loading…
x
Reference in New Issue
Block a user