形成层级树关系的方法有很多,大多数用的TreeView,主要用于目录的搜索,通过一个递归算法实现层级的展示,或者说是通过鼠标的点击事件实现递归展示。在这里,我推荐一下更直观的方法,首先这个方法也是用的递归方法,不过它没有用到微软的官方控件,用的是javascript+css。它的好处是一目了然,可用于很多场合,比如说一个部门的展示,形成的最终效果如下:
并且通过点击每一项后会出现这个项的详细解释,如应用于部门的话可以展示一下这个部门的人员等。
它的前台代码如下:
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="生成部门结构树.aspx.cs" Inherits="生成部门结构树" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<title>无标题页</title>
<style type="text/css">
p, span, div, table, tr, td, input
{
font-family: Tahoma;
font-size: 11px;
}
.sectionPaddig
{
padding-left: 4;
padding-right: 4;
filter: progid:DXImageTransform.Microsoft.dropShadow( Color=BCBCBC,offX=2,offY=2,positive=true);
}
.inline
{
display: inline;
vertical-align: text-top;
}
.dotbox
{
display: inline;
height: 1px;
}
.sectionStyle1
{
padding-left: 2;
padding-right: 2;
border: 1px solid #000000;
border-top-color: #000000;
border-left-color: #000000;
border-right-color: #000000;
border-bottom-color: #000000;
background-color: #abcdef;
text-align: center;
cursor: hand;
}
.selected
{
cursor: hand;
color: white;
background-color: gray;
}
.unselected
{
cursor: hand;
}
.skin
{
border-right: buttonhighlight 2px outset;
border-top: buttonhighlight 2px outset;
font-size: 10pt;
visibility: hidden;
border-left: buttonhighlight 2px outset;
100px;
cursor: default;
padding-top: 4px;
border-bottom: buttonhighlight 2px outset;
font-family: "宋体";
position: absolute;
background-color: menu;
text-align: left;
}
.menuitems
{
padding-right: 1px;
padding-left: 10px;
padding-bottom: 2px;
padding-top: 2px;
}
#login_t { z-index:10;border:1px solid #006600;200px;height:200px;background:#FFF;margin:-35px 0 0 595px; position:absolute;}
</style>
<script type="text/javascript">
//当鼠标在部门上面时,显示此部门下的员工
function ShowPerson(DepartmentID)
{
divPerson.style.left = event.clientX+document.documentElement.scrollLeft;
divPerson.style.top = event.clientY+document.documentElement.scrollTop;
divPerson.innerHTML="<img src='http://images.cnblogs.com/animated_loading.gif'/>";
PageMethods.GetPersonByDepartmentID(DepartmentID,SetDivStyle);
divPerson.style.visibility = "visible";
divPerson.style.background = "#E5EEF7";
divPerson.style.position = "absolute";
divPerson.style.width = "50px";
divPerson.style.padding= "10px";
}
//设置此DIV所要显示的员工
function SetDivStyle(msg)
{
if(msg !="")
{
var ArrPerson = new Array();
ArrPerson = msg.split('~');
divPerson.innerHTML = "";
for (var i=0; i<ArrPerson.length; i++)
{
if(i!=ArrPerson.length-1)
{
divPerson.innerHTML += ArrPerson[i] + "<br>";
}
else
{
divPerson.innerHTML += ArrPerson[i];
}
}
}
else
{
divPerson.innerHTML = "空";
}
}
//当鼠标离开时,隐藏此DIV
function HiddenPerson()
{
divPerson.style.visibility = "hidden";
divPerson.innerHTML = "";
}
</script>
</head>
<body>
<form id="form1" runat="server">
<asp:ScriptManager ID="ScriptManager1" EnablePageMethods="true" runat="server">
</asp:ScriptManager>
<div>
<input type="hidden" id="IdepartM" runat="server" />
<div id ="divPerson" style="border:solid 1px #333333; visibility:hidden;filter: progid:DXImageTransform.Microsoft.Shadow(color=#666666,direction=135,strength=3);cursor:hand;" onclick="this.style.visibility ='hidden';"></div>
</div>
</form>
<script language="javascript" type="text/javascript">
var Sys_Group = new Array();
var MaxStack;
/******************************************************************************
*
* Record by 孤海傲月
*
* 说明: Sys_Group 为一个array类型的Array,他的每一个【i】都是一个Array
* 子array= new Array(x, y, z);
* 其中,x 为部门的ID, ------------- DEPARTMENT_ID
* y 为他的父部门的ID,--------- DEPARTMENT_PID
* z 为部门名称。--------------- DEPARTMENT_NAME
*
*******************************************************************************/
// Sys_Group[0] = new Array(1, 0, "总经司");
// Sys_Group[1] = new Array(2, 1, "人事部");
var strDepartM = document.getElementById ('IdepartM').value;
var ArrDepartM = new Array();
ArrDepartM = strDepartM.split(';');
for (var i =0; i<ArrDepartM.length;i++)
{
var ArrDMD = new Array();
ArrDMD = ArrDepartM[i].split(',');
Sys_Group[i] = new Array(ArrDMD[0],ArrDMD[1],ArrDMD[2]);
}
MaxStack=Sys_Group.length;
var str;
var Old_Group=new Array(),Yu_Group =new Array();
for(var i=0; i<MaxStack; i++)
{
Old_Group[i]=new Array(null, null, null);
}
i=0;
Yu_Group=Sys_Group;
str='<table border="0" id=T0 align="center" cellpadding="0" cellspacing="0" class="inline">';
str+=' <tr>';
str+=' <td align="left" valign="top"></td>';
str+=' </tr>';
str+=' <tr>';
str+=' <td align="center" valign="top"></td>';
str+=' </tr>';
str+=' <tr>';
str+=' <td align="center" valign="top" class="sectionPaddig"><table width="150" height="30" border="0" align="center" cellpadding="0" cellspacing="0" class="inline" >';
str+=' <tr>';
str+=' <td align="center" class="sectionStyle1" onclick="ShowPerson('+Sys_Group[0][0]+')" >'+Sys_Group[0][2]+'</td>';
str+=' </tr>';
str+=' </table>';
str+=' </td>';
str+=' </tr>';
str+=' <tr>';
str+=' <td align="center" valign="top">';
if (MaxStack>1)
{//这里是添加竖线
str+='<table border="0" cellpadding="0" cellspacing="0" bgcolor=#000000 width=1 height=15 class="inline" >';
str+=' <tr>';
str+=' <td align=center>';
str+=' </td>';
str+=' </tr>';
str+=' </table>';
}
str+=' </td>';
str+=' </tr>';
str+=' <tr>';
str+=' <td align="center" valign="top">';
Old_Group[0]=Yu_Group[0];
Yu_Group[0]=new Array(null, null, null);
Grouplist(1,0);
str+=' </td>';
str+=' </tr>';
str+='</table>';
//alert(str);
document.write(str);
function Grouplist(InGroup_ID,A)
{
var Old_Find,Yu_Find,YuID_Find,TempGroup_ID,TestStr;
if (A==MaxStack)
{
return;
}
for(var i=0; i<MaxStack; i++)
{
if (Yu_Group[i][1]!=null && Yu_Group[i][1]== InGroup_ID )
{
str+='<table border="0" id=T'+Sys_Group[i][0]+' align="center" cellpadding="0" cellspacing="0" class="inline">';
for (var j=0; j<MaxStack; j++)
{
Old_Find=false;
if (Yu_Group[i][1]!=null && Old_Group[j][1]!=null && Old_Group[j][1]==Yu_Group[i][1])
{
Old_Find=true;
break;
}
}
for (var j=0; j<MaxStack; j++)
{
Yu_Find=false;
if ( i!=j && Yu_Group[i][1]!=null && Yu_Group[j][1]==Yu_Group[i][1] && Yu_Group[j][0]!=Yu_Group[i][0] )
{
Yu_Find=true;
// if (i==4)
// {
// alert(Yu_Find);
// }
break;
}
}
for (var j=0; j<MaxStack; j++)
{
YuID_Find=false;
if ( i!=j && Yu_Group[i][1]!=null && Yu_Group[j][1]==Yu_Group[i][0] )
{
YuID_Find=true;
break;
}
}
str+=' <tr>';
if (Old_Find==false&&Yu_Find==false)
{
str+=' <td align="center" valign="top" >';
str+='<table border="0" cellpadding="0" cellspacing="0" bgcolor=#000000 width=1 class="dotbox" >';
str+=' <tr>';
str+=' <td align=center ></td>';
str+=' </tr>';
str+=' </table>';
str+='</td>';
}
if (Old_Find==true&&Yu_Find==false)
{
str+=' <td align="left" valign="top">';
str+='<table border="0" cellpadding="0" cellspacing="0" bgcolor=#000000 width=50% class="dotbox" >';
str+=' <tr>';
str+=' <td align=center ></td>';
str+=' </tr>';
str+=' </table>';
str+='</td>';
}
if (Old_Find==true&&Yu_Find==true)
{
str+=' <td align="center" valign="top">';
str+='<table border="0" cellpadding="0" cellspacing="0" bgcolor=#000000 width=100% class="dotbox" >';
str+=' <tr>';
str+=' <td align=center ></td>';
str+=' </tr>';
str+=' </table>';
str+='</td>';
}
if (Old_Find==false&&Yu_Find==true)
{
str+=' <td align="right" valign="top">';
str+='<table border="0" cellpadding="0" cellspacing="0" bgcolor=#000000 width=50% class="dotbox" >';
str+=' <tr>';
str+=' <td align=center ></td>';
str+=' </tr>';
str+=' </table>';
str+='</td>';
}
str+=' </tr>';
str+=' <tr>';
// str+=' <td align="center" valign="top"><img src="http://images.cnblogs.com/line_4.gif" width="60" height="15" class="inline"></td>';
str+=' <td>';
str+='<table border="0" cellpadding="0" cellspacing="0" bgcolor=#000000 width=1 height=15 class="inline" >';
str+=' <tr>';
str+=' <td align=center>';
str+=' </td>';
str+=' </tr>';
str+=' </table>';
str+=' </td>';
str+=' </tr>';
str+=' <tr>';
// str+=' <td align="center" valign="top" class="sectionPaddig"><table width="80" height="30" border="0" align="center" cellpadding="0" cellspacing="0" class="inline" >';
str+=' <td align="center" valign="top" class="sectionPaddig"><table width="20" height="100" border="0" align="center" cellpadding="0" cellspacing="0" class="inline" >';
str+=' <tr>';
str+=' <td align="center" class="sectionStyle1" onclick="ShowPerson('+Sys_Group[i][0]+')" >'+Sys_Group[i][2]+'</td>';
str+=' </tr>';
str+=' </table>';
str+=' </td>';
str+=' </tr>';
str+=' <tr>';
str+=' <td align="center" valign="top">';
if(YuID_Find==true)
{
str+=' <table border="0" cellpadding="0" cellspacing="0" class="inline" >';
str+=' <tr>';
str+=' <td>';
// str+=' <img src="http://images.cnblogs.com/line_4.gif" width="60" height="15" class="inline">';
str+='<table border="0" cellpadding="0" cellspacing="0" bgcolor=#000000 width=1 height=15 class="inline" >';
str+=' <tr>';
str+=' <td align=center>';
str+=' </td>';
str+=' </tr>';
str+=' </table>';
str+=' </td>';
str+=' </tr>';
str+=' </table>';
}
str+=' </td>';
str+=' </tr>';
str+=' <tr>';
str+=' <td align="center" valign="top">';
Old_Group[i]=Yu_Group[i];
TempGroup_ID=Yu_Group[i][0];
Yu_Group[i]=new Array(null, null, null);
//alert(TempGroup_ID);
Grouplist(TempGroup_ID,i);
str+=' </td>';
str+=' </tr>';
str+='</table>';
}
}
}
</script>
</body>
</html>
主要应用的是递归算法,这个方法比较通用,需要的时候直接拿过来用就可以,主要不同的是后台代码,通过从数据库中调用数据,反馈给前台,从而达到了展示的目的。在这里我举了一个例子,是一部美剧,吸血鬼日记,展示了一下吸血鬼家族,这里没有用到数据库,只是通过集合类模拟一下,用于项目时可以自己修改,后台代码如下:
using System;
using System.Collections.Generic;
using System.Configuration;
using System.Data;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.HtmlControls;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
public partial class 生成部门结构树 : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
List<Dapartment> list = new List<Dapartment>();
Dapartment a = new Dapartment("1", "0", "尼克劳斯家族");
Dapartment b1 = new Dapartment("2", "1", "吸血鬼祖先克劳斯");
Dapartment b2 = new Dapartment("3", "1", "吸血鬼祖先以利亚");
Dapartment c1 = new Dapartment("4", "3", "凯瑟琳");
Dapartment d1 = new Dapartment("5", "4", "达蒙");
Dapartment d2 = new Dapartment("6", "4", "斯蒂夫");
list.Add(a);
list.Add(b1);
list.Add(b2);
list.Add(c1);
list.Add(d1);
list.Add(d2);
if (!IsPostBack)
{
string strDepartMent = "";
for (int i = 0; i < list.Count; i++)
{
strDepartMent += list[i].department_id + ",";
strDepartMent += list[i].department_pid + ",";
strDepartMent += list[i].department_name + ";";
}
strDepartMent = strDepartMent.Substring(0, strDepartMent.Length - 1);
this.IdepartM.Value = strDepartMent;
}
}
//当点击名字时调用此方法
[System.Web.Services.WebMethod]
public static string GetPersonByDepartmentID(string DepartmentID)
{
string result = "";
result += "他们都是吸血鬼" + "~" + "他们都是好人" + "~" + "他们长生不老";
return result;
}
}
public class WebFuWuduan
{
}
public class Dapartment
{
public string department_id
{ get; set; }
public string department_pid
{ get; set; }
public string department_name
{ get; set; }
public Dapartment() { }
public Dapartment(string department_id, string department_pid, string department_name)
{
this.department_id = department_id;
this.department_pid = department_pid;
this.department_name = department_name;
}
}
需要注意的是,这里当点击前台的节点时,用的是微软AJAX的方法,这个方法在VS2008及其以上都是封装好的,直接可以调用,比较方便,如果是VS2005的话,需要引用AjaxPro.dll组件,也可以实现相同的效果。
通过这两个页面就可以实现层级数的展示了,可以试一下。