今天打算用Asp.Net复合控件技术制作一个服务器端的文件管理控件,基本实现构想如下:
- 设置一个属性,通过该属性指定此控件所管理的根目录路径
- 递归向下扫描指定的根目录下的所有子目录及文件,用TreeView控件将其显示出来
- 使TreeView显示复选框,用以勾选待处理文件,然后做进一步处理(复制、移动、删除)
- 在TreeView中单击某项后,可以对其进行重命名操作,也可以指示将勾选的文件复制、移动到所选目录中
TreeView基本效果如下图:
在页面上直接堆控件进行了一番测试,基本没有问题,于是就开始着手创建复合控件了,然而却遭遇连番郁闷……
RenderContents()的尴尬
首先我老老实实的在CreateChildControls()方法中书写了创建和添加TreeView控件的代码。
然后在RenderContents()方法中开始扫描目录结构、更新到TreeView控件中,然后输出控件,然而却出现了很奇怪的现象:
- 已在CreateChildControls()方法中设定了TreeView的ExpandDepth属性为1,也就是说TreeView应当在首次展示时展开一个层级,而实际是一层都没有展开;
- 手动展开根节点后,再继续展开其子节点就莫名其妙地又自动合上根节点了……;
- 单击任何一项的时候,会回发到服务器,然后就又回到初始状态了……;
对于第一个问题,我猜测是在CreateChildControls()方法到RenderContents()方法之间的某个生命阶段,TreeView控件可能已被视作进行了首次展示,所以这个属性便失效了。
第二个问题完全没有头绪,个人觉得不太符合科学道理,因为这完全是客户端的范畴,未涉及回发服务器,也就肯定不是代码写错了产生的问题吧,有谁有说得通的见解不妨讲给我。
第三个问题开始猜测是因为没有加“if(!Page.IsPostback)”判定,致使在每次加载页面时都重新刷新一遍TreeView控件,导致总回到初始状态,于是我尝试加入了IsPostback判定,结果再测试时发现回发后TreeView(里的所有节点)彻底消失……
OnLoad()的尴尬
鉴于上述第一个问题,我决定把这部分主要功能的代码前移到OnLoad()方法中,结果发现在这时候控件还没初始化(CreateChildControls()方法还未执行)……
CreateChildControls()的尴尬
我想干脆把主要功能代码直接写在CreateChildControls()方法里得了,让它在构造时就直接读取文件系统结构来更新TreeView,其结果是:
- 显示的根目录不是我在代码中为控件属性指定的目录,而是网页所在的目录;
- 点击一下触发回发之后,仍然是一切消失……
对于第一个问题,经过断点调试闹明白了,原来在CreateChildControls()方法执行的时候获取的根目录属性值还是空的,也就是说我在控件的HTML代码中赋予此控件的属性值都还未加载。
第二个问题,乃是“if(!Page.IsPostback)”所致,去掉之后就正常了,视图状态在回发时也能完好保存了,而且也没有之前遇到的展开子节点时自动关闭根节点的灵异事件了。
但是第一个问题仍然是很头疼的,这说明在CreateChildControls()中执行主要功能代码还是太早了,该在哪个阶段执行呢?
PS:另外,由于CreateChildControls()方法的执行时间是不确定的,所以很不稳定,官方也不建议在这里书写重要的功能代码。
OnPreRender()的尴尬
尝试把主要功能代码转到RenderContents()方法之前的OnPreRender()阶段执行,遇到的问题是视图状态无法保存,回发时回到初始状态,而其他方面则一切正常,恼~
LoadViewState()的尴尬
既然问题出在视图状态这里,那么我们在重写LoadViewState()方法中的base.LoadViewState(savedState)代码之前执行主要功能不就OK了吗?
运行一看:什么都没有了……
后来才想起来,在首次加载的时候应当是不执行LoadViewState()方法的,LoadViewState()仅在页面回发时执行。
最终解决办法
这就比较明了了,就是在OnPreRender()中加入“if(!Page.IsPostback)”判定,然后执行主要功能代码,然后再在LoadViewState()中base.LoadViewState(savedState)代码之前再执行一次主要功能代码。
这样在首次加载页面时就是在OnPreRender()时段执行主要功能,而在回发页面时就会在LoadViewState()中执行主要功能,这样就同时解决了属性获取、首次展示、视图状态这三个问题。
实在是很尴尬的一系列生命阶段啊-_-#,这个解决办法也自觉有些山寨风,有高人知道能完美搞定上述问题的生命阶段么?
下载
转载请遵循此协议:署名 - 非商业用途 - 保持一致
并保留此链接:http://skyd.cnblogs.com/