07年时的笔记:TreeView读取数据库里的数据:http://www.nnllok.cn/myBlog/archives/2007/3551.html
今天主要是想搞winform,winform下,TreeView有好多不同,没有了FindNode方法,一些属性也不同了
在连接数据库的时候,也有不同,webform下用的是web.config,winform下是app.config,在读取app.config里设置的连接字符串时,要先在资源管理器里添加引用System.configuration
数据结构方面,因为webform里,TreeView有自带的FindNode方法和PathSeparator属性,所以使用父级路径ParentPath字段比较快,就是,在winform里,FindNode方法和PathSeparator属性都没有,所以使用父级编号ParentID字段比较好,因为对数据库来说,记录路径的字段最大是varchar(8000),无限级分类也会变成有限级分类,还有就是记录一个字符串,比记录一个int型数据占空间,检索也慢
测试环境:VS.NET 2008 + MS SQL 2000
先记录我的表结构:
CREATE TABLE [A_Class] (
[ClassID] [int] IDENTITY (1, 1) NOT NULL ,
[ClassName] [varchar] (50) COLLATE Chinese_PRC_CI_AS NOT NULL ,
[ParentID] [int] NOT NULL ,
[ParentPath] [varchar] (200) COLLATE Chinese_PRC_CI_AS NOT NULL ,
[ClassLayer] [int] NOT NULL ,
[ClassOrder] [int] NOT NULL ,
CONSTRAINT [PK_A_Class] PRIMARY KEY CLUSTERED
(
[ClassID]
) ON [PRIMARY]
) ON [PRIMARY]
GO
数据:

