Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > ASP .Net > Custom build DataGridColumn event problem

Reply
Thread Tools

Custom build DataGridColumn event problem

 
 
Girish
Guest
Posts: n/a
 
      07-18-2005
OK.. phew. Playing with data grids for the past few days has been fun and a
huge learning experience..

My problem. I have a requirement to display a gird with a gird. Within the
embedded grid, theres a requirement to show a drop down menu list (this is a
control I downloaded online) in one of the columns. For the purposes of this
question, Ive implemented the drop down menu as a drop down list instead.
Ive got all this working at this point. Heres my problem:

1) When a person selects an item in the drop down list, I need the server to
autopost back and fire an event which I can handle on the sever side.
2) On the server side, I need to be able to figure out which drop down list
the event was fired for and what the selected value is.

Ive implemented the display of the column showing the drop down list in a
custom built DataGridColumn. All the code is below.

My Question:

1) How do I setup ONE postback event handler for ALL the drop downlist
controls being rendered dynamically in the embedded grid?
2) The event handler must be in the code-behind code that uses the custom
built DataGridColumn and should not be in the DataGridColumn code itself.
2) How do I figure out in that one event handler method, the drop down list
that threw the event, and the value of the selected item.

If you look towards the end of the method
CustomerDataGrid_OnItemDataBound(object sender, DataGridItemEventArgs e),
you'll find the code where I programmatically attach the new column. The
custom col code itself is the last snippet of code in this email.

Appreciate anyones help.

Girish

----------------
ASPX CODE
---------------

<%@ Page language="c#" Inherits="MasterDetail.CustomerOrderDataGrid"
EnableViewState="False" CodeBehind="CustomerOrderDataGrid.aspx.cs"
AutoEventWireup="false" %>
<HTML>
<LINK REL=StyleSheet HREF="menu.css" TYPE="text/css" />

<body style="FONT: x-small Verdana, Arial, sans-serif">
<!-- Begin Web Form -->
<form id="CustomerOrderDataGrid" method="post" runat="server">
<p><a href="/DayOfDotNet/">Parent Directory</a></p>
<!-- Begin DataGrid -->
<aspataGrid id="CustomerDataGrid" runat="server"
AutoGenerateColumns="False" CellPadding="2"
CellSpacing="0" Font-Names="Verdana, Arial, sans-serif"
BorderColor="Black" BorderWidth="1"
GridLines="Horizontal"
OnItemDataBound="CustomerDataGrid_OnItemDataBound" EnableViewState="False">
<AlternatingItemStyle BackColor="Tan"></AlternatingItemStyle>
<ItemStyle Font-Size="X-Small"></ItemStyle>
<HeaderStyle Font-Size="Small" Font-Names="Arial" Font-Bold="True"
ForeColor="White" BackColor="Maroon"></HeaderStyle>
<Columns>
<asp:BoundColumn Visible="False"
DataField="CustomerID"></asp:BoundColumn>
<asp:HyperLinkColumn
DataTextField="CustomerID"
DataNavigateUrlField="CustomerID"
DataNavigateUrlFormatString="OrderDetailDataGrid.a spx?customerid={0}"
HeaderText="ID"
ItemStyle-VerticalAlign="Top" />

<asp:TemplateColumn HeaderText="Customer">
<ItemStyle VerticalAlign="Top"></ItemStyle>
<ItemTemplate>
<b>
<%# DataBinder.Eval(Container.DataItem, "CompanyName") %>
</b>
<br>
<%# DataBinder.Eval(Container.DataItem, "Address" ) %>
<br>
<%# DataBinder.Eval(Container.DataItem, "City" ) %>
,
<%# DataBinder.Eval(Container.DataItem, "Region") %>
<%# DataBinder.Eval(Container.DataItem, "PostalCode" ) %>
<br>
<br>
<%# DataBinder.Eval(Container.DataItem, "ContactName" ) %>
<br>
<%# DataBinder.Eval(Container.DataItem, "ContactTitle" ) %>
<br>
<%# DataBinder.Eval(Container.DataItem, "Phone" ) %>
</ItemTemplate>
</asp:TemplateColumn>
<asp:TemplateColumn ItemStyle-VerticalAlign="Top"
HeaderText="Orders">
<%-- Embedded DataGrid will go here --%>
</asp:TemplateColumn>
</Columns>
</aspataGrid>
<!-- End DataGrid -->
</form>
<!-- End Web Form -->
</body>
</HTML>

