implemented subclass factories for XRC

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/branches/WX_2_4_BRANCH@17375 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Václav Slavík
2002-09-25 11:10:39 +00:00
parent 5e3012152c
commit 3ce501311b
4 changed files with 152 additions and 20 deletions

View File

@@ -37,6 +37,9 @@ class WXDLLEXPORT wxFrame;
class WXDLLEXPORT wxToolBar;
class WXXMLDLLEXPORT wxXmlResourceHandler;
class WXXMLDLLEXPORT wxXmlSubclassFactory;
class WXXMLDLLEXPORT wxXmlSubclassFactoriesList;
class wxXmlResourceModule;
// These macros indicate current version of XML resources (this information is
@@ -134,6 +137,11 @@ public:
// Removes all handlers
void ClearHandlers();
// Registers subclasses factory for use in XRC. This function is not meant
// for public use, please see the comment above wxXmlSubclassFactory
// definition.
static void AddSubclassFactory(wxXmlSubclassFactory *factory);
// Loads menu from resource. Returns NULL on failure.
wxMenu *LoadMenu(const wxString& name);
@@ -244,6 +252,9 @@ private:
#endif
friend class wxXmlResourceHandler;
friend class wxXmlResourceModule;
static wxXmlSubclassFactoriesList *ms_subclassFactories;
// singleton instance:
static wxXmlResource *ms_instance;
@@ -438,6 +449,20 @@ protected:
void wxXmlInitResourceModule();
// This class is used to create instances of XRC "object" nodes with "subclass"
// property. It is _not_ supposed to be used by XRC users, you should instead
// register your subclasses via wxWindows' RTTI mechanism. This class is useful
// only for language bindings developer who need a way to implement subclassing
// in wxWindows ports that don't support wxRTTI (e.g. wxPython).
class WXXMLDLLEXPORT wxXmlSubclassFactory
{
public:
// Try to create instance of given class and return it, return NULL on failure:
virtual wxObject *Create(const wxString& className) = 0;
virtual ~wxXmlSubclassFactory() {}
};
/* -------------------------------------------------------------------------
Backward compatibility macros. Do *NOT* use, they may disappear in future
versions of the XRC library!

View File

@@ -547,6 +547,40 @@ wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wx
}
#include "wx/listimpl.cpp"
WX_DECLARE_LIST(wxXmlSubclassFactory, wxXmlSubclassFactoriesList);
WX_DEFINE_LIST(wxXmlSubclassFactoriesList);
wxXmlSubclassFactoriesList *wxXmlResource::ms_subclassFactories = NULL;
/*static*/ void wxXmlResource::AddSubclassFactory(wxXmlSubclassFactory *factory)
{
if (!ms_subclassFactories)
{
ms_subclassFactories = new wxXmlSubclassFactoriesList;
ms_subclassFactories->DeleteContents(TRUE);
}
ms_subclassFactories->Append(factory);
}
class wxXmlSubclassFactoryCXX : public wxXmlSubclassFactory
{
public:
~wxXmlSubclassFactoryCXX() {}
wxObject *Create(const wxString& className)
{
wxClassInfo* classInfo = wxClassInfo::FindClass(className);
if (classInfo)
return classInfo->CreateObject();
else
return NULL;
}
};
wxXmlResourceHandler::wxXmlResourceHandler()
@@ -568,18 +602,23 @@ wxObject *wxXmlResourceHandler::CreateResource(wxXmlNode *node, wxObject *parent
!(m_resource->GetFlags() & wxXRC_NO_SUBCLASSING))
{
wxString subclass = node->GetPropVal(wxT("subclass"), wxEmptyString);
wxClassInfo* classInfo = wxClassInfo::FindClass(subclass);
if (classInfo)
m_instance = classInfo->CreateObject();
if (!subclass.empty())
{
for (wxXmlSubclassFactoriesList::Node *i = wxXmlResource::ms_subclassFactories->GetFirst();
i; i = i->GetNext())
{
m_instance = i->GetData()->Create(subclass);
if (m_instance)
break;
}
if (!m_instance)
{
wxString name = node->GetPropVal(wxT("name"), wxEmptyString);
wxLogError(_("Subclass '%s' not found for resource '%s', not subclassing!"),
subclass.c_str(), node->GetPropVal(wxT("name"), wxEmptyString).c_str());
subclass.c_str(), name.c_str());
}
}
m_instance = classInfo->CreateObject();
}
m_node = node;
@@ -1167,11 +1206,13 @@ public:
wxXmlResourceModule() {}
bool OnInit()
{
wxXmlResource::AddSubclassFactory(new wxXmlSubclassFactoryCXX);
return TRUE;
}
void OnExit()
{
delete wxXmlResource::Set(NULL);
wxDELETE(wxXmlResource::ms_subclassFactories);
CleanXRCID_Records();
}
};

