DrawTreeNodeEventArgs Class
Collapse the table of content
Expand the table of content

DrawTreeNodeEventArgs Class


Provides data for the DrawNode event.

Namespace:   System.Windows.Forms
Assembly:  System.Windows.Forms (in System.Windows.Forms.dll)


public class DrawTreeNodeEventArgs : EventArgs

System_CAPS_pubmethodDrawTreeNodeEventArgs(Graphics, TreeNode, Rectangle, TreeNodeStates)

Initializes a new instance of the DrawTreeNodeEventArgs class.


Gets the size and location of the TreeNode to draw.


Gets or sets a value indicating whether the TreeNode should be drawn by the operating system rather than being owner drawn.


Gets the Graphics object used to draw the TreeNode.


Gets the TreeNode to draw.


Gets the current state of the TreeNode to draw.


Determines whether the specified object is equal to the current object.(Inherited from Object.)


Allows an object to try to free resources and perform other cleanup operations before it is reclaimed by garbage collection.(Inherited from Object.)


Serves as the default hash function. (Inherited from Object.)


Gets the Type of the current instance.(Inherited from Object.)


Creates a shallow copy of the current Object.(Inherited from Object.)


Returns a string that represents the current object.(Inherited from Object.)

Use the DrawNode event to customize the appearance of nodes in a TreeView control using owner drawing.

The DrawNode event is raised by a TreeView control when its TreeView.DrawMode property is set to TreeViewDrawMode.OwnerDrawAll or TreeViewDrawMode.OwnerDrawText and a node is displayed or updated. The DrawTreeNodeEventArgs passed to the event handler contains information about the node to draw as well as providing methods to help you draw the node.

Use the State or Node properties to retrieve information about the node to draw. Use the Graphics property to do the actual drawing within the area specified by the Bounds property. To make the operating system draw a node that does not need to be owner drawn, set the DrawDefault property to true.

When the TreeView.DrawMode property is set to TreeViewDrawMode.OwnerDrawText, the area indicated by the Bounds property includes the label portion of the node only. When the TreeView.DrawMode property is set to TreeViewDrawMode.OwnerDrawAll, the Bounds area includes the entire node, including the area typically used for icons, checkboxes, plus and minus signs, and lines connecting the nodes.

Legacy Code Example

The following code example demonstrates how to customize a TreeView control using owner drawing. The TreeView control in the example displays optional node tags alongside the standard node labels. Node tags are specified using the TreeNode.Tag property. The TreeView control also uses custom colors, including a custom highlight color.

You can customize most of the TreeView colors by setting color properties, but the selection highlight color is not available as a property. Additionally, the default selection highlight rectangle extends only around a node label. Owner drawing must be used to draw the node tags and to draw a customized highlight rectangle large enough to include a node tag.

In the example, a handler for the TreeView.DrawNode event draws the node tags and the custom selection highlight manually. Unselected nodes do not need customization. For these, the DrawDefault property is set to true so that they will be drawn by the operating system.

Additionally, a handler for the Control.MouseDown event provides hit-testing. By default, a node can be selected only by clicking the region around its label. The Control.MouseDown event handler selects a node that is clicked anywhere within this region or within the region around a node tag, if present.

// Create a namespace that contains a class, MyItem,
// that implements the IStateManager interface and 
// another, MyControl, that overrides its own view-state
// management methods to use those of MyItem.
using System;
using System.Web;
using System.Web.UI;
using System.Collections;
using System.Security.Permissions;

