功能:
单击行弹出当前行详细页面 双击行进入编辑状态(GridView/DataGrid内置 Edit)
说明:
单击事件(onclick)使用了 setTimeout 延迟,根据实际需要修改延迟时间 常见处理行方式会选择在 RowDataBound/ItemDataBound 中处理,这里我选择 Page.Render 中处理,至少基于以下考虑 RowDataBound 仅仅在调用 DataBind 之后才会触发,回发通过 ViewState 创建空件不触发 假如需要更多的处理,你需要分开部分逻辑到 RowCreated 等事件中 并且我们希望使用 ClientScript.GetPostBackEventReference 和 ClientScript.RegisterForEventValidation 方法 进行安全脚本的注册,而后者需要在页的 Render 阶段中才能处理 关于“DataGrid中采取的辅助按钮支持回发”见
ASP.NET DEMO8: 为 GridView 每行添加服务器事件 PS:未实现 Edit 对应的 Update/Cancel ,根据需要自行添加即可。
原始需求:既有单击又有双击的GridView是否存在(问了许多人都说不能,郁闷)
可直接运行源码(单页 .aspx):
<%
@ Page Language
=
"
C#
"
%>
<%
@ Import Namespace
=
"
System.Data
"
%>

<%--
http:
//
community.youkuaiyun.com/Expert/TopicView3.asp?id=5767096--%>
<!
DOCTYPE html PUBLIC
"
-//W3C//DTD XHTML 1.0 Transitional//EN
"
"
http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd
"
>

<
script runat
=
"
server
"
>

protected
void
Page_Load(
object
sender, EventArgs e)

{

if (!IsPostBack)
{
LoadGridViewProductData();
LoadDataGridProductData();
}
}

protected
void
GridView1_RowDataBound(
object
sender, GridViewRowEventArgs e)

{

/**//*
当然可以在这里进行客户端脚本绑定,
但是,我选择在重载页的 Render 方法中处理,因为
1. RowDataBound 仅仅在调用 DataBind 之后才会触发,回发通过 ViewState 创建空件不触发
假如需要更多的处理,你需要分开部分逻辑到 RowCreated 等事件中
2. 并且我们希望使用
ClientScript.GetPostBackEventReference 和 ClientScript.RegisterForEventValidation 方法
进行安全脚本的注册,而后者需要在页的 Render 阶段中才能处理
*/
}

protected
void
DataGrid1_ItemDataBound(
object
sender, DataGridItemEventArgs e)

{
// 隐藏辅助按钮列
int cellIndex = 0;
e.Item.Cells[cellIndex].Attributes["style"] = "display:none";
}
void
LoadGridViewProductData()

{
DataTable dt = CreateSampleProductData();

GridView1.DataSource = dt;
GridView1.DataBind();
}

void
LoadDataGridProductData()

{
DataTable dt = CreateSampleProductData();

DataGrid1.DataSource = dt;
DataGrid1.DataBind();
}


sample data
#region sample data

static DataTable CreateSampleProductData()

{
DataTable tbl = new DataTable("Products");

tbl.Columns.Add("ProductID", typeof(int));
tbl.Columns.Add("ProductName", typeof(string));
tbl.Columns.Add("UnitPrice", typeof(decimal));
tbl.Columns.Add("CategoryID", typeof(int));

tbl.Rows.Add(1, "Chai", 18, 1);
tbl.Rows.Add(2, "Chang", 19, 1);
tbl.Rows.Add(3, "Aniseed Syrup", 10, 2);
tbl.Rows.Add(4, "Chef Anton's Cajun Seasoning", 22, 2);
tbl.Rows.Add(5, "Chef Anton's Gumbo Mix", 21.35, 2);
tbl.Rows.Add(47, "Zaanse koeken", 9.5, 3);
tbl.Rows.Add(48, "Chocolade", 12.75, 3);
tbl.Rows.Add(49, "Maxilaku", 20, 3);

return tbl;
}

#endregion
protected
void
GridView1_RowEditing(
object
sender, GridViewEditEventArgs e)

{
GridView1.EditIndex = e.NewEditIndex;
LoadGridViewProductData();
}

protected
void
DataGrid1_EditCommand(
object
source, DataGridCommandEventArgs e)

{
DataGrid1.EditItemIndex = e.Item.ItemIndex;
LoadDataGridProductData();
}

protected
override
void
Render(HtmlTextWriter writer)

