今天比较郁闷的一件事情,就是用TreeView动态加载目录,从数据库中将目录读出来。
9 J8 B4 p7 V7 K! [6 b+ `这个应该用动态规划比较简单,但是最近确实是用脑过度了,脑子里全是浆糊,就用下面要讲的死办法了~~==!
% y: v6 k! q% \& y3 T& q/ U因为数据库设计的时候没有考虑到动态目录树的问题,没有在数据表中比较有前瞻性地设置上级编号、下级编号,只能将不同级别的目录内同一个一个找出来,我的这次,就用到了三张表,采用3重循环将数据添加到TreeNode中去:- step1:绑定节点数据* d# k% o- _5 `6 J5 {9 c" ^
- public TreeNode GetTreeNode()
$ B8 }) Z% u# e - {//这个函数还要做优化,因为这样写和数据库的交互会比较多,待有时间了再修改好了+ _6 e$ S$ f! ~
- int i = 0;8 J1 Z: \5 j8 ?" c+ J
- int n = 0;
6 A6 y. b6 h( ~5 f; [5 b+ O E- K
# h4 ^. A1 |# `& g" k- this.currentUserID = (int)Session[SessionStr.CurrentUserID];8 y' s; V1 H. f* m% b+ z
9 i, n% c% y3 n- @5 y- TreeNode treeNode = new TreeNode();
0 D" m$ r- o9 f6 F - DataTable dtCourse = CourseManagementBL.GetCourseIDListByStudentUserID(this.currentUserID);" x1 ?$ }/ X* R+ G7 X7 o
- foreach (DataRow row in dtCourse.Rows)" _: O1 g/ Z4 r
- {
: W9 U0 t' W" ^! y* i - treeNode.ChildNodes.Add(new TreeNode(row[1].ToString()));( w6 k' L& \& ~* A' e3 c
- foreach (DataRow Experiment_row in ExperimentManagementBL.GetExperimentNameListByCourseID(int.Parse(row["courseID"].ToString())).Rows)! r: C) T+ o S% Z8 B) i
- {7 ^. U+ A0 q: @( _. I6 s
- TreeNode expNode = new TreeNode();
7 `, X( \8 S5 v8 Y5 U }) q2 V( g - expNode.Text = Experiment_row[1].ToString();) ~. k! Q2 [4 \" u/ k0 n% X; i
- treeNode.ChildNodes[i].ChildNodes.Add(expNode);# W( b: @; p) T( v, ]
- 3 f$ m- h3 I: P- \" ~
- //treeNode.ChildNodes[i].ChildNodes.Add(new TreeNode(Experiment_row[1].ToString()));
. |7 p6 P4 V/ S: `5 F4 ^' G. c4 L - foreach (DataRow Practice_row in PracticeManagementBL.GetPracticeIDListByExperimentID(int.Parse(Experiment_row["experimentID"].ToString())).Rows)
% T5 {" e4 a1 W - {
' {& A* H E! F9 B8 L1 {6 S* c C - treeNode.ChildNodes[i].ChildNodes[n].ChildNodes.Add(new TreeNode(Practice_row[1].ToString()));4 ^4 |, Q$ S7 k5 q. L
- }9 _& x/ h. f6 B7 ~# ?
- n++;
4 _. X2 F2 K8 |3 c - }: o- W8 S% C- Q* f- P. [4 o8 N9 D
- i++;+ @: l2 P5 N% {8 d& Y ~* W
- @ b. ?2 Q2 z7 ~2 N3 L( [
- }. y2 ]4 M t3 Q7 [- b5 |+ i' Z4 e0 a
- return treeNode;6 p: f; `3 o) Q) S% [9 K8 b
- }2 w" M0 J% r$ ^
复制代码 step2:将节点内容添加到TreeView中) `! J: r2 T% b7 r
也就是在这一步发现了TreeView中一个比较奇怪的东西,每将treeNode中一个节点Add到treeView中时,会自动地将treeNode的被添加的这个节点删掉(为什么为什么为什么???),这样就不能用foreach了,因为foreach只能读只读的数据0 }$ ~0 q2 n: O" f* c( {7 T D
' i: H! c: C, b9 m2 B& c2 R
那就直接Add整个treeNode吧(asp.net这个倒是挺自动化的),代码简单:! f, t1 p; F w' z
TreeNode tn = this.GetTreeNode();
0 d4 P9 @# s, A! Z) {& Y3 cthis.tvCourseMenu.Nodes.Add(tn); 2 Y4 d! h2 b9 r
问题也有,我用GetTreeNode函数返回的是一个TreeNode,是一个,所以生成的目录最上级是一个空的根目录(我在做数据绑定的时候没有绑定根目录的值啦,当然如果绑定了也可以没有下面的step3了),我想去掉这个,肯定不能Remove啦,因为Remove根目录,整个的都没啦。) w0 l1 b9 p/ B+ a( [
step3:/ ]9 D! ]$ _# V! J; p4 d6 p
用循环绑定根目录的子目录
1 v, x' \" N& {1 e/ ~7 ~3 D【不能这样】6 F2 ]! i6 a6 K+ } w. H- Q. T
for (int i = 0; i < tn.ChildNodes.Count;)
1 u$ c1 n+ h& u0 ~6 U% \ {( U0 K1 Q& @/ m
this.tvCourseMenu.Nodes.Add(tn.ChildNodes);
3 W8 ]* V0 P( `' c+ W2 s9 { }
; M$ i$ i! J W V7 U+ I! |【只能这样】, }+ [ L5 ^ p4 m
while (tn.ChildNodes.Count != 0)
4 g, ~# x! u) E7 _" b# {. r { U! n9 {* b: @: L% _
this.tvCourseMenu.Nodes.Add(tn.ChildNodes[0]);8 _1 ]* ^# ^/ r8 V
}
8 w4 r: a' H5 t+ Y+ [" z& S1 L【理由】上面说了已经
2 b8 f7 R# g6 E: L
6 l/ z, `9 h1 X终于弄好了,在做这个遇到step2中的问题的时候去请教了一个实验室的师兄,结果直接说,“我基本不用服务器控件的”,巨囧啊~~看来微软的这种控件还是有一些优化空间的啊,难怪不断地有VS05、08、10 |