-------------------
CODE BEHIND
------------------
using System;
using System.Data;
using System.Data.SqlClient;
using System.Drawing;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.HtmlControls;
using System.Configuration;

namespace MasterDetail
{
public class CustomerOrderDataGrid : System.Web.UI.Page
{
protected DataGrid CustomerDataGrid;
private DataSet ds = new DataSet();

private void Page_Load(object sender, System.EventArgs e)
{
string sqlStmt = "SELECT top 2 * FROM Customers; SELECT * FROM Orders";
string conString =
"server=localhost;database=Northwind;uid=sa;pwd=ti etronix;";

SqlDataAdapter sda = new SqlDataAdapter(sqlStmt, conString);

sda.Fill(ds);
ds.Tables[0].TableName = "Customers";
ds.Tables[1].TableName = "Orders";

CustomerDataGrid.DataSource = ds.Tables["Customers"];
CustomerDataGrid.DataBind();
}

//Use the OnItemDataBound event handler to dynamically add an embedded
DataGrid
protected void CustomerDataGrid_OnItemDataBound(object sender,
DataGridItemEventArgs e)
{
//When each row is created in the DataGrid, eval the ItemType
if(e.Item.ItemType == ListItemType.Item ||
e.Item.ItemType == ListItemType.AlternatingItem)
{
//If the ItemType is Item or AlternatingItem,
//Create a new DataGrid object named OrdersDataGrid
DataGrid OrdersDataGrid = new DataGrid();

//Format the DataGrid to look cool.
OrdersDataGrid.BorderWidth = (Unit)1;
OrdersDataGrid.CellPadding = 4;
OrdersDataGrid.CellSpacing = 0;
OrdersDataGrid.GridLines = GridLines.Horizontal;
OrdersDataGrid.BorderColor = Color.FromName("Black");

OrdersDataGrid.ItemStyle.Font.Name = "Verdana";
OrdersDataGrid.ItemStyle.Font.Size = FontUnit.XSmall;

OrdersDataGrid.AlternatingItemStyle.BackColor =
Color.FromName("LightGray");

OrdersDataGrid.ShowHeader = true;
OrdersDataGrid.HeaderStyle.BackColor = Color.FromName("Black");
OrdersDataGrid.HeaderStyle.ForeColor = Color.FromName("White");
OrdersDataGrid.HeaderStyle.Font.Bold = true;
OrdersDataGrid.HeaderStyle.Font.Size = FontUnit.XSmall;


//Do not autogenerate columns.
OrdersDataGrid.AutoGenerateColumns = false;

//Add a series of BoundColumns
//Order ID
BoundColumn bc = new BoundColumn();
//Set the BoundColumn Values
bc.HeaderText = "Order ID";
bc.DataField = "OrderID";
bc.ItemStyle.Wrap = false;
//Add the BoundColumn to the OrdersDataGrid.
OrdersDataGrid.Columns.Add(bc);

//Order Date
bc = new BoundColumn();
bc.HeaderText = "Order Date";
bc.DataField = "OrderDate";
bc.DataFormatString="{0:d}";
bc.ItemStyle.Wrap = false;
OrdersDataGrid.Columns.Add(bc);

//Required Date
bc = new BoundColumn();
bc.HeaderText = "Required Date";
bc.DataField = "RequiredDate";
bc.DataFormatString="{0:d}";
bc.ItemStyle.Wrap = false;
OrdersDataGrid.Columns.Add(bc);

//Shipped Date
bc = new BoundColumn();
bc.HeaderText = "Shipped Date";
bc.DataField = "ShippedDate";
bc.DataFormatString="{0:d}";
bc.ItemStyle.Wrap = false;
OrdersDataGrid.Columns.Add(bc);

// ADD THE CUSTOM BUILT COL HERE
DropDownListColumn DDLC = new DropDownListColumn();
DDLC.HeaderText = "My DDL";
OrdersDataGrid.Columns.Add(DDLC);

//End BoundColumns

//Get the Authors DataView and filter it for the current ISBN
DataView _orders = ds.Tables["Orders"].DefaultView;
_orders.RowFilter = "CustomerID='" + e.Item.Cells[0].Text + "'";

//Bind the DataGrid.
OrdersDataGrid.DataSource = _orders;
OrdersDataGrid.DataBind();

e.Item.Cells[3].Controls.Add(OrdersDataGrid);
}
}


override protected void OnInit(EventArgs e)
{
//
// CODEGEN: This call is required by the ASP.NET Web Form Designer.
//
InitializeComponent();
base.OnInit(e);
}

private void InitializeComponent()
{
this.Load += new System.EventHandler(this.Page_Load);
}
}
}

