- wxPropertyGrid: added wxPG_NO_INTERNAL_BORDER, wxPG_EX_NO_TOOLBAR_DIVIDER
   and wxPG_EX_TOOLBAR_SEPARATOR styles for finer control over borders.
   Borders around property grid are now native for consistency.
+- Added wxXmlResource::LoadObjectRecursively().
 
 GTK:
 
 
     // Load an object from the resource specifying both the resource name and
     // the classname.  This lets you load nonstandard container windows.
     wxObject *LoadObject(wxWindow *parent, const wxString& name,
-                         const wxString& classname);
+                         const wxString& classname)
+    {
+        return DoLoadObject(parent, name, classname, false /* !recursive */);
+    }
 
     // Load an object from the resource specifying both the resource name and
     // the classname.  This form lets you finish the creation of an existing
     // instance.
-    bool LoadObject(wxObject *instance, wxWindow *parent, const wxString& name,
-                    const wxString& classname);
+    bool LoadObject(wxObject *instance,
+                    wxWindow *parent,
+                    const wxString& name,
+                    const wxString& classname)
+    {
+        return DoLoadObject(instance, parent, name, classname, false);
+    }
+
+    // These versions of LoadObject() look for the object with the given name
+    // recursively (breadth first) and can be used to instantiate an individual
+    // control defined anywhere in an XRC file. No check is done that the name
+    // is unique, it's up to the caller to ensure this.
+    wxObject *LoadObjectRecursively(wxWindow *parent,
+                                    const wxString& name,
+                                    const wxString& classname)
+    {
+        return DoLoadObject(parent, name, classname, true /* recursive */);
+    }
+
+    bool LoadObjectRecursively(wxObject *instance,
+                               wxWindow *parent,
+                               const wxString& name,
+                               const wxString& classname)
+    {
+        return DoLoadObject(instance, parent, name, classname, true);
+    }
 
     // Loads a bitmap resource from a file.
     wxBitmap LoadBitmap(const wxString& name);
     // (Uses only 'handlerToUse' if != NULL)
     wxObject *CreateResFromNode(wxXmlNode *node, wxObject *parent,
                                 wxObject *instance = NULL,
-                                wxXmlResourceHandler *handlerToUse = NULL);
+                                wxXmlResourceHandler *handlerToUse = NULL)
+    {
+        return node ? DoCreateResFromNode(*node, parent, instance, handlerToUse)
+                    : NULL;
+    }
 
     // Helper of Load() and Unload(): returns the URL corresponding to the
     // given file if it's indeed a file, otherwise returns the original string
     wxXmlResourceDataRecords& Data() { return *m_data; }
     const wxXmlResourceDataRecords& Data() const { return *m_data; }
 
+    // the real implementation of CreateResFromNode(): this should be only
+    // called if node is non-NULL
+    wxObject *DoCreateResFromNode(wxXmlNode& node,
+                                  wxObject *parent,
+                                  wxObject *instance,
+                                  wxXmlResourceHandler *handlerToUse = NULL);
+
+    // common part of LoadObject() and LoadObjectRecursively()
+    wxObject *DoLoadObject(wxWindow *parent,
+                           const wxString& name,
+                           const wxString& classname,
+                           bool recursive);
+    bool DoLoadObject(wxObject *instance,
+                      wxWindow *parent,
+                      const wxString& name,
+                      const wxString& classname,
+                      bool recursive);
+
 private:
     long m_version;
 
 
         The first overload lets you load nonstandard container windows and returns
         @NULL on failure. The second one lets you finish the creation of an existing
         instance and returns @false on failure.
+
+        In either case, only the resources defined at the top level of XRC
+        files can be loaded by this function, use LoadObjectRecursively() if
+        you need to load an object defined deeper in the hierarchy.
     */
     wxObject* LoadObject(wxWindow* parent, const wxString& name,
                          const wxString& classname);
                     const wxString& classname);
     //@}
 
