Link to home
Start Free TrialLog in
Avatar of ClassyLinks
ClassyLinksFlag for Canada

asked on

Set SelectedIndex on Dynamically Generated DropDownList

Hey folks!

I've got a very large datagrid, filled with client data to be edited, populated from tblClient.

In this grid, I've got 6 dropdownlists populated with selections from separate tables.  How do I get the selected index of each dropdownlist to equal the value entered in the tblclient??

I tried "selecedIndex='<%#Container.DataItem("FieldName")%> but that just gave me the second or third in the list, not the actual match.

Is that at all clear??

Thanks to all for your help!
Avatar of raterus
raterus
Flag of United States of America image

SelectedIndex refers to the index of the listitems, not necessarily the actual values of the listitems.  If you are doing all this extra binding, I'd do this it in the ItemDataBound event of the DataGrid, much easier to keep track of.  In there, you would need to have something like this.

thisDDL.items.FindByValue(e.Item.DataItem("FieldName")).selected = True

Hope this gets you started,
--Michael
Avatar of ClassyLinks

ASKER

Thanks Michael.

So, Would I put it in the BindGrid, or where I'm populating the dropdown??

for example, by ddl is populated with this:

'*******************************************
   
    Private Function BindState()
        Dim myCommand As SqlCommand = New SqlCommand("sp_listareas_display", Connect)

        myCommand.CommandType = CommandType.StoredProcedure
            'myCommand.Parameters.Add("@RegionId", RegionID)

        Connect.Open()
        Return myCommand.ExecuteReader(CommandBehavior.CloseConnection)
    End Function
 
  Dim strCurrentState as Integer
 
