Canvas: Ensure all element types are initialized before first usage.
If setting properties on a group a check is performed if this property exists on any possible child element, and only if this is the case the property is stored in the groups style. Previously elements have been only initialized during their first usage, leading to ignored styles if they have been set on a parent element before instantiating an instance of the actual element type.
This commit is contained in:
parent
fc75b0bd21
commit
b236821661
@ -523,6 +523,8 @@ namespace canvas
|
||||
_style( parent_style ),
|
||||
_drawable( 0 )
|
||||
{
|
||||
staticInit();
|
||||
|
||||
SG_LOG
|
||||
(
|
||||
SG_GL,
|
||||
@ -530,11 +532,6 @@ namespace canvas
|
||||
"New canvas element " << node->getPath()
|
||||
);
|
||||
|
||||
if( !isInit<Element>() )
|
||||
{
|
||||
addStyle("clip", "", &Element::setClip, false);
|
||||
}
|
||||
|
||||
// Ensure elements are drawn in order they appear in the element tree
|
||||
_transform->getOrCreateStateSet()
|
||||
->setRenderBinDetails
|
||||
@ -545,6 +542,15 @@ namespace canvas
|
||||
);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
void Element::staticInit()
|
||||
{
|
||||
if( isInit<Element>() )
|
||||
return;
|
||||
|
||||
addStyle("clip", "", &Element::setClip, false);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool Element::isStyleEmpty(const SGPropertyNode* child) const
|
||||
{
|
||||
|
@ -197,6 +197,8 @@ namespace canvas
|
||||
typedef std::map<std::string, StyleInfo> StyleSetters;
|
||||
static StyleSetters _style_setters;
|
||||
|
||||
static void staticInit();
|
||||
|
||||
Element( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
const Style& parent_style,
|
||||
@ -210,7 +212,7 @@ namespace canvas
|
||||
* @tparam Derived (Derived) class type
|
||||
*/
|
||||
template<class Derived>
|
||||
bool isInit() const
|
||||
static bool isInit()
|
||||
{
|
||||
static bool is_init = false;
|
||||
if( is_init )
|
||||
@ -239,6 +241,7 @@ namespace canvas
|
||||
typename T2,
|
||||
class Derived
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -282,6 +285,7 @@ namespace canvas
|
||||
typename T,
|
||||
class Derived
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -295,6 +299,7 @@ namespace canvas
|
||||
typename T,
|
||||
class Derived
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -315,6 +320,7 @@ namespace canvas
|
||||
typename T2,
|
||||
class Derived
|
||||
>
|
||||
static
|
||||
StyleSetterFunc
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -333,6 +339,7 @@ namespace canvas
|
||||
template<
|
||||
class Derived
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -354,6 +361,7 @@ namespace canvas
|
||||
class Other,
|
||||
class OtherRef
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -377,6 +385,7 @@ namespace canvas
|
||||
class Other,
|
||||
class OtherRef
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -400,6 +409,7 @@ namespace canvas
|
||||
class Other,
|
||||
class OtherRef
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -421,6 +431,7 @@ namespace canvas
|
||||
class Other,
|
||||
class OtherRef
|
||||
>
|
||||
static
|
||||
StyleSetter
|
||||
addStyle( const std::string& name,
|
||||
const std::string& type,
|
||||
@ -439,6 +450,7 @@ namespace canvas
|
||||
}
|
||||
|
||||
template<typename T, class Derived, class Other, class OtherRef>
|
||||
static
|
||||
boost::function<void (Derived&, T)>
|
||||
bindOther( void (Other::*setter)(T), OtherRef Derived::*instance_ref )
|
||||
{
|
||||
@ -446,6 +458,7 @@ namespace canvas
|
||||
}
|
||||
|
||||
template<typename T, class Derived, class Other, class OtherRef>
|
||||
static
|
||||
boost::function<void (Derived&, T)>
|
||||
bindOther( const boost::function<void (Other&, T)>& setter,
|
||||
OtherRef Derived::*instance_ref )
|
||||
@ -463,6 +476,7 @@ namespace canvas
|
||||
}
|
||||
|
||||
template<typename T1, typename T2, class Derived>
|
||||
static
|
||||
StyleSetterFuncUnchecked
|
||||
bindStyleSetter( const std::string& name,
|
||||
const boost::function<void (Derived&, T2)>& setter )
|
||||
|
@ -38,6 +38,7 @@ namespace canvas
|
||||
template<typename ElementType>
|
||||
void add(ElementFactories& factories)
|
||||
{
|
||||
ElementType::staticInit();
|
||||
factories[ElementType::TYPE_NAME] = &Element::create<ElementType>;
|
||||
}
|
||||
|
||||
@ -53,20 +54,26 @@ namespace canvas
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Group::Group( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
const Style& parent_style,
|
||||
Element* parent ):
|
||||
Element(canvas, node, parent_style, parent)
|
||||
{
|
||||
if( !isInit<Group>() )
|
||||
void Group::staticInit()
|
||||
{
|
||||
if( isInit<Group>() )
|
||||
return;
|
||||
|
||||
add<Group>(_child_factories);
|
||||
add<Image>(_child_factories);
|
||||
add<Map >(_child_factories);
|
||||
add<Path >(_child_factories);
|
||||
add<Text >(_child_factories);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Group::Group( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
const Style& parent_style,
|
||||
Element* parent ):
|
||||
Element(canvas, node, parent_style, parent)
|
||||
{
|
||||
staticInit();
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
@ -35,6 +35,7 @@ namespace canvas
|
||||
{
|
||||
public:
|
||||
static const std::string TYPE_NAME;
|
||||
static void staticInit();
|
||||
|
||||
typedef std::list< std::pair< const SGPropertyNode*,
|
||||
ElementPtr
|
||||
|
@ -89,6 +89,18 @@ namespace canvas
|
||||
//----------------------------------------------------------------------------
|
||||
const std::string Image::TYPE_NAME = "image";
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
void Image::staticInit()
|
||||
{
|
||||
if( isInit<Image>() )
|
||||
return;
|
||||
|
||||
addStyle("fill", "color", &Image::setFill);
|
||||
addStyle("slice", "", &Image::setSlice);
|
||||
addStyle("slice-width", "", &Image::setSliceWidth);
|
||||
addStyle("outset", "", &Image::setOutset);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Image::Image( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
@ -100,6 +112,8 @@ namespace canvas
|
||||
_src_rect(0,0),
|
||||
_region(0,0)
|
||||
{
|
||||
staticInit();
|
||||
|
||||
_geom = new osg::Geometry;
|
||||
_geom->setUseDisplayList(false);
|
||||
|
||||
@ -128,16 +142,7 @@ namespace canvas
|
||||
|
||||
setDrawable(_geom);
|
||||
|
||||
if( !isInit<Image>() )
|
||||
{
|
||||
addStyle("fill", "color", &Image::setFill);
|
||||
addStyle("slice", "", &Image::setSlice);
|
||||
addStyle("slice-width", "", &Image::setSliceWidth);
|
||||
addStyle("outset", "", &Image::setOutset);
|
||||
}
|
||||
|
||||
setFill("#ffffff"); // TODO how should we handle default values?
|
||||
|
||||
setupStyle();
|
||||
}
|
||||
|
||||
|
@ -35,6 +35,7 @@ namespace canvas
|
||||
{
|
||||
public:
|
||||
static const std::string TYPE_NAME;
|
||||
static void staticInit();
|
||||
|
||||
/**
|
||||
* @param node Property node containing settings for this image:
|
||||
|
@ -46,6 +46,17 @@ namespace canvas
|
||||
const std::string GEO = "-geo";
|
||||
const std::string Map::TYPE_NAME = "map";
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
void Map::staticInit()
|
||||
{
|
||||
Group::staticInit();
|
||||
|
||||
if( isInit<Map>() )
|
||||
return;
|
||||
|
||||
// Do some initialization if needed...
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Map::Map( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
@ -56,7 +67,7 @@ namespace canvas
|
||||
_projection(new SansonFlamsteedProjection),
|
||||
_projection_dirty(true)
|
||||
{
|
||||
|
||||
staticInit();
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
@ -36,6 +36,7 @@ namespace canvas
|
||||
{
|
||||
public:
|
||||
static const std::string TYPE_NAME;
|
||||
static void staticInit();
|
||||
|
||||
Map( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
|
@ -473,17 +473,11 @@ namespace canvas
|
||||
const std::string Path::TYPE_NAME = "path";
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Path::Path( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
const Style& parent_style,
|
||||
Element* parent ):
|
||||
Element(canvas, node, parent_style, parent),
|
||||
_path( new PathDrawable(this) )
|
||||
void Path::staticInit()
|
||||
{
|
||||
setDrawable(_path);
|
||||
if( isInit<Path>() )
|
||||
return;
|
||||
|
||||
if( !isInit<Path>() )
|
||||
{
|
||||
PathDrawableRef Path::*path = &Path::_path;
|
||||
|
||||
addStyle("fill", "color", &PathDrawable::setFill, path);
|
||||
@ -494,6 +488,17 @@ namespace canvas
|
||||
addStyle("stroke-linecap", "", &PathDrawable::setStrokeLinecap, path);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Path::Path( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
const Style& parent_style,
|
||||
Element* parent ):
|
||||
Element(canvas, node, parent_style, parent),
|
||||
_path( new PathDrawable(this) )
|
||||
{
|
||||
staticInit();
|
||||
|
||||
setDrawable(_path);
|
||||
setupStyle();
|
||||
}
|
||||
|
||||
|
@ -31,6 +31,7 @@ namespace canvas
|
||||
{
|
||||
public:
|
||||
static const std::string TYPE_NAME;
|
||||
static void staticInit();
|
||||
|
||||
Path( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
|
@ -262,20 +262,11 @@ namespace canvas
|
||||
const std::string Text::TYPE_NAME = "text";
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Text::Text( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
const Style& parent_style,
|
||||
Element* parent ):
|
||||
Element(canvas, node, parent_style, parent),
|
||||
_text( new Text::TextOSG(this) )
|
||||
void Text::staticInit()
|
||||
{
|
||||
setDrawable(_text);
|
||||
_text->setCharacterSizeMode(osgText::Text::OBJECT_COORDS);
|
||||
_text->setAxisAlignment(osgText::Text::USER_DEFINED_ROTATION);
|
||||
_text->setRotation(osg::Quat(osg::PI, osg::X_AXIS));
|
||||
if( isInit<Text>() )
|
||||
return;
|
||||
|
||||
if( !isInit<Text>() )
|
||||
{
|
||||
osg::ref_ptr<TextOSG> Text::*text = &Text::_text;
|
||||
|
||||
addStyle("fill", "color", &TextOSG::setFill, text);
|
||||
@ -303,6 +294,21 @@ namespace canvas
|
||||
addStyle("text", "", &Text::setText, false);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
Text::Text( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
const Style& parent_style,
|
||||
Element* parent ):
|
||||
Element(canvas, node, parent_style, parent),
|
||||
_text( new Text::TextOSG(this) )
|
||||
{
|
||||
staticInit();
|
||||
|
||||
setDrawable(_text);
|
||||
_text->setCharacterSizeMode(osgText::Text::OBJECT_COORDS);
|
||||
_text->setAxisAlignment(osgText::Text::USER_DEFINED_ROTATION);
|
||||
_text->setRotation(osg::Quat(osg::PI, osg::X_AXIS));
|
||||
|
||||
setupStyle();
|
||||
}
|
||||
|
||||
|
@ -34,6 +34,7 @@ namespace canvas
|
||||
{
|
||||
public:
|
||||
static const std::string TYPE_NAME;
|
||||
static void staticInit();
|
||||
|
||||
Text( const CanvasWeakPtr& canvas,
|
||||
const SGPropertyNode_ptr& node,
|
||||
|
Loading…
Reference in New Issue
Block a user