哪位高人,给一个TreeView的实例好吗?
是要无级限的那种,就像windows里的资源管理器一样的,要可以动态的新增,删除!!
从数据库里读取资料的!!
在下不盛感谢!!

解决方案 »

  1.   

    数据库:
    子ID            父ID       名字       页面地址
     1                0         XX
     2                1         XX
     3                1         XX
      

  2.   

    private void InitTree(TreeNodeCollection Nds,int parentid)
    {
    DataView dv=new DataView();
    TreeNode tmpNd;
    int intId;
    dv.Table=ds.Tables[0];
    dv.RowFilter="Parent_Id=" +parentid;
    foreach(DataRowView drv in dv)
    {
    tmpNd= new TreeNode();
    tmpNd.ID=drv["Func_Id"].ToString();
    tmpNd.Text=drv["Func_Name"].ToString();
    tmpNd.NavigateUrl=drv["Page_Url"].ToString();
    tmpNd.Target ="main";
    Nds.Add(tmpNd);
    intId=Int32.Parse(drv["Parent_Id"].ToString());
    InitTree(tmpNd.Nodes,Int32.Parse(tmpNd.ID));
    }
    }
      

  3.   

    using System;
    using Microsoft.Web.UI.WebControls;
    using System.Data.SqlClient;
    //using Shaka.Database;
    namespace Shaka.Tree
    {
    /// <summary>
    /// Class1 的摘要说明。
    /// </summary>
    public class Tree
    {
    private TreeView tv; public Tree(TreeView p_tv)
    {
    // 把外部的TreeView1对象传进来
    tv = p_tv;
    }
    /// <summary>
    /// 加载树菜单和链接
    /// </summary>
    /// <param name="strTableMain">主表名</param>
    /// <param name="strTableSub">子表名</param>
    /// <param name="strMainId">主表关联Id</param>
    /// <param name="strMainText">主表文本</param>
    /// <param name="strFatherId">子表中连接主表的字段</param>
    /// <param name="strSubText">子表文本</param>
    /// <param name="strSubLink">子表链接</param>
    /// <param name="strConnString">数据库连接字符串</param>
    public void LoadTree(string strTableMain , string strTableSub , string strMainId , string strMainText , string strFatherId ,string strSubText , string strSubLink , string strConnString)
    {
    SqlConnection conn1 = new SqlConnection();
    conn1.ConnectionString = strConnString;
    conn1.Open();
    string strSql1 = "select ";
    strSql1 += strMainId;
    strSql1 += ",";
    strSql1 += strMainText + " ";
    strSql1 += " from ";
    strSql1 += strTableMain;
    SqlCommand comm1 = new SqlCommand(strSql1,conn1);
    SqlDataReader dr1 = comm1.ExecuteReader();
    TreeNode node;
    while(dr1.Read())
    {
    node = new TreeNode();
    node.Text = dr1[strMainText].ToString();
    tv.Nodes.Add(node);
    TreeNode subNode;
    string strSql2 = "select ";
    strSql2 += strSubText;
    strSql2 += ",";
    strSql2 += strSubLink;
    strSql2 += " ";
    strSql2 += "from ";
    strSql2 += strTableSub;
    strSql2 += " where ";
    strSql2 += strFatherId;
    strSql2 += "=";
    strSql2 += dr1[strMainId];
    SqlConnection conn2 = new SqlConnection(strConnString);
    conn2.Open();
    SqlCommand comm2 = new SqlCommand(strSql2 , conn2);
    SqlDataReader dr2 = comm2.ExecuteReader();
    while(dr2.Read())
    {
    subNode = new TreeNode();
    subNode.Text = dr2[strSubText].ToString();
    subNode.NavigateUrl = dr2[strSubLink].ToString();
    node.Nodes.Add(subNode);
    }
    dr2.Close();
    }
    dr1.Close();
    }
    }
    }
      

  4.   

    要无级限的那种,就像windows里的资源管理器一样的,要可以动态的新增,删除!!//--------
    你建数据库的时候有个技巧,把从属的父ID做成
    A_B_C_D_  这些一直延伸的形式,那些读取的时候用递归就可以全部显示了
    其中ABCD是不同从属ID
    示例表如下
    id   父ID
    1    0_
    2    0_1_  
    3    0_2_
    4    0_1_
    5    0_1_4_
    ...   
    n    0_1_4_
    也就是( n  0_1_4_ )从属于id=4的,如果这个继续有子目录,就是0_1_4_n_..
    以此类推,按这样的结构来做比较简单哦
    显示的时候用递归算法,很容易做出来了
      

  5.   

    这里面有个例子 ,使用递规得到所有的数据,不过没有动态的新增,删除
    http://blog.csdn.net/sunnystar365/archive/2005/09/13/479440.aspx
      

  6.   

    1、加載樹節點方法(无级限)
    /// <summary>
    /// 加载树节点。建树的基本思路是:从根节点开始递归调用显示子树。
    /// </summary>
    /// <param name="dt">是DataTable类型的保存树节点的数据表</param>
    /// <param name="nodeID">数据表中保存节点的列名称</param>
    /// <param name="parentID">数据表中保存节点父节点的列名称</param>
    /// <param name="nodeName">数据表中保存节点名称的列名称</param>
    /// <param name="treeNodeCollection">表示TreeView.Nodes对象的集合</param>
    /// <param name="rootNodeTag">定义根节点的父节点的标记</param>
    //法一:用DataView
    public static void InitTree(DataTable dt,string nodeID,string parentID,string nodeName,TreeNodeCollection treeNodeCollection,string rootNodeTag)
    {
    try
    {
    TreeNode tmpNode;
    DataView dv=new DataView();
    dv.Table=dt;
    if (rootNodeTag!=""||rootNodeTag!=null)
    dv.RowFilter=parentID+"='"+rootNodeTag+"'";
    foreach(DataRowView drv in dv)
    {
    tmpNode=new TreeNode();
    tmpNode.Text=drv[nodeName].ToString();
    tmpNode.Tag=drv[nodeID];
    string father=drv[nodeID].ToString();
    treeNodeCollection.Add(tmpNode);
    InitTree(dt,nodeID,parentID,nodeName,tmpNode.Nodes,father);
    }
    }
    catch(Exception te)
    {
    MessageBox.Show(te.Message,"Error",MessageBoxButtons.OK,MessageBoxIcon.Warning);
    }
    }
      

  7.   

    注意:以下為彈出菜單項代碼及相關的函數和方法
    2、增加根節點
    private void menuItemAddRoot_Click(object sender, System.EventArgs e)
    {
    try
    {
    TreeNode treeNode=new TreeNode("新节点");
    treeNode.Tag=MaxRecordNumber(dataSet.Tables["tree"],"NodeID")+1;
    this.treeView.Nodes.Add(treeNode);
    AddDeleteNode(treeNode,RootNodeTag,"Add");
    treeView.SelectedNode = treeNode ;
    LoadTreeView.LoadTreeNodeImage(treeView.SelectedNode,this.imageList1,NodeImageMode);
    //执行指定节点的选定操作
    this.treeViewAfterSelect(treeView.SelectedNode );
    menuItemRename_Click(new object(),new System.EventArgs());
    }
    catch(Exception te)
    {
    MessageBox.Show(this,te.Message,"ErrorRoot",MessageBoxButtons.OK,MessageBoxIcon.Warning);
    }
    }
    3、增加子節點
    private void menuItemAddChild_Click(object sender, System.EventArgs e)
    {
    try
    {
    //1.当一个节点有对应链接资料时,不可以增加子节点
    //2.当一个节点有对应链接资料时,可以增加图片
    if (this.IsHaveLineData(dataSet.Tables["data"],this.richTextBoxId))
    {
    MessageBox.Show(this,"要增加子节点,必须在这个节点没有可以链接的资料后才可以增加!","操作错误",MessageBoxButtons.OK,MessageBoxIcon.Information );
    return;
    }
    TreeNode treeNode=new TreeNode("新节点");
    treeNode.Tag=MaxRecordNumber(dataSet.Tables["tree"],"NodeID")+1;
    treeView.SelectedNode.Nodes.Add(treeNode);
    AddDeleteNode(treeNode,treeView.SelectedNode.Tag.ToString(),"Add");
    treeView.SelectedNode = treeNode ;
    LoadTreeView.LoadTreeNodeImage(treeView.SelectedNode,this.imageList1,NodeImageMode);
    //执行指定节点的选定操作
    this.treeViewAfterSelect(treeView.SelectedNode );
    menuItemRename_Click(new object(),new System.EventArgs());
    }
    catch(Exception te)
    {
    MessageBox.Show(this,te.Message,"ErrorChild",MessageBoxButtons.OK,MessageBoxIcon.Warning);
    }
    }
    4、增加兄弟節點
    private void menuItemAddBorther_Click(object sender, System.EventArgs e)
    {
    try
    {
    //判断是否选定组件中的根节点
    if (treeView.SelectedNode.Parent==null)
    {
    MessageBox.Show ("节点<"+treeView.SelectedNode.Text.Trim()+ ">为根节点,要加入兄弟节点,请使用\"加入根节点\"选项!" , "Information" , MessageBoxButtons.OK , MessageBoxIcon.Information ) ;
    return;
    }
    TreeNode treeNode=new TreeNode("新节点");
    treeNode.Tag=MaxRecordNumber(dataSet.Tables["tree"],"NodeID")+1;
    treeView.SelectedNode.Parent.Nodes.Add(treeNode);
    AddDeleteNode(treeNode,treeView.SelectedNode.Parent.Tag.ToString().Trim(),"Add");
    treeView.SelectedNode = treeNode ;
    LoadTreeView.LoadTreeNodeImage(treeView.SelectedNode,this.imageList1,NodeImageMode);
    //执行指定节点的选定操作
    this.treeViewAfterSelect(treeView.SelectedNode );
    menuItemRename_Click(new object(),new System.EventArgs());
    }
    catch(Exception te)
    {
    MessageBox.Show(this,te.Message,"ErrorParent",MessageBoxButtons.OK,MessageBoxIcon.Warning);
    }
    }
    5、刪除節點
    private void menuItemDelete_Click(object sender, System.EventArgs e)
    {
    try
    {
    if(MessageBox.Show(this,"删除节点《"+treeView.SelectedNode.Text.Trim()+"》,与其对应的信息也将被删除,你确定要删除吗?","Information",MessageBoxButtons.OKCancel,MessageBoxIcon.Question)==DialogResult.OK)
    {
    //判断选定的节点是否存在下一级节点
    if ( treeView.SelectedNode.Nodes.Count == 0 )
    {
    //删除节点
    TreeNode deleNode=treeView.SelectedNode;
    if (File.Exists(this.richTextBoxPictureName)) File.Delete(this.richTextBoxPictureName);
    int rows=myBindTree.Position;
    treeView.Nodes.Remove(deleNode);
    dataSet.Tables["tree"].Rows[rows].Delete();
    }
    else
    MessageBox.Show ( "请先删除此节点中的子节点!" , "Information" , MessageBoxButtons.OK , MessageBoxIcon.Information ) ;
    }
    }
    catch(Exception te)
    {
    MessageBox.Show(this,te.Message,"ErrorDelete",MessageBoxButtons.OK,MessageBoxIcon.Warning);
    }
    }
    6、节点重命名
    private void menuItemRename_Click(object sender, System.EventArgs e)
    {
    TreeNode mySelectedNode=treeView.SelectedNode;
    if (mySelectedNode!=null)
    {
    treeView.SelectedNode=mySelectedNode;
    treeView.LabelEdit=true;
    mySelectedNode.BeginEdit();
    }
    else
    MessageBox.Show("No tree node selected .\n","Invalid selection");
    }/// <summary>
    /// 返回指定表的最大NodeID号码,也就是当前选定节点的tag
    /// </summary>
    /// <param name="dt">数据表</param>
    /// <param name="columnName">数据列</param>
    /// <returns>最大NodeID号码</returns>
    private int MaxRecordNumber(DataTable dt,string columnName)
    {
    int number=0;
    DataView dv=dt.DefaultView;
    dv.Sort=columnName+" ASC";//一个字符串,它包含列名,后跟“ASC”(升序)或“DESC”(降序)。在默认情况下,列按升序排列。多个列可用逗号隔开。
    foreach(DataRow dr in dt.Rows)
    {
    number=Convert.ToInt16(dr[columnName].ToString().Trim())>number?Convert.ToInt16(dr[columnName].ToString().Trim()):number;
    }
    return number;
    }/// <summary>
    /// 在数据表中增加节点或删除节点
    /// </summary>
    /// <param name="addDeleteNode">要增加或删除的节点</param>
    /// <param name="parentNodeId">要增加或删除节点的父节点</param>
    /// <param name="AddDeleteTag">增删节点标志(add为增加节点,delete为删除节点,不区分大小写)</param>
    private void AddDeleteNode(TreeNode addDeleteNode,string parentNodeId,string AddDeleteTag)
    {
    try
    {
    if(AddDeleteTag.ToUpper()=="ADD")
    {
    object key=parentNodeId;
    DataRow dr=dataSet.Tables["tree"].Rows.Find(key);
    DataRow drNew=dataSet.Tables["tree"].NewRow();
    if(dr!=null)
    {
    drNew["ParentID"]=dr["NodeID"];
    }
    else
    {
    drNew["ParentID"]=RootNodeTag;
    }
    drNew["NodeID"]=(int)addDeleteNode.Tag;
    drNew["NodeName"]=addDeleteNode.Text.Trim();
    dataSet.Tables["tree"].Rows.Add(drNew);
    }
    else
    {
    if(AddDeleteTag.ToUpper()=="DELETE")
    {
    dataSet.Tables["tree"].Rows[myBindTree.Position].Delete();
    }
    }
    }
    catch(Exception te)
    {
    MessageBox.Show(this,te.Message,"Error",MessageBoxButtons.OK,MessageBoxIcon.Warning);
    }
    }
      

  8.   

    请参考http://community.csdn.net/Expert/topic/4124/4124603.xml?temp=.7494776