----------------------------------
Custom built data Grid col code
-----------------------------------
using System;
using System.Web.UI.WebControls;

namespace MasterDetail
{

public class DropDownListColumn : DataGridColumn
{
public DropDownListColumn() : base()
{
}

public override void InitializeCell(TableCell cell, int columnIndex,
ListItemType itemType)
{
base.InitializeCell(cell, columnIndex, itemType);

switch (itemType)
{
case ListItemType.EditItem:
case ListItemType.Item:
case ListItemType.AlternatingItem:
case ListItemType.SelectedItem:
cell.DataBinding += new EventHandler(this.ItemDataBinding);
DropDownList DLL = new DropDownList();
cell.Controls.Add( DLL );
break;
case ListItemType.Header:
break;
}

}

private void ItemDataBinding(object sender, EventArgs e)
{
TableCell cell = (TableCell)sender;
DropDownList DDL1 = (DropDownList)cell.Controls[0];
DDL1.Items.Add(new ListItem("one","1"));
DDL1.Items.Add(new ListItem("two","2"));
DDL1.Items.Add(new ListItem("three","3"));
}
}
}


 
Reply With Quote
 
 
 
 
=?Utf-8?B?UGhpbGxpcCBXaWxsaWFtcw==?=
Guest
Posts: n/a
 
      07-19-2005
"Girish" wrote:

> My Question:
>
> 1) How do I setup ONE postback event handler for ALL the drop downlist
> controls being rendered dynamically in the embedded grid?
> 2) The event handler must be in the code-behind code that uses the custom
> built DataGridColumn and should not be in the DataGridColumn code itself.
> 2) How do I figure out in that one event handler method, the drop down list
> that threw the event, and the value of the selected item.


You can have the dropdownlist raise the SelectedIndexChanged event and then
trap the event (in the codebehind of the Page class, as you wanted) using
Event Bubbling. Lookup for samples on Event Bubbling on the MSDN library.

Consider though the size of the downloaded page. If every row of your
DataGrid were to repeat the same data for the dropdownlist then your page can
easily run over 1 megabyte in size (when handling real data). I would either:

1. Add an EditCommandButton in the DataGrid and leave the DropDownList in
the EditItemTemplate of one column. The DropDownList will only be displayed
in one row at a time when you bind it to its DataSource (this happens during
your handling the EditItem event). In this scenario the Update button would
raise the ItemCommand event. In processing the ItemCommand event you can get
both:

a. The ItemIndex of the grid where the postback occurred:
e.Item.ItemIndex, and
b. A reference to the dropdown list:
(DropDownList)e.Item.Cells[x].Controls[0]
(where x = the column no).

2. Replace the DropDownList by a TextBox and use client-side Javascript
to transform an xml data document using xslt to display a list of matching
results as demonstrated on this page:
http://www.societopia.net/samples/textbox.htm

--
http://www.webswapp.com
http://www.societopia.net

 
Reply With Quote
 
 
 
 
Girish
Guest
Posts: n/a
 
      07-19-2005
Appreciate the insight into page load size. I dont think this will be an
issue since we will be working with barely 10 rows per page.

I looked at Event Bubbling, but it requires that my DropDownListColumn
inherit from class Control. My DropDownListColumn already inherits from
DataGridColumn so i cant multiple inherit... im sure im missing something
simple here. pse advice.

