• TreeView的动态显示及利用框架实现导航


          在Asp.net中我们知道TreeView控件可以实现站点导航功能,利用模板加上站点地图作为TreeView的DataSource就可以实现轻松的导航功能。我本次所要实现的导航抛开了模板和站点地图,利用框架动态实现导航。

        我们知道,TreeView控件可以静态的预定义其结构,支持的数据源控件有XmlDataSource SiteMapDataSource ,并不支持sqldatasource控件。这次我们的数据源正是数据库,所以我们可以动态的填充TreeView的节点。在实现TreeView的动态填充节点后,我们可以利用iframe框架,来实现导航。

    一.对TreeView控件本次所要用到的属性及事件的介绍

    1.TreeNode.SelectAction属性:获取或设置选择节点时引发的事件,此属性的值为TreeNodeSelectAction 值之一,默认为TreeNodeSelectAction.Select。TreeView的文本节点可以处于两种模式之一,默认情况下,会有一个节点处于选定状态,即TreeNodeSelectAction.Select,此模式下引发SelectedNodeChanged事件,引发后节点只会展开,不会折叠。若要使一个节点处于导航模式,可以把该节点的 NavigateUrl 属性值设置为空字符串 ("") 以外的值。若要使节点处于选择模式,可以把节点的 NavigateUrl 属性设置为空字符串。

    2.TreeNode.PopulateOnDemand属性:该属性只为bool类型,获取或设置一个值,该值指示是否动态填充节点,默认为false。当节点的 PopulateOnDemand 属性设置为 true 时,在运行阶段展开节点时通过回发事件填充节点。若要动态填充节点,必须为 TreeNodePopulate 事件定义填充节点的事件处理方法。

    3.TreeNode.TreeNodePopulate事件:当节点的 PopulateOnDemand 属性设置为 true ,可以触发该事件,以编程的方式动态填充节点。

    二.实现TreeView的动态填充节点.

    1.由于是获取数据里面的数据,于是写了个SqlHelper类,我前面的一篇文章详细叙述过,里面同样介绍了数据库的关系图,感兴趣的朋友可以参考对DataList控件绑定图片的一点小结 里的部分内容,这里为了不影响阅读,把代码还是贴出来了:

     

    DALHelper类

    2.建立了一个页面DynamicPlayer.aspx,页面内容为:

    DynamicPlayer.aspx页面内容

     3.实现TreeNode.TreeNodePopulate事件

     1  /// <summary>
     2     /// TreeNodePopulate事件,实现动态填充叶节点
     3     /// </summary>
     4     /// <param name="sender"></param>
     5     /// <param name="e"></param>
     6     protected void trPlayer_TreeNodePopulate(object sender, TreeNodeEventArgs e)
     7     {
     8         if (e.Node.ChildNodes.Count==0)
     9         {
    10             switch (e.Node.Depth)
    11             {
    12                 case 0:
    13                     BindTeam(e.Node);//填充第一层节点
    14                     break;
    15                 case 1:
    16                     BindPlayer(e.Node);//填充第二层节点
    17                     break;
    18                 default:
    19                     break;
    20             }
    21         }
    22     }

     4.实现TreeView动态填充节点,主要有两个方法:

      i: BindTeam(TreeNode node),实现第一层节点绑定 

     1 //第一层节点绑定到数据库表里的Team的球队名字
     2     public void BindTeam(TreeNode node)
     3     {
     4         string sql = "select TeamID,TeamNameCH from Team";
     5         DataTable dt = DBHelper.DALHelper.GetDataTable(sql);
     6         if (dt!=null)
     7         {
     8             foreach (DataRow dr in dt.Rows)
     9             {
    10                 TreeNode tn = new TreeNode(Convert.ToString(dr["TeamNameCH"])
    11                 , Convert.ToString(dr["TeamID"]));
    12                 tn.PopulateOnDemand = true;
    13                 tn.SelectAction = TreeNodeSelectAction.Expand;
    14                 node.ChildNodes.Add(tn);
    15             }
    16         }
    17     }

    ii:BindPlayer(TreeNode node):实现第二层节点绑定:

     1 //第二层节点绑定到数据库表里的Player的球员名字
     2     public void BindPlayer(TreeNode node)
     3     {
     4         string sql= "select PlayerID,NameCH from Player where TeamID='{0}'";
     5         sql = string.Format(sql, node.Value);
     6         DataTable dt =DBHelper.DALHelper.GetDataTable(sql);
     7         if (dt != null)
     8         {
     9             foreach (DataRow dr in dt.Rows)
    10             {
    11                
    12                 TreeNode tn = new TreeNode(Convert.ToString(dr["NameCH"]), Convert.ToString(dr["PlayerID"]));
    13                 tn.PopulateOnDemand = false;//设为FALSE时不会在去填充下一级节点
    14 
    15                 //设为select模式可以实现导航,需设置NavigateUrl属性,由于本次实现的
    16                 //是框架内的导航模式,所以NavigateUrl的值为空
    17                 tn.SelectAction = TreeNodeSelectAction.Select;
    18               //  tn.NavigateUrl = "ShowPlayerImage.aspx?PlayerID=" + playerID;
    19                 tn.Target = "myframe";
    20                 node.ChildNodes.Add(tn);
    21             }
    22         }
    23     }

    三.实现当单击叶节点即是点击球员姓名时在iframe中导航至一个已经写好了的专门用来显示球员相片的的页面

    1.显示球员相片的的页面为ShowPlayerImage.aspx。

    页面内容为:

    ShowPlayerImage.aspx页面内容

    后台代码为:

    ShowPlayerImage.aspx后台代码

    2.由于TreeNode里的两事件TreeNodeCollapsed(当节点折叠后触发),TreeNodeExpanded(节点展开后触发)都没有实现导航功能所想要的事件,于是自己自定义了一个关于TreeView的节点单击事所要触发的事件TreeNodeOnClick,每当单击叶节点时都会触发该事件,并导航到显示相片的页面。

    自定义事件的代码为:

     1  //自定义TreeNodeOnClickHandler委托
     2     public delegate void TreeNodeOnClickHandler(object sender, TreeNodeEventArgs e);
     3     //自定义TreeNodeOnClick事件,每当鼠标单击节点时触发该事件
     4     public event TreeNodeOnClickHandler TreeNodeOnClick;
     5  /// <summary>
     6     ///单击叶节点事件, 实现动态导航
     7     /// </summary>
     8     /// <param name="sender"></param>
     9     /// <param name="e"></param>
    10     protected void DynamicPlayer_TreeNodeOnClick(object sender, TreeNodeEventArgs e)
    11     {
    12         string src = "";
    13         string playerID = "";
    14         if (e.Node.ChildNodes.Count == 0 && e.Node.Depth == 2)
    15         {
    16             playerID = e.Node.Value;
    17             src = "ShowPlayerImage.aspx?PlayerID=" + playerID;
    18             //把iframe的属性src会发给客户端时赋给一个hidden
    19             Page.ClientScript.RegisterHiddenField("srcHidden", src);
    20             //注册客户端脚本,给iframe的属性src赋值,这样就可以在框架内导航到另外一个页面
    21             Page.ClientScript.RegisterStartupScript(this.GetType(), "registFrameAttribute",
    22                 "var frame=document.getElementById('myframe');frame.src=document.getElementById('srcHidden').value;",true);
    23         }
    24     }

    3.每次我们单击叶节点会向服务器回发,此时就可以实现导航,代码为:

     1  protected void Page_Load(object sender, EventArgs e)
     2     {
     3         //每次单击节点时回发
     4         if (IsPostBack)
     5         {
     6             //注册事件
     7              this.TreeNodeOnClick += new TreeNodeOnClickHandler(DynamicPlayer_TreeNodeOnClick);
     8             //如果是叶节点并且被选中事,触发自定义的TreeView的Click事件
     9              if (trPlayer.SelectedNode.Selected&&trPlayer.SelectedNode.ChildNodes.Count==0)
    10              {
    11                  TreeNodeOnClick(thisnew TreeNodeEventArgs(trPlayer.SelectedNode));
    12              }
    13         }
    14        
    15     }

    这样就简单实现了我说的全部功能,运行后效果为:

  • 相关阅读:
    51 Nod 1086 多重背包问题(单调队列优化)
    51 Nod 1086 多重背包问题(二进制优化)
    51 Nod 1085 01背包问题
    poj 2559 Largest Rectangle(单调栈)
    51 Nod 1089 最长回文子串(Manacher算法)
    51 Nod N的阶乘的长度 (斯特林近似)
    51 Nod 1134 最长递增子序列(经典问题回顾)
    51 Nod 1020 逆序排列
    PCA-主成分分析(Principal components analysis)
    Python中cPickle
  • 原文地址:https://www.cnblogs.com/ecin/p/1487735.html
Copyright © 2020-2023  润新知