|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Announcements
Chapters
Services
Feature Zones
|
IntroductionThis article demonstrates how to use the free Please provide a rating / vote before leaving this articleThis is the only way authors get any type of credit for their work they freely share with everyone. It's sad to see articles that have helped over 100,000 people and fewer than 200 bother to vote or provide a rating. BackgroundOne common control used in web development is the One issue in using Microsoft’s free control is the lack of support and the fact that the control is designed to leverage ASP.NET’s server-side eventing architecture. Experienced web developers strive to reduce or eliminate as many server round trips as possible (commonly known as post-backs) to increase the end user’s satisfaction and response times. This article will demonstrate how to use Microsoft’s The control used in this article is a free download from Microsoft, and the control's overview is included in their online documentation. What is the Microsoft TreeView?
The tree view provides an object oriented hierarchical or parent/child relationship view of data and meta-data. The most common example of a tree view is Windows Explorer’s directory structure where disk drives contain folders, folders contain sub-folders and folders contain files. The MS
What is the NodeData property?The The issue is the property’s underlying type is a string. So how do you store several pieces of meta-data in the property? Well, I’ve found the easiest way to do this is to create a delimited list of key valued pairs that can be accessed on either the client or server. I typically use a semi-colon (;) as the main delimiter and separate the key and value with an equal sign (=). For example, I would store meta-data in a tree node’s TreeNode tn = new TreeNode();
tn.Text = "Root Parent Node";
tn.NodeData = "Id=1000;Name=Mike Elliott;Article=ASP.NET " +
"Tree View Control & the Client's Browser";
You can get at the You could choose to use XML instead of a key valued pair, but for performance reasons, I prefer to work with key valued pairs because they are stored in arrays. Preparing to build the examplesBefore jumping into examples, I want to provide a little set-up information in case you want to follow along. The first step is to download Microsoft’s free control suite. The control suite contains more than just the Be prepared, the .bat file distributed with the free download has a bug that may prevent the .dll from being produced (most of the time), and there are no warnings or exception messages given. Open the build.bat file in Notepad, and find the line that reads: csc.exe /out:build\Microsoft.Web.UI.WebControls.dll @IEWebControls.rsp
Unless you have placed the csc.exe compile utility in your main path or placed a copy of the executable in the system or system32 directory, the .bat file will not find the compile utility and fails silently. To correct this, modify the .bat file to have the full path to the csc.exe compile utility as shown below (the location and version may be different on your machine): C:\Windows\Microsoft.NET\Framework\v1.14322\csc.exe
/out:build\Microsoft.Web.UI.WebControls.dll @IEWebControls.rsp
This should correct the build issue and allow the Microsoft.Web.UI.WebControls.dll to be produced as the readme indicates in the download. Complete the installation instructions as detailed in the readme file. Once you have properly installed the control library, create a new ASP.NET web application and add a reference to the newly created Microsoft.Web.UI.WebControls.dll. Next, add a Web Form named TVExample.aspx to the new web project. Now you will be ready to copy and paste the code as it is described in the article. Client side eventsI am going to demonstrate how to intercept the following events on the client instead of allowing server-side post-backs.
These are the most common events you will need to intercept to prevent the intrinsic server-side events or post-backs from happening. This should greatly increase your end user’s experience and increase the response time. It will also reduce the load on your web servers by pushing much of the work to the client’s machine. The following examples are going to display the intercepted event, how to get the meta-data from the tree node's Getting to the codeOne point I want to make before getting into the code is ASP.NET provides access to most HTML and JavaScript attributes through the The HTML and the JavaScript code we will use to intercept what are typically server-side events is pretty straightforward and should be self-documenting, but here are a few high points to which you should pay attention:
The entire TVExample.aspx code set<%@ Page language="c#" Codebehind="TVExample.aspx.cs"
AutoEventWireup="false"
Inherits="Mike.Elliott.Articles.TreeView.TVExample" %>
<%@ Register TagPrefix="iewc"
Namespace="Microsoft.Web.UI.WebControls"
Assembly="Microsoft.Web.UI.WebControls" %>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<head>
<title>Tree View Example</title>
<meta name="GENERATOR"
Content="Microsoft Visual Studio .NET 7.1">
<meta name="CODE_LANGUAGE" Content="C#">
<meta name=vs_defaultClientScript content="JavaScript">
<meta name=vs_targetSchema
content="http://schemas.microsoft.com/intellisense/ie5">
</head>
<body MS_POSITIONING="GridLayout">
<script language="javascript">
// Intercepts the index changed event on the client.
//
function TVIndexChanged()
{
ChangeText( 'node changed' );
}
// Intercepts the expand event on the client.
//
function TVNodeExpand()
{
ChangeText( 'onexpand' );
}
// Intercepts the collapse event on the client.
//
function TVNodeCollapse()
{
ChangeText( 'oncollapse' );
}
// Intercepts the double-click event on the client.
//
function TVDoubleClick()
{
ChangeText( 'dblclick' );
}
// Intercepts the right-click event
// on the client. The selected
// tree node is changed to the node
// over which the end user has
// right-clicked so that, that node's
// meta-data can be obtained.
//
function TVRightClick()
{
// Get a handle to the tree view.
var tree = GetTreeHandle();
var treenode;
if ( null == tree || undefined == tree )
return;
// Get the selected node.
treenode = tree.getTreeNode( event.treeNodeIndex );
if ( null == treenode || undefined == treenode )
return;
// Cause the tree node that was
// right-clicked on to become the
// selected node.
tree.selectedNodeIndex = event.treeNodeIndex;
ChangeText( 'oncontextmenu' );
}
// Simply changes the information
// in the display text boxes to
// demonstrate how to obtain meta-data
// from the selected node's
// NodeData property on the client.
//
function ChangeText( eventName )
{
var treeNode = GetSelectedNode();
if ( null == treeNode || undefined == treeNode )
{
return;
}
var nodeData =
treeNode.getAttribute( 'nodeData' ).split( ';' );
var id = GetKeyValue( 'SomeId' );
var name = GetKeyValue( 'Name' );
document.getElementById( 'txtEvent' ).value =
eventName;
document.getElementById( 'txtId' ).value = id;
document.getElementById( 'txtName' ).value = name;
}
// Gets the value of the searchKey
// from the NodeData of a TreeNode.
//
function GetKeyValue( searchKey )
{
// Get a handle to the selected TreeNode.
var treenode = GetSelectedNode();
// Validate the node handle.
if ( null == treenode || undefined == treenode )
return null;
// Get the node's NodeData property's value.
var nodeDataAry = treenode.getAttribute( 'nodeData' );
if ( null == nodeDataAry || undefined == nodeDataAry )
return null;
nodeDataAry = nodeDataAry.split( ';' );
if ( null == nodeDataAry || undefined == nodeDataAry ||
0 >= nodeDataAry.length )
return null;
var count = 0;
var returnValue = null;
while ( count < nodeDataAry.length )
{
var workingItem = nodeDataAry[ count ];
if ( 0 >= workingItem.length )
{
count++;
continue;
}
// Split the string into its key value pairs.
var kv = workingItem.split( '=' );
if ( 1 >= kv.length )
{
count++;
continue;
}
var key = kv[ 0 ];
var kValue = kv[ 1 ];
if ( key != searchKey )
{
count++;
continue;
}
returnValue = kValue;
break;
}
return returnValue;
}
// Gets a handle to the TreeView.
//
function GetTreeHandle()
{
var tree;
var treeName = 'tvControl';
// Get a handle to the TreeView.
tree = document.getElementById( treeName );
if ( null == tree || undefined == tree )
return null;
return tree;
}
// Gets a handle to the TreeView's selected node.
//
function GetSelectedNode()
{
var tree = GetTreeHandle();
var treeNode;
if ( null == tree || undefined == tree )
return null;
treeNode = tree.getTreeNode( tree.selectedNodeIndex );
if ( null == treeNode || undefined == treeNode )
return null;
return treeNode;
}
</script>
<form id="frmTVExample" method="post" runat="server">
<table width="100%" align="center" border="0">
<tr><td>
<iewc:treeview id="tvControl" runat="server"
SystemImagesPath=
"/webctrl_client/1_0/treeimages/"
EnableViewState="False">
</iewc:treeview>
</td></tr>
<tr>
<td><input type="text" id="txtId" name="txtId">
</td></tr>
<tr>
<td><input type="text" id="txtName" name="txtName">
</td></tr>
<tr>
<td><INPUT type="text" id="txtEvent" name="txtEvent">
</td> </tr>
</table>
</form>
</body>
</html>
The TVExample.aspx.cs or code behind (this section does not include the using Microsoft.Web.UI.WebControls;
namespace Mike.Elliott.Articles.TreeView
{
public class TVExample : System.Web.UI.Page
{
protected Microsoft.Web.UI.WebControls.TreeView tvControl;
private void Page_Load( object sender, System.EventArgs e )
{
// Create the root tree node.
TreeNode root = new TreeNode();
root.Text = "Root Parent Node";
root.NodeData = "SomeId=1000;Name=Mike Elliott";
// Create a child node.
TreeNode tn = new TreeNode();
tn.Text = "Child 1 of Root Parent";
tn.NodeData = "SomeId=1001;Name=Play For Sport, Inc.";
// Add the child to the root node.
root.Nodes.Add( tn );
// Create another child node.
tn = new TreeNode();
tn.Text = "Child 2 or Root Parent";
tn.NodeData = "SomeId=1002;Name=Chip Oxendine";
// Create a grandchild node and add it to its parent.
TreeNode cn = new TreeNode();
cn.Text = "Grandchild of Root Parent";
cn.NodeData = "SomeId=1003;Name=Mike Elliott";
tn.Nodes.Add( cn );
// Add the child to the root node.
root.Nodes.Add( tn );
root.Expanded = true;
// Add all the nodes to the tree view.
this.tvControl.Nodes.Add( root );
this.OverRideServerEvents();
}
private void OverRideServerEvents()
{
// Create and wire up the javascript event handlers.
//
string clickHandler = "TVIndexChanged();";
this.tvControl.Attributes.Add( "onselectedindexchange",
clickHandler );
clickHandler = "TVNodeExpand();";
this.tvControl.Attributes.Add( "onexpand",
clickHandler );
clickHandler = "TVNodeCollapse();";
this.tvControl.Attributes.Add( "oncollapse",
clickHandler );
clickHandler = "TVDoubleClick();";
this.tvControl.Attributes.Add( "ondblclick",
clickHandler );
clickHandler = "TVRightClick();";
this.tvControl.Attributes.Add( "oncontextmenu",
clickHandler );
}
}
}
The Next, the When you cause any of the events to fire, the events are intercepted by our JavaScript functions, the target tree node’s meta-data is parsed and displayed in the text boxes and the intercepted event’s name is also displayed so you can see exactly what's happening.
What's going on?
Although I didn’t cover it in this article, you can completely manage the tree view’s state on the client by storing the state of each tree node (expanded/collapsed). This is something you will need to do to completely push the tree view’s functionality to the client. Otherwise, as soon as you cause a post-back, you will lose the state of which nodes were expanded, which nodes were collapsed and which node was selected. This is a topic that is a little more involved, and I will cover in a subsequent article. SummaryIt is very much possible to move the heavy server-side events to the client to streamline your ASP.NET applications that make use of the free MS History
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||