thanks,
Girish


"Phillip Williams" <(E-Mail Removed)> wrote in message
news:(E-Mail Removed)...
> "Girish" wrote:
>
>> My Question:
>>
>> 1) How do I setup ONE postback event handler for ALL the drop downlist
>> controls being rendered dynamically in the embedded grid?
>> 2) The event handler must be in the code-behind code that uses the custom
>> built DataGridColumn and should not be in the DataGridColumn code itself.
>> 2) How do I figure out in that one event handler method, the drop down
>> list
>> that threw the event, and the value of the selected item.

>
> You can have the dropdownlist raise the SelectedIndexChanged event and
> then
> trap the event (in the codebehind of the Page class, as you wanted) using
> Event Bubbling. Lookup for samples on Event Bubbling on the MSDN library.
>
> Consider though the size of the downloaded page. If every row of your
> DataGrid were to repeat the same data for the dropdownlist then your page
> can
> easily run over 1 megabyte in size (when handling real data). I would
> either:
>
> 1. Add an EditCommandButton in the DataGrid and leave the DropDownList
> in
> the EditItemTemplate of one column. The DropDownList will only be
> displayed
> in one row at a time when you bind it to its DataSource (this happens
> during
> your handling the EditItem event). In this scenario the Update button
> would
> raise the ItemCommand event. In processing the ItemCommand event you can
> get
> both:
>
> a. The ItemIndex of the grid where the postback occurred:
> e.Item.ItemIndex, and
> b. A reference to the dropdown list:
> (DropDownList)e.Item.Cells[x].Controls[0]
> (where x = the column no).
>
> 2. Replace the DropDownList by a TextBox and use client-side
> Javascript
> to transform an xml data document using xslt to display a list of matching
> results as demonstrated on this page:
> http://www.societopia.net/samples/textbox.htm
>
> --
> http://www.webswapp.com
> http://www.societopia.net
>



 
Reply With Quote
 
=?Utf-8?B?UGhpbGxpcCBXaWxsaWFtcw==?=
Guest
Posts: n/a
 
      07-20-2005
This is a quick modification of your code to make the Event Bubbling works
http://www.societopia.net/samples/webform6.aspx

If I had more time I could have probably created a more elaborate custom
event.

I would still prefer the EditItem Template strategy as I mentioned in the
previous email. It is much cleaner.

Phillip
--
http://www.webswapp.com


"Girish" wrote:

> Appreciate the insight into page load size. I dont think this will be an
> issue since we will be working with barely 10 rows per page.
>
> I looked at Event Bubbling, but it requires that my DropDownListColumn
> inherit from class Control. My DropDownListColumn already inherits from
> DataGridColumn so i cant multiple inherit... im sure im missing something
> simple here. pse advice.
>
> thanks,
> Girish
>
>
> "Phillip Williams" <(E-Mail Removed)> wrote in message
> news:(E-Mail Removed)...
> > "Girish" wrote:
> >
> >> My Question:
> >>
> >> 1) How do I setup ONE postback event handler for ALL the drop downlist
> >> controls being rendered dynamically in the embedded grid?
> >> 2) The event handler must be in the code-behind code that uses the custom
> >> built DataGridColumn and should not be in the DataGridColumn code itself.
> >> 2) How do I figure out in that one event handler method, the drop down
> >> list
> >> that threw the event, and the value of the selected item.

