I have seen a number of questions regarding how to specify what the selected ListItem is on a DropDownList used in an EditRow of A GridView. So I thought it might make a good blog.
Note: for an example that uses Ajax, specifically the CascadingDropDown, look here
http://www.myfriedmind.com/techBlog/2009/06/22/CascadingDropDownListsGridViewsAndDynamicallySelectingTheAppropriateListItemDuringEdit.aspx.
Basically what people are trying to do is use a DropDownList as one of the input controls on a DataRow when edit is selected for that Row. This, of course, limits what people can enter which is a good thing. For example, what if you wanted to create a DropDownList that specified which state someone was from, or what time (using 15-minute increments)?
Creating the DropDownList is fairly straightforward, as is populating it. What is confusing people is how to specify what the selected value is. To do that you need to handle the OnRowDataBound event, snag the DataItem and select the ListItem that matches the appropriate property. Like so:
Sample DataObject (in c#)
class MyObject
{
public int ObjId {get; set;}
public string StateAbbreviation {get; set; }
}
Sample DataObject (in vb.net)
Class MyObject
Public ObjId As Integer
Public StateAbbreviation As String
End Class
Entry on the SampleGridview.aspx page (as simple as you can get it )
<asp:GridView runat="server" ID="lstMyData" DataKeyNames="ObjId"
AutoGenerateColumns="false" EnableViewState="true"
AutoGenerateEditButton="true"
OnRowDataBound="lstMyData_RowDataBound" >
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:Label runat="server" ID="lblState" Text='<%# Eval("StateAbbreviation") %>' />
</ItemTemplate>
<EditItemTemplate>
<asp:DropDownList runat="server" ID="uxState" />
</EditItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
Codebehind (in c#) SampleGridview.aspx.cs
protected void lstMyData_RowDataBound(object sender,
GridViewRowEventArgs e)
{
// verify this is a DataRow, not a Header, Footer, etc...
if (e.Row.RowType == DataControlRowType.DataRow)
{
// in case you want to do something else here....
// see if this is the Row used for Editing
if ((e.Row.RowState & DataControlRowState.Edit) != 0)
{
// get the DataItem that is bound
// and cast it accordingly
MyObject _myObject = (MyObject)e.Row.DataItem;
// get the dropdownlist
DropDownList _uxState =
(DropDownList) e.Row.FindControl("uxState");
// dynamically create the DDL for demo...
// this could also be done statically in the aspx page
_uxState.Items.Add(new ListItem("Hawaii", "HI"));
_uxState.Items.Add(new ListItem("Iowa", "IA"));
_uxState.Items.Add(new ListItem("Minnesota", "MN"));
_uxState.Items.Add(new ListItem("Wisconsin", "WI"));
// find the matching ListItem and Select it
ListItem _matchingItem =
_uxState.Items.FindByValue(_myObject.StateAbbreviation);
if (_matchingItem == null)
{
// Houston we have a problem, no match...
// handle this as you see fit
}
else
{
_matchingItem.Selected = true;
}
}
}
}
Protected Sub lstMyData_RowDataBound(ByVal sender As Object, _
ByVal e As System.Web.UI.WebControls.GridViewRowEventArgs) _
Handles lstMyData.RowDataBound
If e.Row.RowType = DataControlRowType.DataRow Then
' in case you want to do something else here....
' see if this is the Row used for Editing
If (e.Row.RowState And DataControlRowState.Edit) <> 0 Then
' get the DataItem that is bound
' and cast it accordingly
Dim _myObject As MyObject = _
DirectCast(e.Row.DataItem, MyObject)
' get the dropdownlist
Dim _uxState As DropDownList = _
DirectCast(e.Row.FindControl("uxState"), DropDownList)
' dynamically create the DDL for demo...
' this could also be done statically in the aspx page
_uxState.Items.Add(New ListItem("Hawaii", "HI"))
_uxState.Items.Add(New ListItem("Iowa", "IA"))
_uxState.Items.Add(New ListItem("Minnesota", "MN"))
_uxState.Items.Add(New ListItem("Wisconsin", "WI"))
' find the matching ListItem and Select it
Dim _matchingItem As ListItem = _
_uxState.Items.FindByValue(_myObject.StateAbbreviation)
If _matchingItem Is Nothing Then
' Houston we have a problem, no match...
' handle this as you see fit
Else
_matchingItem.Selected = True
End If
End If
End If
End Sub
So basically what you are doing is getting a hold of both the value that you want selected (by using the e.Row.DataItem) and the DropDownList (by using e.Row.FindControl) and then simply doing a match...
Hope this helps...