+    //@{
+    /**
+        Load an object from anywhere in the resource tree.
+
+        These methods are similar to LoadObject() but may be used to load an
+        object from anywhere in the resource tree and not only the top level.
+        Note that you will very rarely need to do this as in normal use the
+        entire container window (defined at the top level) is loaded and not
+        its individual children but this method can be useful in some
+        particular situations.
+
+        @since 2.9.1
+    */
+    wxObject* LoadObjectRecursively(wxWindow* parent,
+                                    const wxString& name,
+                                    const wxString& classname);
+    bool LoadObjectRecursively(wxObject* instance, wxWindow* parent,
+                    const wxString& name,
+                    const wxString& classname);
+    //@}
+
     /**
         Loads a panel. @a parent points to the parent window.
     */
 
     EVT_MENU(XRCID("platform_property_tool_or_menuitem"), MyFrame::OnPlatformPropertyToolOrMenuCommand)
     EVT_MENU(XRCID("art_provider_tool_or_menuitem"), MyFrame::OnArtProviderToolOrMenuCommand)
     EVT_MENU(XRCID("variable_expansion_tool_or_menuitem"), MyFrame::OnVariableExpansionToolOrMenuCommand)
+    EVT_MENU(XRCID("recursive_load"), MyFrame::OnRecursiveLoad)
     EVT_MENU(wxID_ABOUT, MyFrame::OnAboutToolOrMenuCommand)
 END_EVENT_TABLE()
 
     dlg.ShowModal();
 }
 
+void MyFrame::OnRecursiveLoad(wxCommandEvent& WXUNUSED(event))
+{
+    // this dialog is created manually to show how you can inject a single
+    // control from XRC into an existing dialog
+    //
+    // this is a slightly contrived example, please keep in mind that it's done
+    // only to demonstrate LoadObjectRecursively() in action and is not the
+    // recommended to do this
+    wxDialog dlg(NULL, wxID_ANY, "Recursive Load Example",
+                 wxDefaultPosition, wxDefaultSize,
+                 wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER);
+    wxSizer * const sizer = new wxBoxSizer(wxVERTICAL);
+    sizer->Add
+    (
+        new wxStaticText
+        (
+            &dlg,
+            wxID_ANY,
+            "The entire tree book control below is loaded from XRC"
+        ),
+        wxSizerFlags().Expand().Border()
+    );
+
+    sizer->Add
+    (
+        static_cast<wxWindow *>
+        (
+            // notice that controls_treebook is defined inside a notebook page
+            // inside a dialog defined in controls.xrc and so LoadObject()
+            // wouldn't find it -- but LoadObjectRecursively() does
+            wxXmlResource::Get()->
+                LoadObjectRecursively(&dlg, "controls_treebook", "wxTreebook")
+        ),
+        wxSizerFlags(1).Expand().Border()
+    );
+
+    dlg.SetSizer(sizer);
+    dlg.SetClientSize(400, 200);
+
+    dlg.ShowModal();
+}
 
 void MyFrame::OnAboutToolOrMenuCommand(wxCommandEvent& WXUNUSED(event))
 {
 
     void OnPlatformPropertyToolOrMenuCommand(wxCommandEvent& event);
     void OnArtProviderToolOrMenuCommand(wxCommandEvent& event);
     void OnVariableExpansionToolOrMenuCommand(wxCommandEvent& event);
+    void OnRecursiveLoad(wxCommandEvent& event);
     void OnAnimationCtrlPlay(wxCommandEvent& event);
 
     // Any class wishing to process wxWidgets events must use this macro
 
             <bitmap>variable.xpm</bitmap>
             <help>Replace variables in the XRC file at runtime</help>
         </object>        
+        <object class="wxMenuItem" name="recursive_load">
+            <label>_Recursive Load</label>
+            <help>Show how an individual control can be loaded</help>
+        </object>
     </object>    
     <object class="wxMenu" name="help_menu">
         <label>_Help</label>
 
 }
 
 
-wxObject *wxXmlResource::LoadObject(wxWindow *parent, const wxString& name, const wxString& classname)
+wxObject *
+wxXmlResource::DoLoadObject(wxWindow *parent,
+                            const wxString& name,
+                            const wxString& classname,
+                            bool recursive)
 {
-    return CreateResFromNode(FindResource(name, classname), parent, NULL);
+    wxXmlNode * const node = FindResource(name, classname, recursive);
+
+    return node ? DoCreateResFromNode(*node, parent, NULL) : NULL;
 }
 