> >
> > You can have the dropdownlist raise the SelectedIndexChanged event and
> > then
> > trap the event (in the codebehind of the Page class, as you wanted) using
> > Event Bubbling. Lookup for samples on Event Bubbling on the MSDN library.
> >
> > Consider though the size of the downloaded page. If every row of your
> > DataGrid were to repeat the same data for the dropdownlist then your page
> > can
> > easily run over 1 megabyte in size (when handling real data). I would
> > either:
> >
> > 1. Add an EditCommandButton in the DataGrid and leave the DropDownList
> > in
> > the EditItemTemplate of one column. The DropDownList will only be
> > displayed
> > in one row at a time when you bind it to its DataSource (this happens
> > during
> > your handling the EditItem event). In this scenario the Update button
> > would
> > raise the ItemCommand event. In processing the ItemCommand event you can
> > get
> > both:
> >
> > a. The ItemIndex of the grid where the postback occurred:
> > e.Item.ItemIndex, and
> > b. A reference to the dropdown list:
> > (DropDownList)e.Item.Cells[x].Controls[0]
> > (where x = the column no).
> >
> > 2. Replace the DropDownList by a TextBox and use client-side
> > Javascript
> > to transform an xml data document using xslt to display a list of matching
> > results as demonstrated on this page:
> > http://www.societopia.net/samples/textbox.htm
> >
> > --
> > http://www.webswapp.com
> > http://www.societopia.net
> >

>
>
>

 
Reply With Quote
 
girish
Guest
Posts: n/a
 
      07-20-2005
Thanks for your help again Phillip. I tend to be very inquisitive by
nature... my apologies in advance..

1) What do you mean by "create a more elaborate custom event?"
2) To bubble events in user created controls, you have to inherit from
control and override RaiseBubbleEvent . Why is this? Why cant you get away
with what you did in your example?

If you could point me to articles, that would also be helpful rather than
typing out huge replies.

Thanks a mill again,
Girish


"Phillip Williams" <(E-Mail Removed)> wrote in message
news:(E-Mail Removed)...
> This is a quick modification of your code to make the Event Bubbling works
> http://www.societopia.net/samples/webform6.aspx
>
> If I had more time I could have probably created a more elaborate custom
> event.
>
> I would still prefer the EditItem Template strategy as I mentioned in the
> previous email. It is much cleaner.
>
> Phillip
> --
> http://www.webswapp.com
>
>
> "Girish" wrote:
>
>> Appreciate the insight into page load size. I dont think this will be an
>> issue since we will be working with barely 10 rows per page.
>>
>> I looked at Event Bubbling, but it requires that my DropDownListColumn
>> inherit from class Control. My DropDownListColumn already inherits from
>> DataGridColumn so i cant multiple inherit... im sure im missing something
>> simple here. pse advice.
>>
>> thanks,
>> Girish
>>
>>
>> "Phillip Williams" <(E-Mail Removed)> wrote in message
>> news:(E-Mail Removed)...
>> > "Girish" wrote:
>> >
>> >> My Question:
>> >>
>> >> 1) How do I setup ONE postback event handler for ALL the drop downlist
>> >> controls being rendered dynamically in the embedded grid?
>> >> 2) The event handler must be in the code-behind code that uses the
>> >> custom
>> >> built DataGridColumn and should not be in the DataGridColumn code
>> >> itself.
>> >> 2) How do I figure out in that one event handler method, the drop down
>> >> list
>> >> that threw the event, and the value of the selected item.
>> >
>> > You can have the dropdownlist raise the SelectedIndexChanged event and
>> > then
>> > trap the event (in the codebehind of the Page class, as you wanted)
>> > using
>> > Event Bubbling. Lookup for samples on Event Bubbling on the MSDN
>> > library.
>> >
>> > Consider though the size of the downloaded page. If every row of your
>> > DataGrid were to repeat the same data for the dropdownlist then your
>> > page
>> > can
>> > easily run over 1 megabyte in size (when handling real data). I would
>> > either:
>> >
>> > 1. Add an EditCommandButton in the DataGrid and leave the
>> > DropDownList
>> > in
>> > the EditItemTemplate of one column. The DropDownList will only be
>> > displayed
>> > in one row at a time when you bind it to its DataSource (this happens
>> > during
>> > your handling the EditItem event). In this scenario the Update button
>> > would
>> > raise the ItemCommand event. In processing the ItemCommand event you
>> > can
>> > get
>> > both:
>> >
>> > a. The ItemIndex of the grid where the postback occurred:
>> > e.Item.ItemIndex, and
>> > b. A reference to the dropdown list:
>> > (DropDownList)e.Item.Cells[x].Controls[0]
>> > (where x = the column no).
>> >
>> > 2. Replace the DropDownList by a TextBox and use client-side
>> > Javascript
>> > to transform an xml data document using xslt to display a list of
>> > matching
>> > results as demonstrated on this page:
>> > http://www.societopia.net/samples/textbox.htm
>> >
>> > --
>> > http://www.webswapp.com
>> > http://www.societopia.net
>> >