Private Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
 
Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
Dim strTemp as String = cboStateTemp.SelectedItem.Value

       Dim myDropDown as DropDownList
       myDropDown = Ctype(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
End Sub

'*******************************************

Adding:
  myDropDown.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True

Just before the  end of the sub doesn't have any impact.

Nor does putting the same code just before I bind the page.  Where should I put it?
Avatar of praneetha
praneetha

Private Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
 
Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
Dim strTemp as String = cboStateTemp.SelectedItem.Value
mcboStateTemp.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True


   
End Sub
cboStateTemp.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True

or

cboStateTemp.items.FindByValue(e.Item.cells[2].Text).selected = True

if 2 is the index where clinetoriginalareaid in datagrid
I prefer to do it cboStateTemp.SelectedIndex = cboStateTemp.Items.IndexOf(cboStateTemp.Items.FindByValue(e.Item.cells[2].Text))

The reason I prefer to do it this way is because if you do it like cboStateTemp.items.FindByValue(e.Item.cells[2].Text).selected = True and the e.Item.cells[2].Text is not found in the dropdownlist, it will throw an error.  The way I list will not throw the error.  
I have tried as suggested above, but the selected index does not change.  :(
does it throw any exception...


cboStateTemp.items.FindByValue("any team id ").selected = True

hard code it for a while and see if that helps..

cboStateTemp.items.FindByValue("2").selected = True



If you ever run FindByValue and it doesn't cause any errors, then it did at least something.  (If it can't find that listitem, it'll let you know with a big fat exception)  Are you positive you have the correct data in which to assign this ddl set?
Did you try both methods?  Did you get an error thrown?  Are you sure it is calling DG_ItemDataBound?
I must have something totally wrong...because even "hard coding" doesn't have an effect.
make sure it is going to dg_itemdatabound....try it in debug mode...


cboStateTemp.items.FindByValue(cboStateTemp.SelectedItem.Value).selected = false;
cboStateTemp.items.FindByValue("any team id ").selected = True
You can turn trace mode on and use Trace.Write to figure out where it is getting.  Can you post your entire dg_itemdatabound function if it is calling it?
you might also want to wrap your code in ItemDataBound with this, so you won't do this on header/footer items

        If e.Item.ItemType <> ListItemType.Header And e.Item.ItemType <> ListItemType.Footer Then
          'all your code
        End If
Ok....I don't know what you are referring to with trace mode.

Here is the dg_itemdatabound.....

'*******************************************
   
    Private Function BindState()
        Dim myCommand As SqlCommand = New SqlCommand("sp_listareas_display", Connect)

        myCommand.CommandType = CommandType.StoredProcedure
            'myCommand.Parameters.Add("@RegionId", RegionID)

        Connect.Open()
        Return myCommand.ExecuteReader(CommandBehavior.CloseConnection)
    End Function
 
  Dim strCurrentState as Integer
 
Private Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
 
      Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
      Dim strTemp as String = cboStateTemp.SelectedItem.Value
            cboStateTemp.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True
       
    Dim myDropDown as DropDownList
       myDropDown = Ctype(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
End Sub

'*******************************************

And the ddl calls it here:

<asp:DropDownList
id="ClientOriginAreaID"
DataSource="<%# BindState() %>"
DataTextField="AREAName"
DataValueField="AREAID"
runat="server"/>

What am I missing??
You need to hook up the call to DG_ItemDataBound.  Are you doing this?  Are you using Visual Studio.NET?
Trace is a neat little feature that let's you insert debugging print statements

http://www.dotnetjunkies.com/quickstart/aspplus/doc/tracelogpage.aspx
Private Function BindState()

i think bindstate should be either protected or public...

and is bindstate called.....

and it should eithr return dataset or datatable
I have VS.net...but don't use it...never really got the hang of the interface...use text editor instead.

Making the function Protected  or Public doesn't help.

bindState is called with the dropdownlist (called via the DataSource property)

What do you mean by:  "You need to hook up the call to DG_ItemDataBound"??

The field is indeed being bound as the ddl is populated.....just cannot get the right value selected  :(
override protected void OnInit(EventArgs e)
            {      this.DataGrid1.ItemDataBound += new System.Web.UI.WebControls.DataGridItemEventHandler(this.DataGrid1_ItemDataBound);

}
Where should I put that Praneetha??
in oninit method...

all this is automatically done when u use vs.net..so try using it...

oninit is called for every request

override protected void OnInit(EventArgs e)
            {
                  //
                  // CODEGEN: This call is required by the ASP.NET Web Form Designer.
                  //
                  InitializeComponent();
                  base.OnInit(e);
            }
            
            /// <summary>
            /// Required method for Designer support - do not modify
            /// the contents of this method with the code editor.
            /// </summary>
            private void InitializeComponent()
            {    
                  this.DataGrid1.ItemDataBound += new System.Web.UI.WebControls.DataGridItemEventHandler(this.DataGrid1_ItemDataBound);
                  this.Button1.Click += new System.EventHandler(this.Button1_Click);
                  this.Load += new System.EventHandler(this.Page_Load);

            }
Yep...that's what I meant.  If you used VS.Net, it makes it simple to add it, that's why I asked, but the line above will work except of course you need to put in DB_ItemDataBound instead of this.DataGrid1_ItemDataBound.
Should this be INSIDE a sub??

I keep getting

 Name 'override' is not declared.
OT....

This would have been Sooooooooooo easy in Classic ASP.  .Net seems to make things so much more complex to do a simple little function.

<sigh>
does your class derive from

      
      public class webpage1 : System.Web.UI.Page
      {

//here override oninit...


do u have codebehind file...


webform.aspx.cs

It should be inside your page class.  I'm actually surprised you don't have it already.  Are you not doing anything on load of the page?  Are you using code behind or are you putting everything in the aspx page?
everything is on the aspx page.

do you mean it should be in my Page_Load??  It still tells me override is not declared.

    Sub Page_load(ByVal sender As System.Object, ByVal e As System.EventArgs)
   
      override protected void OnInit(EventArgs e)
          {
               //
               // CODEGEN: This call is required by the ASP.NET Web Form Designer.
               //
               InitializeComponent();
               base.OnInit(e);
          }
         
          /// <summary>
          /// Required method for Designer support - do not modify
          /// the contents of this method with the code editor.
          /// </summary>
          private void InitializeComponent()
          {    
               this.ContactGrid.ItemDataBound += new System.Web.UI.WebControls.DataGridItemEventHandler(this.DG_ItemDataBound);
               //this.Button1.Click += new System.EventHandler(this.Button1_Click);
               this.Load += new System.EventHandler(this.Page_Load);

          }

                RegionID = Session("RegionID")
   
            Dim ID AS Integer
 
            If Not IsPostBack then
                BindDataGrid(ID)
            end if
   
   
    End Sub


ok this is C# code..i guess it is diff in vb.net..sorry about that
No.  It shouldn't be in your page_load.  I think we were both under the assumption that you had a code behind page.  I've actually never written a non-code behind page, but my first guess is to ignore the OnInit stuff and instead in your datagrid tag, add "onitemdatabound=DG_ItemDataBound"  I've never done that before though, so I don't really know if it'll work...
OT  You may want to consider spending the time to get a hang of VS.NET.  It REALLY cuts down on dev time and makes it much easier to set stuff like this up...
ok....putting the onitemdatabound=DG_ItemDataBound" in the grid at least moves it along to an error.


System.NullReferenceException: Object reference not set to an instance of an object.

Line 139:Public Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
Line 140:      Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
Line 141:      Dim strTemp as String = cboStateTemp.SelectedItem.Value
Line 142:            cboStateTemp.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True
:Public Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
{

   If e.Item.ItemType <> ListItemType.Header And e.Item.ItemType <> ListItemType.Footer Then
          'all your code
        End If


use that
do you have a control on the page with id=ClientOriginAreaID runat=server?

Which line is bolded as the line of the error?
Praneetha...that gives me:

Exception Details: System.Web.HttpException: A DropDownList cannot have multiple items selected.

 
Public Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
   If e.Item.ItemType <> ListItemType.Header And e.Item.ItemType <> ListItemType.Footer Then
      Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
      Dim strTemp as String = cboStateTemp.SelectedItem.Value
            cboStateTemp.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True
       
    Dim myDropDown as DropDownList
       myDropDown = Ctype(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
      End If  
End Sub
Ignore my questions, praneetha hit it on the head!
Try using my way of selecting from way above...it won't give you that error...
sorry muellerfan,

It was line 141, and yes, the ddl is called ClientOriginAreaID

cboStateTemp.items.FindByValue(cboStateTemp.SelectedItem.Value).selected = False;

cboStateTemp.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True
ASKER CERTIFIED SOLUTION
Avatar of muellerfan
muellerfan

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
With both suggestions I get the same error:

Line 142:      Dim strTemp as String = cboStateTemp.SelectedItem.Value

Exception Details: System.NullReferenceException: Object reference not set to an instance of an object.
comment that link you don;t need it...

Dim strTemp as String = cboStateTemp.SelectedItem.Value
I don't think you need that line of code where you have it.  What do you use strTemp for?
No Joy.

No matter which way I slice it, still get  Object reference not set to an instance of an object.

 Public Function BindState()
        Dim myCommand As SqlCommand = New SqlCommand("sp_listareas_display", Connect)

        myCommand.CommandType = CommandType.StoredProcedure
            'myCommand.Parameters.Add("@RegionId", RegionID)

        Connect.Open()
        Return myCommand.ExecuteReader(CommandBehavior.CloseConnection)
    End Function
 
  Dim strCurrentState as Integer
 
Public Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
  ' If e.Item.ItemType <> ListItemType.Header And e.Item.ItemType <> ListItemType.Footer Then
      Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
      'Dim strTemp as String = cboStateTemp.SelectedItem.Value


'cboStateTemp.items.FindByValue(cboStateTemp.SelectedItem.Value).selected = False
'cboStateTemp.items.FindByValue(e.Item.DataItem("ClientOriginAreaID")).selected = True
cboStateTemp.SelectedIndex = cboStateTemp.Items.IndexOf(cboStateTemp.Items.FindByValue(e.Item.DataItem("ClientOriginAreaID")))
       
   ' Dim myDropDown as DropDownList
    '   myDropDown = Ctype(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
     ' End If  
End Sub
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
That did it!

Brilliant

Now I can get it working for the other 5 ddl's and I'll be laughing.

Thanks to both for all your patience.
before you run away....maybe there is an easier way.

Currently I have 6 identical functions the one above.  I called them DG_ItemDataBound1, DG_ItemDataBound2 etc.

IF the datagrid is calling the DG_ItemDataBound in the onitemdatabound property, How can I have multple values in there so that it runs all 6 functions to populate all 6 ddls??
The ItemDataBound event is raised after an item is data bound to the Datagrid control. This event provides you with the last opportunity to access the data item before it is displayed on the client. After this event is raised, the data item is nulled out and no longer available.(from msdn)


http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpref/html/frlrfsystemwebuiwebcontrolsdatalistclassitemdataboundtopic.asp


Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
Dim cboStateTemp1 As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID1"), DropDownList)

do that in the same function....
i suggest you start using vs.net 2002 ...i am sure you will find lot of things simplified...

Sorry for the delay...I was at lunch.  Yes, you can do as praneetha says and put all six dropdownlist sets in the same DG_ItemDataBound.  Have you tried this yet?  Does it work?
This is great!  Thanks to you both.  For anyone checking out this question and wanting the final code, here is what I'm using:

6 dropdown lists populated this way:

'*******************************************
 
Public Sub DG_ItemDataBound(s as object, e as DataGridItemEventArgs)
   If e.Item.ItemType <> ListItemType.Header And e.Item.ItemType <> ListItemType.Footer Then
      Dim cboStateTemp As DropDownList = CType(e.Item.FindControl("ClientOriginAreaID"), DropDownList)
            cboStateTemp.SelectedIndex = cboStateTemp.Items.IndexOf(cboStateTemp.Items.FindByValue(e.Item.DataItem("ClientOriginAreaID")))

         Dim cboStateTemp2 As DropDownList = CType(e.Item.FindControl("ClientReason1ID"), DropDownList)
            cboStateTemp2.SelectedIndex = cboStateTemp2.Items.IndexOf(cboStateTemp2.Items.FindByValue(e.Item.DataItem("ClientReason1ID")))

         Dim cboStateTemp3 As DropDownList = CType(e.Item.FindControl("ClientReason2ID"), DropDownList)
            cboStateTemp3.SelectedIndex = cboStateTemp3.Items.IndexOf(cboStateTemp3.Items.FindByValue(e.Item.DataItem("ClientReason2ID")))
     
         Dim cboStateTemp4 As DropDownList = CType(e.Item.FindControl("Client1stchoiceAreaID"), DropDownList)
            cboStateTemp4.SelectedIndex = cboStateTemp4.Items.IndexOf(cboStateTemp4.Items.FindByValue(e.Item.DataItem("Client1stchoiceAreaID")))
 
        Dim cboStateTemp5 As DropDownList = CType(e.Item.FindControl("Client1stChoiceResidenceType"), DropDownList)
            cboStateTemp5.SelectedIndex = cboStateTemp5.Items.IndexOf(cboStateTemp5.Items.FindByValue(e.Item.DataItem("Client1stChoiceResidenceType")))
     
        Dim cboStateTemp6 As DropDownList = CType(e.Item.FindControl("Client2ndChoiceAreaID"), DropDownList)
            cboStateTemp6.SelectedIndex = cboStateTemp6.Items.IndexOf(cboStateTemp6.Items.FindByValue(e.Item.DataItem("Client2ndChoiceAreaID")))
     
        Dim cboStateTemp7 As DropDownList = CType(e.Item.FindControl("Client2ndChoiceResidenceType"), DropDownList)
            cboStateTemp7.SelectedIndex = cboStateTemp7.Items.IndexOf(cboStateTemp7.Items.FindByValue(e.Item.DataItem("Client2ndChoiceResidenceType")))
     
     End If  
End Sub

'*******************************************
'*******************************************
 
    Private Function BindState()
        Dim myCommand As SqlCommand = New SqlCommand("sp_listareas_display", Connect)

        myCommand.CommandType = CommandType.StoredProcedure
            'myCommand.Parameters.Add("@RegionId", RegionID)

        Connect.Open()
        Return myCommand.ExecuteReader(CommandBehavior.CloseConnection)
    End Function
'******************************************
'*******************************************
   
    Private Function BindState1()
        Dim myCommand As SqlCommand = New SqlCommand("sp_listreason_display", Connect)

        myCommand.CommandType = CommandType.StoredProcedure
            'myCommand.Parameters.Add("@RegionId", RegionID)

        Connect.Open()
        Return myCommand.ExecuteReader(CommandBehavior.CloseConnection)
    End Function
 
'*******************************************

'*******************************************
   
    Private Function BindState2()
        Dim myCommand As SqlCommand = New SqlCommand("sp_listrestype_display", Connect)

        myCommand.CommandType = CommandType.StoredProcedure
            'myCommand.Parameters.Add("@RegionId", RegionID)

        Connect.Open()
        Return myCommand.ExecuteReader(CommandBehavior.CloseConnection)
    End Function

'*******************************************

Then each ddl calls the appropriate function in its datasource property like this:

<asp:dropdownlist
    Runat="server"
    DataSource="<%# BindState1() %>"
    rows="1"
    id="ClientReason1ID"
    DataTextField="ReasonforLeaving"
    DataValueField="ReasonID" />

Hope this helps the next person struggling with the same thing.

Cheers!