Re: TreeView Dynamic XML Binding



David,

The functionality that exists when I explicitly set the DataFile property in the XmlDataSource control is exactly the functionality I want when I set the value dynamically in the Page_Load event. Everything works fine when it is set in the control, however the error occurs when it is set dynamically. See my reply the Steven Cheng for more detailed code. The following code works the way I want it to (I'll add the SelectedNodeChanged event once I get the rest stable. Having the event defined does not change the issue I'm having.).

<asp:TreeView ID="cSchemaTree" runat="server" DataSourceID="cSchemaXML" ExpandDepth="1">
</asp:TreeView>
<asp:XmlDataSource ID="cSchemaXML" runat="server"
DataFile="D:\DotNet\TestData\TestXml.xml"></asp:XmlDataSource>

I'll try changing the code to set the datasource as you show and see if it makes any difference. According to the documentation, I should just be able to set the XmlDataSource.DataFile value and the binding will proceed because of the relationship between the IDs.

Thanks - Rich F.


"David R. Longnecker" <dlongnecker@xxxxxxxxxxxxxxxx> wrote in message news:a0e9b9da345828ca5d3990b6ca6a@xxxxxxxxxxxxxxxxxxxxxxx
Rich-

How are you implementing loading loading the data file on Page_Load? Here's an example of loading the data file dynamically in code behind.

aspx :

<asp:TreeView ID="CompanyTreeXml" runat="server"
ExpandDepth="1" EnableClientScript="true" PopulateNodesFromClient="true" ontreenodedatabound="CompanyTreeXml_TreeNodeDataBound">
<NodeStyle ForeColor="Black" />
</asp:TreeView>

(Notice no DataSourceId attribute or XmlDataSource control).

code-behind:

protected void Page_Load(object sender, EventArgs e)
{
CompanyTreeXml.DataSource = new XmlDataSource { DataFile = "~/Company.xml" };
CompanyTreeXml.DataBind();
}

Programatically loading the DataFile (and generating the XmlDataSource since XmlDataSource implements IHeirarchicalDataSource, which the TreeView will need) is taken care of in those two lines.

Now, with that, I need a bit more to understand what you're trying to do. If you click on the tree node, say USAddress for example, and click that word, the tree expands out--but that's because we're telling it to .Expand rather than .Select.
I want the Expand/Collapse action to happen on the client but the Select
action to be a postback.

How would you know when the user wants to "select" and when they "expand"?


Side question:
It's not quite AJAX, but it is JavaScript that toggles the tables around. If you view the source of a generated page, you can see the WebResource scripts and then the javascript method calls on each of the tree nodes. For example, here's the HTML code generated by the root node, Company:

<td>

<a id="CompanyTreeXmln0" href="javascript:TreeView_ToggleNode(CompanyTreeXml_Data,0,document.getElementById('CompanyTreeXmln0'),' ',document.getElementById('CompanyTreeXmln0Nodes'))">

<img src="/WebResource.axd?d=UK9sboTp8hUXuZ9MjiTSmX-mKNPjvYpQyEaZoUuGRa01&amp;t=633408388558438142" alt="Collapse Company" style="border-width:0;" /></a>

</td>

<td class="CompanyTreeXml_2" style="white-space:nowrap;">

<a class="CompanyTreeXml_0 CompanyTreeXml_1" href="javascript:TreeView_ToggleNode(CompanyTreeXml_Data,0,document.getElementById('CompanyTreeXmln0'),' ',document.getElementById('CompanyTreeXmln0Nodes'))" id="CompanyTreeXmlt0">Company</a>

</td>

If that HTML is a bit heavy (for a single node on your TreeView), I'd recommend checking out the CSS Friendly Adapters (http://www.codeplex.com/cssfriendly). It started out as a MS project, it's now on CodePlex. That same code with the adapters looks like:

<span class="AspNet-TreeView-ClickableNonLink" onclick="ExpandCollapse__AspNetTreeView(this.parentNode.getElementsByTagName('span')[0])"
onmouseover="Hover__AspNetTreeView(this)" onmouseout="UnHover__AspNetTreeView(this)">
Company</span>


HTH.

-dl


--
David R. Longnecker
http://blog.tiredstudent.com

David,

