implemented Alex's <object_ref> symlinks in XRC
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@13608 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
@@ -179,7 +179,8 @@ protected:
|
|||||||
void UpdateResources();
|
void UpdateResources();
|
||||||
|
|
||||||
// Finds resource (calls UpdateResources) and returns node containing it
|
// Finds resource (calls UpdateResources) and returns node containing it
|
||||||
wxXmlNode *FindResource(const wxString& name, const wxString& classname);
|
wxXmlNode *FindResource(const wxString& name, const wxString& classname, bool recursive = FALSE);
|
||||||
|
wxXmlNode *DoFindResource(wxXmlNode *parent, const wxString& name, const wxString& classname, bool recursive);
|
||||||
|
|
||||||
// Creates resource from info in given node:
|
// Creates resource from info in given node:
|
||||||
wxObject *CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance = NULL);
|
wxObject *CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance = NULL);
|
||||||
|
@@ -344,29 +344,64 @@ void wxXmlResource::UpdateResources()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
wxXmlNode *wxXmlResource::DoFindResource(wxXmlNode *parent,
|
||||||
|
const wxString& name,
|
||||||
|
const wxString& classname,
|
||||||
|
bool recursive)
|
||||||
|
{
|
||||||
|
wxString dummy;
|
||||||
|
wxXmlNode *node;
|
||||||
|
|
||||||
wxXmlNode *wxXmlResource::FindResource(const wxString& name, const wxString& classname)
|
// first search for match at the top-level nodes (as this is
|
||||||
|
// where the resource is most commonly looked for):
|
||||||
|
for (node = parent->GetChildren(); node; node = node->GetNext())
|
||||||
|
{
|
||||||
|
if ( node->GetType() == wxXML_ELEMENT_NODE &&
|
||||||
|
(node->GetName() == wxT("object") ||
|
||||||
|
node->GetName() == wxT("object_ref")) &&
|
||||||
|
(!classname ||
|
||||||
|
node->GetPropVal(wxT("class"), wxEmptyString) == classname) &&
|
||||||
|
node->GetPropVal(wxT("name"), &dummy) && dummy == name )
|
||||||
|
return node;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( recursive )
|
||||||
|
for (node = parent->GetChildren(); node; node = node->GetNext())
|
||||||
|
{
|
||||||
|
if ( node->GetType() == wxXML_ELEMENT_NODE &&
|
||||||
|
(node->GetName() == wxT("object") ||
|
||||||
|
node->GetName() == wxT("object_ref")) )
|
||||||
|
{
|
||||||
|
wxXmlNode* found = DoFindResource(node, name, classname, TRUE);
|
||||||
|
if ( found )
|
||||||
|
return found;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
wxXmlNode *wxXmlResource::FindResource(const wxString& name,
|
||||||
|
const wxString& classname,
|
||||||
|
bool recursive)
|
||||||
{
|
{
|
||||||
UpdateResources(); //ensure everything is up-to-date
|
UpdateResources(); //ensure everything is up-to-date
|
||||||
|
|
||||||
wxString dummy;
|
wxString dummy;
|
||||||
for (size_t f = 0; f < m_data.GetCount(); f++)
|
for (size_t f = 0; f < m_data.GetCount(); f++)
|
||||||
{
|
{
|
||||||
if (m_data[f].Doc == NULL || m_data[f].Doc->GetRoot() == NULL) continue;
|
if ( m_data[f].Doc == NULL || m_data[f].Doc->GetRoot() == NULL )
|
||||||
for (wxXmlNode *node = m_data[f].Doc->GetRoot()->GetChildren();
|
continue;
|
||||||
node; node = node->GetNext())
|
|
||||||
if (node->GetType() == wxXML_ELEMENT_NODE &&
|
wxXmlNode* found = DoFindResource(m_data[f].Doc->GetRoot(),
|
||||||
(!classname ||
|
name, classname, recursive);
|
||||||
node->GetPropVal(wxT("class"), wxEmptyString) == classname) &&
|
if ( found )
|
||||||
node->GetName() == wxT("object") &&
|
{
|
||||||
node->GetPropVal(wxT("name"), &dummy) &&
|
|
||||||
dummy == name)
|
|
||||||
{
|
|
||||||
#if wxUSE_FILESYSTEM
|
#if wxUSE_FILESYSTEM
|
||||||
m_curFileSystem.ChangePathTo(m_data[f].File);
|
m_curFileSystem.ChangePathTo(m_data[f].File);
|
||||||
#endif
|
#endif
|
||||||
return node;
|
return found;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
wxLogError(_("XRC resource '%s' (class '%s') not found!"),
|
wxLogError(_("XRC resource '%s' (class '%s') not found!"),
|
||||||
@@ -374,12 +409,74 @@ wxXmlNode *wxXmlResource::FindResource(const wxString& name, const wxString& cla
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void MergeNodes(wxXmlNode& dest, wxXmlNode& with)
|
||||||
|
{
|
||||||
|
// Merge properties:
|
||||||
|
for (wxXmlProperty *prop = with.GetProperties(); prop; prop = prop->GetNext())
|
||||||
|
{
|
||||||
|
wxXmlProperty *dprop;
|
||||||
|
for (dprop = dest.GetProperties(); dprop; dprop = dprop->GetNext())
|
||||||
|
{
|
||||||
|
|
||||||
|
if ( dprop->GetName() == prop->GetName() )
|
||||||
|
{
|
||||||
|
dprop->SetValue(prop->GetValue());
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( !dprop )
|
||||||
|
dest.AddProperty(prop->GetName(), prop->GetValue());
|
||||||
|
}
|
||||||
|
|
||||||
|
// Merge child nodes:
|
||||||
|
for (wxXmlNode* node = with.GetChildren(); node; node = node->GetNext())
|
||||||
|
{
|
||||||
|
wxString name = node->GetPropVal(wxT("name"), wxEmptyString);
|
||||||
|
wxXmlNode *dnode;
|
||||||
|
|
||||||
|
for (dnode = dest.GetChildren(); dnode; dnode = dnode->GetNext() )
|
||||||
|
{
|
||||||
|
if ( dnode->GetName() == node->GetName() &&
|
||||||
|
dnode->GetPropVal("name", wxEmptyString) == name &&
|
||||||
|
dnode->GetType() == node->GetType() )
|
||||||
|
{
|
||||||
|
MergeNodes(*dnode, *node);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( !dnode )
|
||||||
|
dest.AddChild(new wxXmlNode(*node));
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( dest.GetType() == wxXML_TEXT_NODE && with.GetContent().Length() )
|
||||||
|
dest.SetContent(with.GetContent());
|
||||||
|
}
|
||||||
|
|
||||||
wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance)
|
wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance)
|
||||||
{
|
{
|
||||||
if (node == NULL) return NULL;
|
if (node == NULL) return NULL;
|
||||||
|
|
||||||
|
// handling of referenced resource
|
||||||
|
if ( node->GetName() == wxT("object_ref") )
|
||||||
|
{
|
||||||
|
wxString refName = node->GetPropVal(wxT("ref"), wxEmptyString);
|
||||||
|
wxXmlNode* refNode = FindResource(refName, wxEmptyString, TRUE);
|
||||||
|
|
||||||
|
if ( !refNode )
|
||||||
|
{
|
||||||
|
wxLogError(_("Referenced object node with ref=\"%s\" not found!"),
|
||||||
|
refName.c_str());
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
wxXmlNode copy(*refNode);
|
||||||
|
MergeNodes(copy, *node);
|
||||||
|
|
||||||
|
return CreateResFromNode(©, parent, instance);
|
||||||
|
}
|
||||||
|
|
||||||
wxXmlResourceHandler *handler;
|
wxXmlResourceHandler *handler;
|
||||||
wxObject *ret;
|
wxObject *ret;
|
||||||
wxNode * ND = m_handlers.GetFirst();
|
wxNode * ND = m_handlers.GetFirst();
|
||||||
@@ -403,11 +500,6 @@ wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wx
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
wxXmlResourceHandler::wxXmlResourceHandler()
|
wxXmlResourceHandler::wxXmlResourceHandler()
|
||||||
: m_node(NULL), m_parent(NULL), m_instance(NULL),
|
: m_node(NULL), m_parent(NULL), m_instance(NULL),
|
||||||
m_parentAsWindow(NULL), m_instanceAsWindow(NULL)
|
m_parentAsWindow(NULL), m_instanceAsWindow(NULL)
|
||||||
|
@@ -179,7 +179,8 @@ protected:
|
|||||||
void UpdateResources();
|
void UpdateResources();
|
||||||
|
|
||||||
// Finds resource (calls UpdateResources) and returns node containing it
|
// Finds resource (calls UpdateResources) and returns node containing it
|
||||||
wxXmlNode *FindResource(const wxString& name, const wxString& classname);
|
wxXmlNode *FindResource(const wxString& name, const wxString& classname, bool recursive = FALSE);
|
||||||
|
wxXmlNode *DoFindResource(wxXmlNode *parent, const wxString& name, const wxString& classname, bool recursive);
|
||||||
|
|
||||||
// Creates resource from info in given node:
|
// Creates resource from info in given node:
|
||||||
wxObject *CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance = NULL);
|
wxObject *CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance = NULL);
|
||||||
|
@@ -344,29 +344,64 @@ void wxXmlResource::UpdateResources()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
wxXmlNode *wxXmlResource::DoFindResource(wxXmlNode *parent,
|
||||||
|
const wxString& name,
|
||||||
|
const wxString& classname,
|
||||||
|
bool recursive)
|
||||||
|
{
|
||||||
|
wxString dummy;
|
||||||
|
wxXmlNode *node;
|
||||||
|
|
||||||
wxXmlNode *wxXmlResource::FindResource(const wxString& name, const wxString& classname)
|
// first search for match at the top-level nodes (as this is
|
||||||
|
// where the resource is most commonly looked for):
|
||||||
|
for (node = parent->GetChildren(); node; node = node->GetNext())
|
||||||
|
{
|
||||||
|
if ( node->GetType() == wxXML_ELEMENT_NODE &&
|
||||||
|
(node->GetName() == wxT("object") ||
|
||||||
|
node->GetName() == wxT("object_ref")) &&
|
||||||
|
(!classname ||
|
||||||
|
node->GetPropVal(wxT("class"), wxEmptyString) == classname) &&
|
||||||
|
node->GetPropVal(wxT("name"), &dummy) && dummy == name )
|
||||||
|
return node;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( recursive )
|
||||||
|
for (node = parent->GetChildren(); node; node = node->GetNext())
|
||||||
|
{
|
||||||
|
if ( node->GetType() == wxXML_ELEMENT_NODE &&
|
||||||
|
(node->GetName() == wxT("object") ||
|
||||||
|
node->GetName() == wxT("object_ref")) )
|
||||||
|
{
|
||||||
|
wxXmlNode* found = DoFindResource(node, name, classname, TRUE);
|
||||||
|
if ( found )
|
||||||
|
return found;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
wxXmlNode *wxXmlResource::FindResource(const wxString& name,
|
||||||
|
const wxString& classname,
|
||||||
|
bool recursive)
|
||||||
{
|
{
|
||||||
UpdateResources(); //ensure everything is up-to-date
|
UpdateResources(); //ensure everything is up-to-date
|
||||||
|
|
||||||
wxString dummy;
|
wxString dummy;
|
||||||
for (size_t f = 0; f < m_data.GetCount(); f++)
|
for (size_t f = 0; f < m_data.GetCount(); f++)
|
||||||
{
|
{
|
||||||
if (m_data[f].Doc == NULL || m_data[f].Doc->GetRoot() == NULL) continue;
|
if ( m_data[f].Doc == NULL || m_data[f].Doc->GetRoot() == NULL )
|
||||||
for (wxXmlNode *node = m_data[f].Doc->GetRoot()->GetChildren();
|
continue;
|
||||||
node; node = node->GetNext())
|
|
||||||
if (node->GetType() == wxXML_ELEMENT_NODE &&
|
wxXmlNode* found = DoFindResource(m_data[f].Doc->GetRoot(),
|
||||||
(!classname ||
|
name, classname, recursive);
|
||||||
node->GetPropVal(wxT("class"), wxEmptyString) == classname) &&
|
if ( found )
|
||||||
node->GetName() == wxT("object") &&
|
{
|
||||||
node->GetPropVal(wxT("name"), &dummy) &&
|
|
||||||
dummy == name)
|
|
||||||
{
|
|
||||||
#if wxUSE_FILESYSTEM
|
#if wxUSE_FILESYSTEM
|
||||||
m_curFileSystem.ChangePathTo(m_data[f].File);
|
m_curFileSystem.ChangePathTo(m_data[f].File);
|
||||||
#endif
|
#endif
|
||||||
return node;
|
return found;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
wxLogError(_("XRC resource '%s' (class '%s') not found!"),
|
wxLogError(_("XRC resource '%s' (class '%s') not found!"),
|
||||||
@@ -374,12 +409,74 @@ wxXmlNode *wxXmlResource::FindResource(const wxString& name, const wxString& cla
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void MergeNodes(wxXmlNode& dest, wxXmlNode& with)
|
||||||
|
{
|
||||||
|
// Merge properties:
|
||||||
|
for (wxXmlProperty *prop = with.GetProperties(); prop; prop = prop->GetNext())
|
||||||
|
{
|
||||||
|
wxXmlProperty *dprop;
|
||||||
|
for (dprop = dest.GetProperties(); dprop; dprop = dprop->GetNext())
|
||||||
|
{
|
||||||
|
|
||||||
|
if ( dprop->GetName() == prop->GetName() )
|
||||||
|
{
|
||||||
|
dprop->SetValue(prop->GetValue());
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( !dprop )
|
||||||
|
dest.AddProperty(prop->GetName(), prop->GetValue());
|
||||||
|
}
|
||||||
|
|
||||||
|
// Merge child nodes:
|
||||||
|
for (wxXmlNode* node = with.GetChildren(); node; node = node->GetNext())
|
||||||
|
{
|
||||||
|
wxString name = node->GetPropVal(wxT("name"), wxEmptyString);
|
||||||
|
wxXmlNode *dnode;
|
||||||
|
|
||||||
|
for (dnode = dest.GetChildren(); dnode; dnode = dnode->GetNext() )
|
||||||
|
{
|
||||||
|
if ( dnode->GetName() == node->GetName() &&
|
||||||
|
dnode->GetPropVal("name", wxEmptyString) == name &&
|
||||||
|
dnode->GetType() == node->GetType() )
|
||||||
|
{
|
||||||
|
MergeNodes(*dnode, *node);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( !dnode )
|
||||||
|
dest.AddChild(new wxXmlNode(*node));
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( dest.GetType() == wxXML_TEXT_NODE && with.GetContent().Length() )
|
||||||
|
dest.SetContent(with.GetContent());
|
||||||
|
}
|
||||||
|
|
||||||
wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance)
|
wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wxObject *instance)
|
||||||
{
|
{
|
||||||
if (node == NULL) return NULL;
|
if (node == NULL) return NULL;
|
||||||
|
|
||||||
|
// handling of referenced resource
|
||||||
|
if ( node->GetName() == wxT("object_ref") )
|
||||||
|
{
|
||||||
|
wxString refName = node->GetPropVal(wxT("ref"), wxEmptyString);
|
||||||
|
wxXmlNode* refNode = FindResource(refName, wxEmptyString, TRUE);
|
||||||
|
|
||||||
|
if ( !refNode )
|
||||||
|
{
|
||||||
|
wxLogError(_("Referenced object node with ref=\"%s\" not found!"),
|
||||||
|
refName.c_str());
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
wxXmlNode copy(*refNode);
|
||||||
|
MergeNodes(copy, *node);
|
||||||
|
|
||||||
|
return CreateResFromNode(©, parent, instance);
|
||||||
|
}
|
||||||
|
|
||||||
wxXmlResourceHandler *handler;
|
wxXmlResourceHandler *handler;
|
||||||
wxObject *ret;
|
wxObject *ret;
|
||||||
wxNode * ND = m_handlers.GetFirst();
|
wxNode * ND = m_handlers.GetFirst();
|
||||||
@@ -403,11 +500,6 @@ wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent, wx
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
wxXmlResourceHandler::wxXmlResourceHandler()
|
wxXmlResourceHandler::wxXmlResourceHandler()
|
||||||
: m_node(NULL), m_parent(NULL), m_instance(NULL),
|
: m_node(NULL), m_parent(NULL), m_instance(NULL),
|
||||||
m_parentAsWindow(NULL), m_instanceAsWindow(NULL)
|
m_parentAsWindow(NULL), m_instanceAsWindow(NULL)
|
||||||
|
Reference in New Issue
Block a user