namespace StateBagSample
    // Create a class that implements IStateManager so that
    // it can manage its own view state.   
       Level = AspNetHostingPermissionLevel.Minimal)]
    public sealed class MyItem : IStateManager
        private string _message;

        // The StateBag object that allows you to save
        // and restore view-state information.
        private StateBag _viewstate;

        // The constructor for the MyItem class.
        public MyItem(string mesg)
            _message = mesg;
            _viewstate = new StateBag();
            _viewstate.Add("message", _message);

        // Create a Message property that reads from and writes
        // to view state. If the set accessor writes the message
        // value to view state, the StateBag.SetItemDirty method
        // is called, telling view state that the item has changed. 
        public string Message
                return (string)_viewstate["message"];
                _message = value;
                _viewstate.SetItemDirty("message", true);

        // Implement the LoadViewState method. If the saved view state
        // exists, the view-state value is loaded to the MyItem control. 
        void IStateManager.LoadViewState(object savedState)
            _message = (string)_viewstate["message"];
            if (savedState != null)

        // Implement the SaveViewState method. If the StateBag
        // that stores the MyItem class's view state contains
        // a value for the message property and if the value
        // has changed since the TrackViewState method was last 
        // called, all view state for this class is deleted, 
        // using the StateBag.Clear method,and the new value is added.
        object IStateManager.SaveViewState()
            // Check whether the message property exists in 
            // the ViewState property, and if it does, check
            // whether it has changed since the most recent
            // TrackViewState method call.
            if (!((IDictionary)_viewstate).Contains("message") || _viewstate.IsItemDirty("message"))
                // Add the _message property to the StateBag.
                _viewstate.Add("message", _message);
            return ((IStateManager)_viewstate).SaveViewState();

        // Implement the TrackViewState method for this class by
        // calling the TrackViewState method of the class's private
        // _viewstate property.
        void IStateManager.TrackViewState()

        // Implement the IsTrackingViewState method for this class 
        // by calling the IsTrackingViewState method of the class's
        // private _viewstate property. 
        bool IStateManager.IsTrackingViewState
                return ((IStateManager)_viewstate).IsTrackingViewState;

        // Create a function that iterates through the view-state
        // values stored for this class and returns the
        // results as a string.
        public string EnumerateViewState()
            string keyName, keyValue;
            string result = String.Empty;
            StateItem myStateItem;
            IDictionaryEnumerator myDictionaryEnumerator = _viewstate.GetEnumerator();
            while (myDictionaryEnumerator.MoveNext())
                keyName = (string)myDictionaryEnumerator.Key;
                myStateItem = (StateItem)myDictionaryEnumerator.Value;
                keyValue = (string)myStateItem.Value;
                result = result + "<br>ViewState[" + keyName + "] = " + keyValue;
            return result;
    // This class contains an instance of the MyItem class as 
    // private member. It overrides the state management methods 
    // of the Control class, since it has to invoke state 
    // management methods of MyItem whenever its own
    // view state is being saved, loaded, or tracked.
       Level = AspNetHostingPermissionLevel.Minimal)]
    public sealed class MyControl : Control
        private MyItem myItem;
        public MyControl()
            : base()
            myItem = new MyItem("Hello World!");
        // Override the LoadViewState method of the Control class.
        protected override void LoadViewState(object savedState)
            if (savedState != null)
                object[] myState = (object[])savedState;
                if (myState[0] != null)
                if (myState[1] != null)
        // Override the TrackViewState method of the Control class
        // to call the version of this method that was 
        // implemented in the MyItem class.
        protected override void TrackViewState()
            if (myItem != null)

        // Override the SaveViewState method of the Control class to
        // call the version of this method that was implemented by
        // the MyItem class.
        protected override object SaveViewState()
            object baseState = base.SaveViewState();
            object itemState = (myItem != null) ? ((IStateManager)myItem).SaveViewState() : null;
            object[] myState = new object[2];
            myState[0] = baseState;
            myState[1] = itemState;
            return myState;

        public void SetMessage(string mesg)
            myItem.Message = mesg;

        public string GetMessage()
            return myItem.Message;

        // Display the contents of Message and ViewState properties. 
        protected override void Render(HtmlTextWriter output)
            // Track changes to  view state before rendering.
            output.Write("Message: " + myItem.Message);
            output.Write("<br>Enumerating the view state of the custom control<br>");

.NET Framework
Available since 2.0

Any public static (Shared in Visual Basic) members of this type are thread safe. Any instance members are not guaranteed to be thread safe.

Return to top
© 2015 Microsoft