Thanks - quick and great response.

It actually addressed one issue I was interested in and that is
turnning off the postback at all nodes and expand/collapse images.
This opens up my research into the use of the other events.
Implementing as you suggest removed the error. However, it is not
exactly the result I was looking for. I want the Expand/Collapse
action to happen on the client but the Select action to be a postback.
This works fine when I explicitly set the DataFile on the aspx page,
as in your code below. However, when I dynamically set the DataFile in
the Page_Load, the postback generates the null reference error when
clicking the tree node. Any suggesting into what is causing this?

Your response brings up a side question. When I implemented it and
debug on the TreeNodeDataBound event, it fires when expanding. Is this
using AJAX? I'm moving directly from .NET 1.1 to 3.5, so much of this
is new to me.

Thanks again.

"David R. Longnecker" <dlongnecker@xxxxxxxxxxxxxxxx> wrote in message
news:a0e9b9da344298ca5ca0634b8a3a@xxxxxxxxxxxxxxxxxxxxxxx

Rich-

If I understand correctly, you're trying to create a TreeView based
off of an XML file and retain the expand/collapse functionality but
AVOID the postbacks and flicker, correct?

You can do this by setting the SelectAction to Expand when you
databind your nodes. Here's some sample code I whipped up using your
XML:

aspx:

<asp:TreeView ID="CompanyTreeXml" runat="server"
DataSourceID="CompanyXml"
ExpandDepth="1" EnableClientScript="true"
PopulateNodesFromClient="true"
ontreenodedatabound="CompanyTreeXml_TreeNodeDataBound">
</asp:TreeView>
<asp:XmlDataSource ID="CompanyXml" runat="server"
DataFile="~/Company.xml">
</asp:XmlDataSource>
code-behind:

protected void CompanyTreeXml_TreeNodeDataBound(object sender,
TreeNodeEventArgs e)
{
e.Node.SelectAction = TreeNodeSelectAction.Expand;
}
At this point, CSS or a NodeStyle would be required because the
TreeView generates any Expandable node as a hyperlink and any
non-expanding node as as plain text.

Since EnableClientScript is still enabled, the control generates the
according JavaScript and the Expand links do not fire postbacks. By
default, I think, the TreeNodeSelectAction is set to Select, not
Expand, which fires the SelectedNodeChanged event.

Hope this helps!

-dl

--
David R. Longnecker
http://blog.tiredstudent.com
I'm dynamically binding an XmlDataSource to an xml file in the
Page_Load event. This XmlDataSource control is the DataSourceID for
a TreeView control. I'm receiving a null reference error prior to
entering the Page_Load event when selecting a tree text value.

Page_Load code snippet:
cSchemaXML.DataFile = @"D:\Schemas\2008\Schema_Tree.xml";
Note: The file path above will be calculated once I get it working.
This is for testing only. The code is not in a !this.IsPostBack
conditional.
Aspx page snippet:
<asp:TreeView ID="cSchemaTree" runat="server"
DataSourceID="cSchemaXML"
ExpandDepth="1">
</asp:TreeView>
<asp:XmlDataSource ID="cSchemaXML"
runat="server"></asp:XmlDataSource>
When I click on the tree node (not the Expand icon) for the select
processing, a null reference error (see below) is displayed.
The only way I can get this to work without a the error is to
disable
client
side code:
EnableClientScript="False"
I prefer not to suffer the flashing and time required during
postbacks. I'm simply trying to display the xml element tree
structure. The xml being displayed is nested elements, each
containing
one attribute. If I set the DataFile in the XmlDataSource control
directly, everything works fine. Do I need to set DataFile someplace
other than in the Page_Load event? Some other solution?
Note: If I click a tree node that is part of the initial display
(based on the ExpandDepth setting) I do not get the error until I
expand the tree and then click the node (or one of the expanded
nodes). This may indicate some variance between the viewstate and
the returned tree structure (only a guess).

Sample XML - the actual xml is much more complex and nested much
deeper, but this gives the idea.