View File

@@ -37,6 +37,9 @@ class WXDLLEXPORT wxFrame;
class WXDLLEXPORT wxToolBar;
class WXXMLDLLEXPORT wxXmlResourceHandler;
class WXXMLDLLEXPORT wxXmlSubclassFactory;
class WXXMLDLLEXPORT wxXmlSubclassFactoriesList;
class wxXmlResourceModule;
// These macros indicate current version of XML resources (this information is
@@ -134,6 +137,11 @@ public:
// Removes all handlers
void ClearHandlers();
// Registers subclasses factory for use in XRC. This function is not meant
// for public use, please see the comment above wxXmlSubclassFactory
// definition.
static void AddSubclassFactory(wxXmlSubclassFactory *factory);
// Loads menu from resource. Returns NULL on failure.
wxMenu *LoadMenu(const wxString& name);
@@ -244,6 +252,9 @@ private:
#endif
friend class wxXmlResourceHandler;
friend class wxXmlResourceModule;
static wxXmlSubclassFactoriesList *ms_subclassFactories;
// singleton instance:
static wxXmlResource *ms_instance;
@@ -438,6 +449,20 @@ protected:
void wxXmlInitResourceModule();
// This class is used to create instances of XRC "object" nodes with "subclass"
// property. It is _not_ supposed to be used by XRC users, you should instead
// register your subclasses via wxWindows' RTTI mechanism. This class is useful
// only for language bindings developer who need a way to implement subclassing
// in wxWindows ports that don't support wxRTTI (e.g. wxPython).
class WXXMLDLLEXPORT wxXmlSubclassFactory
{
public:
// Try to create instance of given class and return it, return NULL on failure:
virtual wxObject *Create(const wxString& className) = 0;
virtual ~wxXmlSubclassFactory() {}
};
/* -------------------------------------------------------------------------
Backward compatibility macros. Do *NOT* use, they may disappear in future
versions of the XRC library!

View File

@@ -547,6 +547,40 @@ wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wx
}
#include "wx/listimpl.cpp"
WX_DECLARE_LIST(wxXmlSubclassFactory, wxXmlSubclassFactoriesList);
WX_DEFINE_LIST(wxXmlSubclassFactoriesList);
wxXmlSubclassFactoriesList *wxXmlResource::ms_subclassFactories = NULL;
/*static*/ void wxXmlResource::AddSubclassFactory(wxXmlSubclassFactory *factory)
{
if (!ms_subclassFactories)
{
ms_subclassFactories = new wxXmlSubclassFactoriesList;
ms_subclassFactories->DeleteContents(TRUE);
}
ms_subclassFactories->Append(factory);
}
class wxXmlSubclassFactoryCXX : public wxXmlSubclassFactory
{
public:
~wxXmlSubclassFactoryCXX() {}
wxObject *Create(const wxString& className)
{
wxClassInfo* classInfo = wxClassInfo::FindClass(className);
if (classInfo)
return classInfo->CreateObject();
else
return NULL;
}
};
wxXmlResourceHandler::wxXmlResourceHandler()
@@ -568,18 +602,23 @@ wxObject *wxXmlResourceHandler::CreateResource(wxXmlNode *node, wxObject *parent
!(m_resource->GetFlags() & wxXRC_NO_SUBCLASSING))
{
wxString subclass = node->GetPropVal(wxT("subclass"), wxEmptyString);
wxClassInfo* classInfo = wxClassInfo::FindClass(subclass);
if (classInfo)
m_instance = classInfo->CreateObject();
if (!subclass.empty())
{
for (wxXmlSubclassFactoriesList::Node *i = wxXmlResource::ms_subclassFactories->GetFirst();
i; i = i->GetNext())
{
m_instance = i->GetData()->Create(subclass);
if (m_instance)
break;
}
if (!m_instance)
{
wxString name = node->GetPropVal(wxT("name"), wxEmptyString);
wxLogError(_("Subclass '%s' not found for resource '%s', not subclassing!"),
subclass.c_str(), node->GetPropVal(wxT("name"), wxEmptyString).c_str());
subclass.c_str(), name.c_str());
}
}
m_instance = classInfo->CreateObject();
}
m_node = node;
@@ -1167,11 +1206,13 @@ public:
wxXmlResourceModule() {}
bool OnInit()
{
wxXmlResource::AddSubclassFactory(new wxXmlSubclassFactoryCXX);
return TRUE;
}
void OnExit()
{
delete wxXmlResource::Set(NULL);
wxDELETE(wxXmlResource::ms_subclassFactories);
CleanXRCID_Records();
}
};