不写文字,用代码说话好了,代码最好说话用的
ASP.NET下:
aspx文件:
<asp:TreeView ID="TreeView1" runat="server" PathSeparator="," ShowLines="True"></asp:TreeView>
aspx.cs文件:
protected void Page_Load(object sender, EventArgs e)
{
ReadModule();
}
#region 读取数据到TreeView
/// <summary>
/// 读取数据到TreeView
/// </summary>
public void ReadModule()
{
//清空所有节点
TreeView1.Nodes.Clear();
using (SqlConnection connect = new SqlConnection())
{
//连接字段串和命令
string connectionString, commandText, path = null;
connectionString = ConfigurationManager.ConnectionStrings["TestConnectionString"].ConnectionString;
commandText = "select ClassID, ClassName, ParentPath, ClassLayer, ClassOrder from A_Class order by ParentPath + convert(varchar(10), ClassID)";
//连接数据库
connect.ConnectionString = connectionString;
connect.Open();
using (SqlCommand command = new SqlCommand(commandText, connect))
{
using (SqlDataReader dbReader = command.ExecuteReader())
{
if (dbReader != null)
{
int myOrder = 0;
string nodeText = null, nodeValue = null;
TreeNode tn;
while (dbReader.Read())
{
path = dbReader["parentPath"].ToString().Remove(0, 2);
myOrder = Convert.ToInt32(dbReader["ClassOrder"]) - 1;
nodeText = dbReader["ClassName"].ToString();
nodeValue = dbReader["ClassID"].ToString();
if (path.Length == 0)
{
//添加根节点
InsertOneTreeNode(null, nodeText, nodeValue, myOrder);
}
else
{
//添加子节点,先查找父节点
path = path.Remove(path.Length - 1);
tn = TreeView1.FindNode(path);
//添加子节点
InsertOneTreeNode(tn, nodeText, nodeValue, myOrder);
}
}
}
dbReader.Close();
}
}
connect.Close();
}
//节点排序
}
#endregion
#region 插入一个节点
/// <summary>
/// 插入一个节点
/// </summary>
/// <param name="parentNode">父节点,如果插入根节点,传入null</param>
/// <param name="nodeText">节点描述</param>
/// <param name="nodeValue">节点值</param>
/// <param name="toolTipOrder">节点的排序号,借用ToolTip记录</param>
private void InsertOneTreeNode(TreeNode parentNode, string nodeText, string nodeValue, int toolTipOrder)
{
//插入到父节点集中
TreeNodeCollection tncs;
if (parentNode == null)
{
tncs = TreeView1.Nodes;
}
else
{
tncs = parentNode.ChildNodes;
}
//要插入的节点
TreeNode tnc = new TreeNode(nodeText, nodeValue);
tnc.ToolTip = toolTipOrder.ToString();
tnc.SelectAction = TreeNodeSelectAction.None;
//添加子节点,默认插在第一个节点,如果已经有子节点存在,检查每一个子节点,把新的节点插入到value值小于当前value值的最大节点后面
int insertIndex = 0, tnCount;
tnCount = tncs.Count;
if (tnCount > 0)
{
for (int index = 0; index < tnCount; index++)
{
if (Convert.ToInt32(tncs[index].ToolTip) < toolTipOrder)
{
insertIndex = index + 1; //插入在这个节点的后面
}
else
{
break;
}
}
}
//插入节点
tncs.AddAt(insertIndex, tnc);
}
#endregion
winform下差不多,就是要自己写FindNode方法,我用的是遍历的方法
#region 读取数据到TreeView
/// <summary>
/// 读取数据到TreeView
/// </summary>
public void ReadModule()
{
//清空所有节点
TreeView1.Nodes.Clear();
using (SqlConnection connect = new SqlConnection())
{
//连接字段串和命令
string connectionString, commandText, parentID = null;
connectionString = System.Configuration.ConfigurationManager.ConnectionStrings["Sale.Properties.Settings.SaleNnllTestConnectionString"].ConnectionString;
commandText = "select ClassID, ClassName, ParentID, ClassLayer, ClassOrder from A_Class order by ParentPath + convert(varchar(10), ClassID)";
//连接数据库
connect.ConnectionString = connectionString;
connect.Open();
using (SqlCommand command = new SqlCommand(commandText, connect))
{
using (SqlDataReader dbReader = command.ExecuteReader())
{
if (dbReader != null)
{
int myOrder = 0, nodeLevel;
string nodeText = null, nodeValue = null;
TreeNode tn;
while (dbReader.Read())
{
parentID = dbReader["ParentID"].ToString();
myOrder = Convert.ToInt32(dbReader["ClassOrder"]) - 1;
nodeText = dbReader["ClassName"].ToString();
nodeValue = dbReader["ClassID"].ToString();
nodeLevel = Convert.ToInt32(dbReader["ClassLayer"]);
if (parentID.Equals("0"))
{
//添加根节点
InsertOneTreeNode(null, nodeText, nodeValue, nodeLevel, myOrder);
}
else
{
//添加子节点,先查找父节点
tn = null;
FindNode(TreeView1.Nodes, parentID, ref tn);
//添加子节点
InsertOneTreeNode(tn, nodeText, nodeValue, nodeLevel, myOrder);
}
}
}
dbReader.Close();
}
}
connect.Close();
}
//节点排序
}
#endregion
#region 在一组TreeNode中寻找一个节点
/// <summary>
/// 在TreeView中寻找一个节点
/// </summary>
/// <param name="tncs">一组节点</param>
/// <param name="nodeTag">节点的Tag值</param>
/// <returns></returns>
private void FindNode(TreeNodeCollection tncs, string nodeTag, ref TreeNode tn)
{
if (tn != null) return;
foreach (TreeNode tnc in tncs)
{
TextBox1.Text += "\r\n" + tnc.Text + "," + tnc.Tag;
if (tnc.Tag.Equals(nodeTag))
{
tn = tnc;
break;
}
else if (tnc.GetNodeCount(false) > 0)
{
FindNode(tnc.Nodes, nodeTag, ref tn);
}
}
}
#endregion
#region 插入一个节点
/// <summary>
/// 插入一个节点
/// </summary>
/// <param name="parentNode">父节点,如果插入根节点,传入null</param>
/// <param name="nodeText">节点描述</param>
/// <param name="nodeValue">节点值</param>
/// <param name="toolTipOrder">节点的排序号,借用ToolTip记录</param>
private void InsertOneTreeNode(TreeNode parentNode, string nodeText, string nodeValue, int nodeLevel, int toolTipOrder)
{
//插入到父节点集中
TreeNodeCollection tncs;
if (parentNode == null)
{
tncs = TreeView1.Nodes;
}
else
{
tncs = parentNode.Nodes;
}
//要插入的节点
TreeNode tnc = new TreeNode(nodeText);
tnc.Tag = nodeValue;
//tnc.Level = nodeLevel;
tnc.ToolTipText = toolTipOrder.ToString();
//添加子节点,默认插在第一个节点,如果已经有子节点存在,检查每一个子节点,把新的节点插入到value值小于当前value值的最大节点后面
int insertIndex = 0, tnCount;
tnCount = tncs.Count;
if (tnCount > 0)
{
for (int index = 0; index < tnCount; index++)
{
if (Convert.ToInt32(tncs[index].ToolTipText) < toolTipOrder)
{
insertIndex = index + 1; //插入在这个节点的后面
}
else
{
break;
}
}
}
//插入节点
tncs.Insert(insertIndex, tnc);
}
#endregion