<Company FullPath="Company">
<Name FullPath="Company/Name"/>
<Address FullPath="Company/Address">
<USAddress FullPath="Company/Address/USAddress">
<Street FullPath="Company/Address/USAddress/Street" />
<City FullPath="Company/Address/USAddress/City"/>
<State FullPath="Company/Address/USAddress/State" />
<ZipCode FullPath="Company/Address/USAddress/ZipCode" />
</USAddress>
<ForeignAddress FullPath="Company/Address/ForeignAddress" >
<Street FullPath="Company/Address/USAddress/Street" />
<City FullPath="Company/Address/USAddress/City"/>
<StateOrProvince
FullPath="Company/Address/USAddress/StateOrProvince"
/>
<PostalCode FullPath="Company/Address/USAddress/PostalCode" />
<Country FullPath="Company/Address/ForeignAddress/Country" />
</ForeignAddress>
</Address>
</Company>
The error returned when clicking the tree node is:
Server Error in '/' Application.
--------------------------------------------------------------------
--
----------
Object reference not set to an instance of an object.
Description: An unhandled exception occurred during the execution of
the
current web request. Please review the stack trace for more
information
about the error and where it originated in the code.
Exception Details: System.NullReferenceException: Object reference
not
set to an instance of an object.
Source Error:

An unhandled exception was generated during the execution of the
current web request. Information regarding the origin and location
of the exception can be identified using the exception stack trace
below.

Stack Trace:

[NullReferenceException: Object reference not set to an instance of
an
object.]
System.Xml.XmlLoader.Load(XmlDocument doc, XmlReader reader,
Boolean
preserveWhitespace) +24
System.Xml.XmlDocument.Load(XmlReader reader) +96
System.Web.UI.WebControls.XmlDataSource.PopulateXmlDocument(XmlDocum
en
t
document, CacheDependency& dataCacheDependency, CacheDependency&
transformCacheDependency) +305
System.Web.UI.WebControls.XmlDataSource.GetXmlDocument() +154
System.Web.UI.WebControls.XmlHierarchicalDataSourceView.Select()
+14
System.Web.UI.WebControls.TreeView.DataBindNode(TreeNode node) +126
System.Web.UI.WebControls.TreeView.PopulateNode(TreeNode node) +27
System.Web.UI.WebControls.TreeView.LoadPostData(String postDataKey,
NameValueCollection postCollection) +1082
System.Web.UI.WebControls.TreeView.System.Web.UI.IPostBackDataHandle
r.
LoadPostData(String
postDataKey, NameValueCollection postCollection) +11
System.Web.UI.Page.ProcessPostData(NameValueCollection postData,
Boolean
fBeforeLoad) +661
System.Web.UI.Page.ProcessRequestMain(Boolean
includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
+1194
Thanks for any help - Rich F.



.



Relevant Pages

  • Re: TreeView Dynamic XML Binding
    ... I do not provide any databinding because I have no control of the element names and do not know them in advance. ... The test xml file is not in the website folder as in your code. ... you need to expand a node and click on one of the elements in the expanded node. ... When I click on the tree node for the select ...
    (microsoft.public.dotnet.framework.aspnet.webcontrols)
  • Re: TreeView Dynamic XML Binding
    ... I've lost the speed of the default functionality when loading it from the XmlDataSource. ... If you click on the tree node, say USAddress for example, and click that word, the tree expands out--but that's because we're telling it to .Expand rather than .Select. ...
    (microsoft.public.dotnet.framework.aspnet.webcontrols)
  • Re: TreeView Dynamic XML Binding
    ... XmlDataSource control. ... I'm going to put the xml document into a session variable (I don't ... otherwise the entire tree reset. ... telling it to .Expand rather than .Select. ...
    (microsoft.public.dotnet.framework.aspnet.webcontrols)
  • Re: TreeView Dynamic XML Binding
    ... in the web page (which for the actual xml makes it very slow). ... It seems as if the default settings are doing the populate on expand ... otherwise the entire tree reset. ... (Notice no DataSourceId attribute or XmlDataSource control). ...
    (microsoft.public.dotnet.framework.aspnet.webcontrols)
  • Re: TreeView Dynamic XML Binding
    ... the entire xml structure is ... otherwise the entire tree reset. ... (Notice no DataSourceId attribute or XmlDataSource control). ... telling it to .Expand rather than .Select. ...
    (microsoft.public.dotnet.framework.aspnet.webcontrols)

Loading