-bool wxXmlResource::LoadObject(wxObject *instance, wxWindow *parent, const wxString& name, const wxString& classname)
+bool
+wxXmlResource::DoLoadObject(wxObject *instance,
+                            wxWindow *parent,
+                            const wxString& name,
+                            const wxString& classname,
+                            bool recursive)
 {
-    return CreateResFromNode(FindResource(name, classname), parent, instance) != NULL;
+    wxXmlNode * const node = FindResource(name, classname, recursive);
+
+    return node && DoCreateResFromNode(*node, parent, instance) != NULL;
 }
 
 
          dest.SetContent(overwriteWith.GetContent());
 }
 
-wxObject *wxXmlResource::CreateResFromNode(wxXmlNode *node, wxObject *parent,
-                                           wxObject *instance,
-                                           wxXmlResourceHandler *handlerToUse)
+wxObject *
+wxXmlResource::DoCreateResFromNode(wxXmlNode& node,
+                                   wxObject *parent,
+                                   wxObject *instance,
+                                   wxXmlResourceHandler *handlerToUse)
 {
-    if (node == NULL) return NULL;
-
     // handling of referenced resource
-    if ( node->GetName() == wxT("object_ref") )
+    if ( node.GetName() == wxT("object_ref") )
     {
-        wxString refName = node->GetAttribute(wxT("ref"), wxEmptyString);
+        wxString refName = node.GetAttribute(wxT("ref"), wxEmptyString);
         wxXmlNode* refNode = FindResource(refName, wxEmptyString, true);
 
         if ( !refNode )
         {
             ReportError
             (
-                node,
+                &node,
                 wxString::Format
                 (
                     "referenced object node with ref=\"%s\" not found",
             return NULL;
         }
 
-        if ( !node->GetChildren() )
+        if ( !node.GetChildren() )
         {
             // In the typical, simple case, <object_ref> is used to link
             // to another node and doesn't have any content of its own that
             // would overwrite linked object's properties. In this case,
             // we can simply create the resource from linked node.
 
-            return CreateResFromNode(refNode, parent, instance);
+            return DoCreateResFromNode(*refNode, parent, instance);
         }
         else
         {
             // load the resource from result of the merge.
 
             wxXmlNode copy(*refNode);
-            MergeNodesOver(copy, *node, GetFileNameFromNode(node, Data()));
+            MergeNodesOver(copy, node, GetFileNameFromNode(&node, Data()));
 
             // remember referenced object's file, see GetFileNameFromNode()
             copy.AddAttribute(ATTR_INPUT_FILENAME,
                               GetFileNameFromNode(refNode, Data()));
 
-            return CreateResFromNode(©, parent, instance);
+            return DoCreateResFromNode(copy, parent, instance);
         }
     }
 
     if (handlerToUse)
     {
-        if (handlerToUse->CanHandle(node))
+        if (handlerToUse->CanHandle(&node))
         {
-            return handlerToUse->CreateResource(node, parent, instance);
+            return handlerToUse->CreateResource(&node, parent, instance);
         }
     }
-    else if (node->GetName() == wxT("object"))
+    else if (node.GetName() == wxT("object"))
     {
         for ( wxVector<wxXmlResourceHandler*>::iterator h = m_handlers.begin();
               h != m_handlers.end(); ++h )
         {
             wxXmlResourceHandler *handler = *h;
-            if (handler->CanHandle(node))
-                return handler->CreateResource(node, parent, instance);
+            if (handler->CanHandle(&node))
+                return handler->CreateResource(&node, parent, instance);
         }
     }
 
     ReportError
     (
-        node,
+        &node,
         wxString::Format
         (
             "no handler found for XML node \"%s\" (class \"%s\")",
-            node->GetName(),
-            node->GetAttribute("class", wxEmptyString)
+            node.GetName(),
+            node.GetAttribute("class", wxEmptyString)
         )
     );
     return NULL;
     {
         if ( IsObjectNode(n) )
         {
-            m_resource->CreateResFromNode(n, parent, NULL,
-                                          this_hnd_only ? this : NULL);
+            m_resource->DoCreateResFromNode(*n, parent, NULL,
+                                            this_hnd_only ? this : NULL);
         }
     }
 }