{
// GridView

foreach (GridViewRow row in GridView1.Rows)
{

if (row.RowState == DataControlRowState.Edit)
{ // 编辑状态
row.Attributes.Remove("onclick");
row.Attributes.Remove("ondblclick");
row.Attributes.Remove("style");
row.Attributes["title"] = "编辑行";
continue;
}

if (row.RowType == DataControlRowType.DataRow)
{
//单击事件,为了响应双击事件,延迟 1 s,根据需要可能需要增加延迟
row.Attributes["onclick"] = String.Format("javascript:setTimeout(\"window.open('DummyProductDetail.aspx?productid={0}')\", 1000*1);event.cancelBubble=true;", GridView1.DataKeys[row.RowIndex].Value.ToString());
// 获取ASP.NET内置回发脚本函数,返回 __doPostBack(<<EventTarget>>, <<EventArgument>>)
// 可直接硬编码写入脚本,不推荐
row.Attributes["ondblclick"] = ClientScript.GetPostBackEventReference(GridView1, "Edit$" + row.RowIndex.ToString(), true);
//
row.Attributes["style"] = "cursor:pointer";
row.Attributes["title"] = "单击打开详细页面、双击进入编辑";
}
}

// DataGrid

foreach (DataGridItem item in DataGrid1.Items)
{

if (item.ItemType == ListItemType.EditItem)
{
item.Attributes.Remove("onclick");
item.Attributes.Remove("ondblclick");
item.Attributes.Remove("style");
item.Attributes["title"] = "编辑行";
continue;
}

if (item.ItemType == ListItemType.Item || item.ItemType == ListItemType.AlternatingItem)
{
//单击事件,为了响应双击事件,延迟 1 s,根据需要可能需要增加延迟
item.Attributes["onclick"] = String.Format("javascript:setTimeout(\"window.open('DummyProductDetail.aspx?productid={0}')\", 1000*1);event.cancelBubble=true;", DataGrid1.DataKeys[item.ItemIndex].ToString());
// 双击
// 获取辅助的支持回发按钮
// 相对而言, GridView 支持直接将 CommandName 作为 <<EventArgument>> 故不需要辅助按钮
Button btnHiddenPostButton = item.FindControl("btnHiddenPostButton") as Button;
// 获取ASP.NET内置回发脚本函数,返回 __doPostBack(<<EventTarget>>, <<EventArgument>>)
// 可直接硬编码写入脚本,不推荐
item.Attributes["ondblclick"] = ClientScript.GetPostBackEventReference(btnHiddenPostButton, "");
//
item.Attributes["style"] = "cursor:pointer";
item.Attributes["title"] = "单击打开详细页面、双击进入编辑";
}
}

base.Render(writer);
}
</
script
>

<
html xmlns
=
"
http://www.w3.org/1999/xhtml
"
>
<
head id
=
"
Head1
"
runat
=
"
server
"
>
<
title
>
ASP.NET DEMO15: GridView 行单击与双击事件
</
title
>
</
head
>
<
body
>
<
form id
=
"
form1
"
runat
=
"
server
"
>
<
div
>
<
h3
>
功能:
</
h3
>
<
li
>
单击弹出当前详细页面
</
li
>
<
li
>
双击进入编辑状态(GridView
/
DataGrid内置 Edit)
</
li
>
<
h3
>
说明:
</
h3
>
<
li
>
单击事件(onclick)使用了 setTimeout 延迟,根据实际需要修改延迟时间
</
li
>
<
li
>
常见处理行方式会选择在 RowDataBound
/
ItemDataBound 中处理,这里我选择 Page.Render 中处理,至少基于以下考虑
<
li style
=
"
padding-left:20px; list-style-type:square
"
>
RowDataBound 仅仅在调用 DataBind 之后才会触发,回发通过 ViewState 创建空件不触发
假如需要更多的处理,你需要分开部分逻辑到 RowCreated 等事件中
</
li
>
<
li style
=
"
padding-left:20px; list-style-type:square
"
>
并且我们希望使用
ClientScript.GetPostBackEventReference 和 ClientScript.RegisterForEventValidation 方法
进行安全脚本的注册,而后者需要在页的 Render 阶段中才能处理
</
li
>
</
li
>
<
li
>
关于“DataGrid中采取的辅助按钮支持回发”见
<
a href
=
"
http://www.cnblogs.com/Jinglecat/archive/2007/07/15/818394.html
"
>
ASP.NET DEMO8: 为 GridView 每行添加服务器事件
</
a
>
<
br
/>
<
input type
=
"
button
"
id
=
"
Button1
"
value
=
"
Rebind
"
onclick
=
"
location.href=location.href;
"
/>
<
div style
=
"
float:left
"
>
<
h3
>
GridView Version
</
h3
>
<
asp:GridView ID
=
"
GridView1
"
DataKeyNames
=
"
ProductID
"
runat
=
"
server
"
AutoGenerateColumns
=
"
False
"
OnRowEditing
=
"
GridView1_RowEditing
"
OnRowDataBound
=
"
GridView1_RowDataBound
"
>
<
Columns
>
<
asp:TemplateField HeaderText
=
"
ProductName
"
>
<
ItemTemplate
>
<%
# Eval(
"
ProductName
"
)
%>
</
ItemTemplate
>
<
EditItemTemplate
>
<
asp:TextBox ID
=
"
txtProductName
"
runat
=
"
server
"
Text
=
'
<%# Bind("ProductName") %>
'
/>
</
EditItemTemplate
>
</
asp:TemplateField
>
<
asp:BoundField DataField
=
"
UnitPrice
"
HeaderText
=
"
UnitPrice
"
/>
</
Columns
>
</
asp:GridView
></
div
>
<
div style
=
"
float:left;padding-left:100px;
"
>
<
h3
>
DataGrid Version
</
h3
>
<
asp:DataGrid ID
=
"
DataGrid1
"
DataKeyField
=
"
ProductID
"
runat
=
"
server
"
AutoGenerateColumns
=
"
False
"
OnEditCommand
=
"
DataGrid1_EditCommand
"
OnItemDataBound
=
"
DataGrid1_ItemDataBound
"
>
<
Columns
>
<
asp:TemplateColumn
>
<
ItemTemplate
>
<
asp:Button ID
=
"
btnHiddenPostButton
"
CommandName
=
"
Edit
"
runat
=
"
server
"
Text
=
"
HiddenPostButton
"
style
=
"
display:none
"
/>
</
ItemTemplate
>
</
asp:TemplateColumn
>
<
asp:BoundColumn DataField
=
"
ProductName
"
HeaderText
=
"
ProductName
"
/>
<
asp:BoundColumn DataField
=
"
UnitPrice
"
HeaderText
=
"
UnitPrice
"
/>
</
Columns
>
</
asp:DataGrid
></
div
>
</
li
>
</
div
>
</
form
>
</
body
>
</
html
>
效果:

下载
PS:未实现 Edit 对应的 Update/Cancel ,根据需要自行添加即可。