删除ClerkList.aspx上面的所有控件,重头开始,按下面步骤先初始化控件:
拖入SqlDataSource控件,命名为dsDeptList
拖入DropDownList控件,命名为ddlDeptList
拖入SqlDataSource控件,命名为dsClerkListByDept
拖入GridViewt控件,命名为gvClerkListByDept
拖入SqlDataSource控件,命名为dsClerkDetail
拖入FormViewt控件,命名为fvClerkDetail
看控件的命名就应该知道各自负责什么功能了吧。
下面是设计模式的样式和前台源代码:
在设计界面什么都不要做,接下来编写相应的绑定代码,我们一步一步来,做一步看一下显示结果,前面的几步实现的效果跟以前做的绑定操作其实是一样的,只不过操作方式不一样,变成写后台代码了。
首先初始化部门列表数据源,并绑定到下拉框控件:
接着我们在page_load代码段中增加部门员工列表数据源和GridView控件的初始化和绑定,和上面不一样的是,数据源的select语句是带参的,而且参数是来源于部门下拉框中的值,利用拖放控件并设置数据源已经做过了,那么如何用代码来实现呢?
运行效果如下:
请选择部门:
员工列表:
现在市场部中无人员数据,我想实现返回记录为空的时候出现相应的提示信息,在代码中如何实现呢?
我觉得既然只要设置gridview的编辑模板EmptyDataTemplate就可以,为什么还要写代码?我又不太熟悉TemplateField的写法,为什么要去死钻牛角尖?
该省事的地方,该不需要花费精力的地方就不需要去研究如何写后台代码,用好ASP.NET2带给我们的便利就行了:
前台aspx代码中只多了三行:
运行结果很不错,要是想编写一个定义ItemTemplate的代码:
不过,我想在员工列表中增加一个编辑按钮,而这个按钮名字虽然叫编辑,其实是选定,而且选定的操作是将详细信息FormView刷新。
突然发现我formview的template代码不会写,算了 还是先改用detailsview控件吧。再把员工弄熟了再看看能不能找到后台写formview的代码。
还有我想如果还没有选择一个员工就不出现员工详细信息的部分,所以我把页面中增加一个panel叫ClerkDetailPanel,将ClerkDetail的两个控件放进去。
员工详细信息的控件代码如下,代码中有一段为灰色的是因为接下来这一段要被移到子程序UpdateClerkDetail中去:
为了给员工列表GridView增加一个选择按钮,我们使用前台编辑列的方式增加一个选择按钮并且增加OnSelectedIndexChanged的事件代码如下:
更新员工详细信息的程序如下,其实就是执行了一下数据绑定:
不得不提的是,在改变部门后,由于员工列表的SelectIndex并未改变,所以不会触发员工详细信息的更新,这是一个bug,解决代码如下:
执行结果还是比较满意的:
请选择部门:
员工列表:
首先,DetailsView的字段和GridView是一样的7种类型:BoundedField,ButtonField,CommandField,CheckBoxField,HyperLinkField,ImageField,TemplateField,不过前台的语法声明有点不同,字段DetailsView是用<Fields>,而GridView是Columns。
其实上面实现的后台代码方式还不是正宗ADO.NET方式,我觉得用SqlDataAdapter执行conn+SQLCommand_String 然后再Fill给DataSet,这样DataSet将被填充数据表以及之间的关系,再将DataSet中的对应DataTable赋给某个控件,如gridview,detailsview等。 才是ADO.NET的写法。这样可以把离线的DataSet放到session中,从而通过控件的RowFilter属性可以让不同控件操作显示同一个DataView,速度快,省资源。有必要才需要连接数据库更新DataView或者更新数据库。
拖入SqlDataSource控件,命名为dsDeptList
拖入DropDownList控件,命名为ddlDeptList
拖入SqlDataSource控件,命名为dsClerkListByDept
拖入GridViewt控件,命名为gvClerkListByDept
拖入SqlDataSource控件,命名为dsClerkDetail
拖入FormViewt控件,命名为fvClerkDetail
看控件的命名就应该知道各自负责什么功能了吧。
下面是设计模式的样式和前台源代码:
<form id="form1" runat="server">
<strong>请选择部门:</strong><asp:SqlDataSource ID="dsDeptList" runat="server"></asp:SqlDataSource>
<asp:DropDownList ID="ddlDeptList" runat="server">
</asp:DropDownList><br />
<br />
<strong>员工列表:</strong><br />
<asp:SqlDataSource ID="dsClerkListByDept" runat="server"></asp:SqlDataSource>
<asp:GridView ID="gvClerkListByDept" runat="server">
</asp:GridView>
<br />
<strong>员工详细信息:</strong><br />
<asp:SqlDataSource ID="dsClerkDetail" runat="server"></asp:SqlDataSource>
<asp:FormView ID="fvClerkDetail" runat="server">
</asp:FormView>
</form>
够简洁吧,由于没有绑定数据源,也就没有缺省的那些自动生成的绑定字段了。<strong>请选择部门:</strong><asp:SqlDataSource ID="dsDeptList" runat="server"></asp:SqlDataSource>
<asp:DropDownList ID="ddlDeptList" runat="server">
</asp:DropDownList><br />
<br />
<strong>员工列表:</strong><br />
<asp:SqlDataSource ID="dsClerkListByDept" runat="server"></asp:SqlDataSource>
<asp:GridView ID="gvClerkListByDept" runat="server">
</asp:GridView>
<br />
<strong>员工详细信息:</strong><br />
<asp:SqlDataSource ID="dsClerkDetail" runat="server"></asp:SqlDataSource>
<asp:FormView ID="fvClerkDetail" runat="server">
</asp:FormView>
</form>
在设计界面什么都不要做,接下来编写相应的绑定代码,我们一步一步来,做一步看一下显示结果,前面的几步实现的效果跟以前做的绑定操作其实是一样的,只不过操作方式不一样,变成写后台代码了。
首先初始化部门列表数据源,并绑定到下拉框控件:
protected void Page_Load(object sender, EventArgs e)
{
//初始化部门数据源的连接字串和select命令
dsDeptList.ConnectionString = WebConfigurationManager.ConnectionStrings["CAROAConnectionString"].ConnectionString;
dsDeptList.SelectCommand = "select Code_Dept.DeptID,Code_Dept.DeptName from Code_Dept";
//部门列表下拉框绑定数据源
ddlDeptList.AutoPostBack = true;
if (!IsPostBack)
{
ddlDeptList.DataSourceID = dsDeptList.ID.ToString();
ddlDeptList.DataTextField = "DeptName";
ddlDeptList.DataValueField = "DeptID";
ddlDeptList.DataBind();
}
}
在这里,我们将下拉框设成了自动提交到服务器,同时设置了页面第一次访问才绑定数据源,而不是每次执行都绑定,这样就避免了下拉框中数据每次都会被重置。效果很好。{
//初始化部门数据源的连接字串和select命令
dsDeptList.ConnectionString = WebConfigurationManager.ConnectionStrings["CAROAConnectionString"].ConnectionString;
dsDeptList.SelectCommand = "select Code_Dept.DeptID,Code_Dept.DeptName from Code_Dept";
//部门列表下拉框绑定数据源
ddlDeptList.AutoPostBack = true;
if (!IsPostBack)
{
ddlDeptList.DataSourceID = dsDeptList.ID.ToString();
ddlDeptList.DataTextField = "DeptName";
ddlDeptList.DataValueField = "DeptID";
ddlDeptList.DataBind();
}
}
接着我们在page_load代码段中增加部门员工列表数据源和GridView控件的初始化和绑定,和上面不一样的是,数据源的select语句是带参的,而且参数是来源于部门下拉框中的值,利用拖放控件并设置数据源已经做过了,那么如何用代码来实现呢?
//初始化员工列表数据源
dsClerkListByDept.ConnectionString = WebConfigurationManager.ConnectionStrings["CAROAConnectionString"].ConnectionString;
dsClerkListByDept.SelectCommand = "select ClerkID,RealName,JobNum from Clerk where Clerk.DeptID=@paraDeptID";
if (!IsPostBack)
{
//这一行是指定参数@paraDeptID的来源是ControlParameter对象的一个实例
dsClerkListByDept.SelectParameters.Add(new ControlParameter("paraDeptID", "ddlDeptList", "SelectedValue"));
}
setgvClerkListByDeptField();
//员工列表绑定数据源
gvClerkListByDept.DataSourceID = dsClerkListByDept.ID.ToString();
gvClerkListByDept.DataBind();
dsClerkListByDept.ConnectionString = WebConfigurationManager.ConnectionStrings["CAROAConnectionString"].ConnectionString;
dsClerkListByDept.SelectCommand = "select ClerkID,RealName,JobNum from Clerk where Clerk.DeptID=@paraDeptID";
if (!IsPostBack)
{
//这一行是指定参数@paraDeptID的来源是ControlParameter对象的一个实例
dsClerkListByDept.SelectParameters.Add(new ControlParameter("paraDeptID", "ddlDeptList", "SelectedValue"));
}
setgvClerkListByDeptField();
//员工列表绑定数据源
gvClerkListByDept.DataSourceID = dsClerkListByDept.ID.ToString();
gvClerkListByDept.DataBind();
运行效果如下:
请选择部门:
员工列表:
ClerkID | RealName | JobNum |
---|---|---|
3 | 张大客 | 3001 |
4 | 李大客 | 3002 |
现在市场部中无人员数据,我想实现返回记录为空的时候出现相应的提示信息,在代码中如何实现呢?
我觉得既然只要设置gridview的编辑模板EmptyDataTemplate就可以,为什么还要写代码?我又不太熟悉TemplateField的写法,为什么要去死钻牛角尖?
该省事的地方,该不需要花费精力的地方就不需要去研究如何写后台代码,用好ASP.NET2带给我们的便利就行了:
前台aspx代码中只多了三行:
<asp:GridView ID="gvClerkListByDept" runat="server">
<EmptyDataTemplate>
抱歉,该部门无返员工记录!
</EmptyDataTemplate>
</asp:GridView>
<EmptyDataTemplate>
抱歉,该部门无返员工记录!
</EmptyDataTemplate>
</asp:GridView>
运行结果很不错,要是想编写一个定义ItemTemplate的代码:
private void setgvClerkListByDeptField()
{
TemplateField myDataField = new TemplateField();
myDataField .ItemTemplate = new GridViewTemplate(DataControlRowType.DataRow, "ClerkName");
gvClerkListByDept.Columns.Add(myDataField );
}
public class GridViewTemplate : ITemplate
{
private DataControlRowType templateType;
private string columnName;
public GridViewTemplate(DataControlRowType type, string colname)
{
templateType = type;
columnName = colname;
}
public void InstantiateIn(System.Web.UI.Control container)
{
if (templateType == DataControlRowType.DataRow)
{
//创建模板字段类型
//指定模板字段的数据绑定
switch (columnName)
{
case "":
break;
}
}
}
}
这么复杂,有必要吗?还有要是写一个自定义按钮字段或者其他什么字段的代码,倒还不如在设计窗口或者aspx文件的控件声明中直接去写呢。{
TemplateField myDataField = new TemplateField();
myDataField .ItemTemplate = new GridViewTemplate(DataControlRowType.DataRow, "ClerkName");
gvClerkListByDept.Columns.Add(myDataField );
}
public class GridViewTemplate : ITemplate
{
private DataControlRowType templateType;
private string columnName;
public GridViewTemplate(DataControlRowType type, string colname)
{
templateType = type;
columnName = colname;
}
public void InstantiateIn(System.Web.UI.Control container)
{
if (templateType == DataControlRowType.DataRow)
{
//创建模板字段类型
//指定模板字段的数据绑定
switch (columnName)
{
case "":
break;
}
}
}
}
不过,我想在员工列表中增加一个编辑按钮,而这个按钮名字虽然叫编辑,其实是选定,而且选定的操作是将详细信息FormView刷新。
突然发现我formview的template代码不会写,算了 还是先改用detailsview控件吧。再把员工弄熟了再看看能不能找到后台写formview的代码。
还有我想如果还没有选择一个员工就不出现员工详细信息的部分,所以我把页面中增加一个panel叫ClerkDetailPanel,将ClerkDetail的两个控件放进去。
员工详细信息的控件代码如下,代码中有一段为灰色的是因为接下来这一段要被移到子程序UpdateClerkDetail中去:
//初始化员工详细信息数据源
dsClerkDetail.ConnectionString = WebConfigurationManager.ConnectionStrings["CAROAConnectionString"].ConnectionString;
dsClerkDetail.SelectCommand = "select ClerkID,RealName,JobNum,DeptID from Clerk where Clerk.ClerkID=@paraClerkID";
if (!this.IsPostBack)
{
//这一行是指定参数@paraClerkID的来源是ControlParameter对象的一个实例
dsClerkDetail.SelectParameters.Add(new ControlParameter("paraClerkID", "gvClerkListByDept", "SelectedValue"));
}
dsClerkDetail.ConnectionString = WebConfigurationManager.ConnectionStrings["CAROAConnectionString"].ConnectionString;
dsClerkDetail.SelectCommand = "select ClerkID,RealName,JobNum,DeptID from Clerk where Clerk.ClerkID=@paraClerkID";
if (!this.IsPostBack)
{
//这一行是指定参数@paraClerkID的来源是ControlParameter对象的一个实例
dsClerkDetail.SelectParameters.Add(new ControlParameter("paraClerkID", "gvClerkListByDept", "SelectedValue"));
}
为了给员工列表GridView增加一个选择按钮,我们使用前台编辑列的方式增加一个选择按钮并且增加OnSelectedIndexChanged的事件代码如下:
protected void gvClerkListByDept_SelectedIndexChanged(object sender, EventArgs e)
{
ClerkDetailPanel.Visible = true;
UpdateClerkDetail();
}
{
ClerkDetailPanel.Visible = true;
UpdateClerkDetail();
}
更新员工详细信息的程序如下,其实就是执行了一下数据绑定:
private void UpdateClerkDetail()
{
dvClerkDetail.DataSourceID = dsClerkDetail.ID.ToString();
dvClerkDetail.DataBind();
}
{
dvClerkDetail.DataSourceID = dsClerkDetail.ID.ToString();
dvClerkDetail.DataBind();
}
不得不提的是,在改变部门后,由于员工列表的SelectIndex并未改变,所以不会触发员工详细信息的更新,这是一个bug,解决代码如下:
protected void ddlDeptList_SelectedIndexChanged(object sender, EventArgs e)
{
gvClerkListByDept.SelectedIndex = -1;
ClerkDetailPanel.Visible = false;
}
{
gvClerkListByDept.SelectedIndex = -1;
ClerkDetailPanel.Visible = false;
}
执行结果还是比较满意的:
请选择部门:
员工列表:
ClerkID | RealName | JobNum | |
---|---|---|---|
3 | 张大客 | 3001 | |
4 | 李大客 | 3002 | |
5 | Shao大客 | 3003 |
员工详细信息:
要给员工详细信息加上编辑,删除操作。就用到DetailsView的相关属性和事件。更详细的代码编写见下一篇。ClerkID | 4 |
RealName | 李大客 |
JobNum | 3002 |
DeptID | 3 |
首先,DetailsView的字段和GridView是一样的7种类型:BoundedField,ButtonField,CommandField,CheckBoxField,HyperLinkField,ImageField,TemplateField,不过前台的语法声明有点不同,字段DetailsView是用<Fields>,而GridView是Columns。
其实上面实现的后台代码方式还不是正宗ADO.NET方式,我觉得用SqlDataAdapter执行conn+SQLCommand_String 然后再Fill给DataSet,这样DataSet将被填充数据表以及之间的关系,再将DataSet中的对应DataTable赋给某个控件,如gridview,detailsview等。 才是ADO.NET的写法。这样可以把离线的DataSet放到session中,从而通过控件的RowFilter属性可以让不同控件操作显示同一个DataView,速度快,省资源。有必要才需要连接数据库更新DataView或者更新数据库。