>>
>>
>>



 
Reply With Quote
 
=?Utf-8?B?UGhpbGxpcCBXaWxsaWFtcw==?=
Guest
Posts: n/a
 
      07-20-2005
"girish" wrote:

> Thanks for your help again Phillip. I tend to be very inquisitive by
> nature... my apologies in advance..


You are welcome. I get to learn too.


> 1) What do you mean by "create a more elaborate custom event?"


In this example I had to pass the primary key of the record as the ID of the
dropdownlist control to discover the GridDataItem.ItemIndex. There might be a
better way of doing that.

> 2) To bubble events in user created controls, you have to inherit from
> control and override RaiseBubbleEvent . Why is this? Why cant you get away
> with what you did in your example?


http://msdn.microsoft.com/library/de...mmandevent.asp

In this sample you had your parent Grid on the webform already and added the
code for the child grid in the same page of the codeBehind. This is a just a
proof of concept. However if you intend to deploy them in production you
might create each as separate control inherited from the datagrid and have to
bubble events from the child grid to the parent and then from the parent to
the page that contain it or any other container that you have customized.

Phillip
---
www.societopia.net
www.webswapp.com

 
Reply With Quote
 
=?Utf-8?B?UGhpbGxpcCBXaWxsaWFtcw==?=
Guest
Posts: n/a
 
      07-21-2005

"girish" wrote:

> Thanks for your help again Phillip. I tend to be very inquisitive by
> nature... my apologies in advance..
>
> 1) What do you mean by "create a more elaborate custom event?"


I found a couple of nice and clear samples on the MSDN library to help you
create event delegates and custom event data classes that you might be
interested in:

http://msdn.microsoft.com/library/de...ini-sample.asp

http://msdn.microsoft.com/library/de...trolsample.asp

Hope this helps.

Phillip
---
http://www.webswapp.com
http://www.societopia.net

 
Reply With Quote
 
Girish
Guest
Posts: n/a
 
      07-21-2005
Thanks Phillip. Youve been a great help.

g

"Phillip Williams" <(E-Mail Removed)> wrote in message
news:(E-Mail Removed)...
>
> "girish" wrote:
>
>> Thanks for your help again Phillip. I tend to be very inquisitive by
>> nature... my apologies in advance..
>>
>> 1) What do you mean by "create a more elaborate custom event?"

>
> I found a couple of nice and clear samples on the MSDN library to help you
> create event delegates and custom event data classes that you might be
> interested in:
>
> http://msdn.microsoft.com/library/de...ini-sample.asp
>
> http://msdn.microsoft.com/library/de...trolsample.asp
>
> Hope this helps.
>
> Phillip
> ---
> http://www.webswapp.com
> http://www.societopia.net
>



 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Problem with custom DataGridColumn Dynamic ViewState. VinÝcius Pitta Lima de Ara˙jo ASP .Net Datagrid Control 0 02-14-2005 05:49 PM
SWsoft Acronis Disk Director Suite 9.0 Build 508, Acronis OS Selector 8.0 Build 917, Acronis Partition Expert 2003 Build 292, Acronis Power Utilities 2004 Build 502, F-SECURE.ANTI vIRUS.PROXY v1.10.17.WINALL, F-SECURE.ANTI vIRUS v5.50.10260 for CITRI vvcd Computer Support 0 09-25-2004 01:38 AM
Custom DataGridColumn DataGridItems not saving to ViewState. Not Visible on Postback Jay Walker ASP .Net 2 02-08-2004 04:51 AM
Custom DataGridColumn DataGridItems not saving to ViewState. Not Visible on Postback Jay Walker ASP .Net Web Controls 2 02-08-2004 04:51 AM
Custom DataGridColumn DataGridItems not saving to ViewState. Not Visible on Postback Jay Walker ASP .Net Datagrid Control 2 02-08-2004 04:51 AM



Advertisments