可快速绑定到关系表或单表的树
|
下面這篇文章是關於.net編程的,個人認為實現方法有點過於繁瑣了(我沒有研究
過.net 2003,如有有謬誤之處請見諒),其實在VS C# 2005中,很多部分直接在IDE下 就可直接設置,而不用手工編寫代碼,真正的節省時間,實現快速開發。 |
|
using System; using System.Collections; using System.ComponentModel; using System.Drawing; using System.Data; using System.Windows.Forms; using System.Diagnostics; namespace upControls { /// <summary> /// 可快速绑定到关系表或单表的树,树自动按照主表及其子表的PrimaryKey列值来绑定 /// 只遍历一次Rows中的所有行,所以加载速度非常快 /// 结点内容可以只显示值,也可以显示列名称以作说明 /// 关系型的数据源要求具有:子列必需具唯一约束 /// 附加列必需是关系表中的最底层表所拥有的列 /// 适用于ParentID,ID,Text式之外的所有表的树填充 /// </summary> public class DataTreeView : TreeView { private System.ComponentModel.Container components = null; private DataTable _mainDatatable; private string[] _appendColumnNames=null; private System.Windows.Forms.ContextMenu cntMenu; private bool _columnNameOnText; private TreeNode _parentNode; public DataTreeView () { InitializeComponent(); MenuItem mnu; mnu=cntMenu.MenuItems.Add ("显示列名"); mnu.Click +=new EventHandler(mnu_Click); mnu=cntMenu.MenuItems.Add ("-"); mnu=cntMenu.MenuItems.Add ("展开"); mnu.Click +=new EventHandler(mnu_Click); mnu=cntMenu.MenuItems.Add ("折叠"); mnu.Click +=new EventHandler(mnu_Click); mnu=cntMenu.MenuItems.Add ("-"); mnu=cntMenu.MenuItems.Add ("全部展开"); mnu.Click +=new EventHandler(mnu_Click); mnu=cntMenu.MenuItems.Add ("全部折叠"); mnu.Click +=new EventHandler(mnu_Click); } /// <summary> /// 清理所有正在使用的资源。 /// </summary> protected override void Dispose( bool disposing ) { if( disposing ) { if(components != null) { components.Dispose(); } } base.Dispose( disposing ); } #region 组件设计器生成的代码 /// <summary> /// 设计器支持所需的方法 - 不要使用代码编辑器 /// 修改此方法的内容。 /// </summary> private void InitializeComponent() { this.cntMenu = new System.Windows.Forms.ContextMenu(); this.cntMenu.Popup += new System.EventHandler(this.cntMenu_Popup); this.CheckBoxes = true; this.ContextMenu = this.cntMenu; } #endregion /////////////////////////////////////////////////////////////////////////////// /// <summary> /// 主表,主表的第一个primarykey值将添加在树的顶层 /// </summary> public DataTable MainTable { get{return this._mainDatatable ; } } /// <summary> /// 除primarykey列之外的列,可以附加在最后一个primarykey列的结点之下的列 /// </summary> public string[] AppendColumnNames { get{return _appendColumnNames ; } } /// <summary> /// 结点的文本要否包含列名 /// </summary> public bool ColumnNameOnText { get{return _columnNameOnText ; } } /// <summary> /// 填充一个表及其子表到树,结点显示的数据是每一个键列的内容 /// </summary> /// <param name="dataTable">要填充到树的表</param> /// <param name="parentNode">要填充到哪一个现有的结点之下</param> /// <param name="appendColumnnames">附加列(非键列),格式是:表名.列名,或只有列名</param> /// <param name="ColumnnameOnText">列名要不要显示在结点的文本之中</param> /// <param name="clearNodes">要不要清除现存的结点再填充</param> public void Fill ( DataTable dataTable,TreeNode parentNode, string[] appendColumnnames,bool ColumnnameOnText,bool clearNodes) { _mainDatatable =dataTable; _appendColumnNames=appendColumnnames; _columnNameOnText=ColumnnameOnText; _parentNode=parentNode; TryBinding(clearNodes); } /// <summary> /// 尝试填充树,如果各个必需属性都设置好了 /// </summary> /// <param name="clearNodes"></param> public void TryBinding(bool clearNodes) { if (clearNodes) { this.Nodes.Clear() ; TryBinding(_mainDatatable,null,_appendColumnNames); } else TryBinding(_mainDatatable,_parentNode,_appendColumnNames); } private void TryBinding(DataTable dataTable,TreeNode parentNode, string[] appendColumnNames) { if (dataTable==null) return ; //先加入主表名结点 if (parentNode!=null) parentNode=parentNode.Nodes.Add (dataTable.TableName ); else parentNode=this.Nodes.Add (dataTable.TableName ); //返回包含了一个表中所有键列的数组,但是如果表是子表的话,则作为关系的键列不包含在内
DataColumn[] PrimaryKey=AddThesePrimaryKey(dataTable); TreeNode[] priNodes=new TreeNode[PrimaryKey.Length ]; |

浙公网安备 33010602011771号