locked
DDL Control has a SelectedValue which is invalid because it does not exist in the list of items RRS feed

  • Question

  • User-1367363180 posted

    Hi,

    I have rather simple db with next tables: Product (ProductID (primarykey), ProductName), CColor (CColorID (primarykey), CColorName) and Uses_Color (ProductID (primarykey, foreignkey), CColorID (primarykey, foreignkey), Description).

    For instance, tables could look like: 

    Product: 

    1, Product1

    2, Product2

    3, Product3

    CColor:

    1, White

    2, Black

    3, Blue

    4, Red

    5, Yellow

    Uses_Color:

    1, 1, Description1 (Product1 has White color)

    1, 2, Description2 (Product1 has Black color also)

    On web page, for a selected product, I want to be able to add additional colors but only those that are not fould in Uses_Color for that selected product. It means that for my test product Product1, I would be able to choose only 3 remaining colors: Blue, Red and Yellow not found in Uses_Color.

    Regarding controls on that page, I have a DetailsView in Insert mode where I could choose remaining colors for particular product and GridView to display all chosen colors for that products. Here is the sample:

    CColor.aspx:

    <asp:DetailsView ID="DetailsView1" runat="server"
                AutoGenerateRows="False"
                DataKeyNames="ProductID, CColorID" 
                InsertMethod="DetailsView1_InsertItem" 
                DefaultMode="Insert" 
                OnItemInserted="DetailsView1_ItemInserted" 
                >
                <Fields>
                    <asp:TemplateField SortExpression="CColorName" HeaderText="Color Name" >
                        <ItemTemplate>
                            <asp:Label ID="Label33" runat="server" Text='<%# Eval("CColorName") %>'></asp:Label>
                        </ItemTemplate>
                        <InsertItemTemplate>
                            <asp:DropDownList ID="DdlColorName" runat="server"
                                DataTextField="CColorName"
                                DataValueField="CColorID"
                                SelectedValue='<%# Bind("CColorID") %>'
                                SelectMethod="DdlColorName_GetData"
                                Width="250">
                            </asp:DropDownList>
                        </InsertItemTemplate>
                    </asp:TemplateField>
    ...
    ...
    <asp:GridView ID="GridView1" runat="server" 
                AutoGenerateColumns="False"
                DataKeyNames ="ProductID, CColorID" 
                SelectMethod="GridView1_GetData" 
                UpdateMethod="GridView1_UpdateItem"
                DeleteMethod="GridView1_DeleteItem"
                >
                <Columns>
                    <asp:BoundField DataField="ProductID" SortExpression="ProductID" HeaderText="ProductID" ReadOnly="true"/>
    
                    <asp:TemplateField SortExpression="CColorName" HeaderText="Color Name" >
                        <ItemTemplate>
                            <asp:Label ID="Label24" runat="server" Text='<%# Eval("CColorName") %>'></asp:Label>
                        </ItemTemplate>
                        <EditItemTemplate>
                            <asp:DropDownList ID="DdlColorName1" runat="server"
                                DataTextField="CColorName"
                                DataValueField="CColorID"
                                SelectedValue='<%# Bind("CColorID") %>'
                                SelectMethod="DdlColorName_GetData"
                                >
                            </asp:DropDownList>
                        </EditItemTemplate>
                    </asp:TemplateField>
    ...
    ...

    Code behind in CColor.aspx.cs:

    ...
    ...
    public IQueryable GridView1_GetData(string sortByExpression)
        {
            int chosen_pid = int.Parse(Request.QueryString["pid"]);
    
            var result = from u in db.Uses_Color
                           from c in db.CColores
                           where
                                c.CColoID == u.CColoID &&
                                u.ProductID == chosen_pid
                           select new { u.ProductID, u.CColorID, c.CColorName, u.Description };
           
            return result.AsQueryable();
        }
    
        public IQueryable DdlColorName_GetData()
        {
            int chosen_pid = int.Parse(Request.QueryString["pid"]);
    
            var result =
            (from c in db.CColores
             where
               !
                 (from u in db.Uses_Color
                  where
                     u.ProductID == chosen_pid 
                  select new
                  {
                      u.CColorID,
                     
                  }).Contains(new { CColorID = c.CColorID })
             select new
             {
                 c.CColorID,
                 c.CColorName
             });
    
            return result.AsQueryable();
        }
    ...
    ...

    DropDownList DdlColorName in DetailsView works as expected - it shows only remaining colors, but the same method used to populate DdlColorName1 in GridView throws error, when I click on Edit button:

    'DdlColorName1' has a SelectedValue which is invalid because it does not exist in the list of items.
    Parameter name: value

    Anyone knows where the problem is?

    Thanks, Alex

      

    Sunday, February 23, 2014 4:21 PM

Answers

  • User-1818759697 posted

    Hi,

    DropDownList chosen_color = (DropDownList)GridView1.FindControl("DropDownList1");

    For this situation, the above codes couldn't get the dropdownlist. And you could refer to the following information:

    GridView is a control which repeats its rows based on the bound data, e.g in practise it creates a set of controls (one row in it) as many times as there are rows in data source. In order to keep IDs of these controls unique, GridView and its rows are naming containers (implement INamingContainer interface). Being a naming container means that a control provides a new naming scope for its child controls by appending it's ID into ID of its own naming container.

    And being a naming container means that in order to look for a control with its local ID (not the unique id) you need to run FindControl against its naming container. In this case you run it againt GridView but GridView is not the direct naming container (or parent) of the HiddenField but the corresponding row (GridViewRow) is.

    (DropDownList)GridView1.Rows[i].FindControl("DropDownList1")

    Besides, you could also refer to:

    http://www.codeproject.com/Articles/12021/Accessing-the-different-controls-inside-a-GridView

    Regards

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Tuesday, March 4, 2014 8:50 PM

All replies

  • User22205941 posted

                            <asp:DropDownList ID="DdlColorName1" runat="server"
                                DataTextField="CColorName"
                                DataValueField="CColorID"
                                SelectedValue='<%# Bind("CColorID") %>'
                                SelectMethod="DdlColorName_GetData"
                                >
                            </asp:DropDownList>DropDownList DdlColorName in DetailsView works as expected - it shows only remaining colors, but the same method used to populate DdlColorName1 in GridView throws error, when I click on Edit button:
    

    'DdlColorName1' has a SelectedValue which is invalid because it does not exist in the list of items.
    Parameter name: value 

    DDL has selected value and that value is not exist in Dropdown ListItems. So you have to bind data first and then set a selected value. So you set a selected value in codebehind.

    ie,

    DdlColorName1.SelectedValue= your value.
    Sunday, February 23, 2014 11:12 PM
  • User-1367363180 posted

    While I was trying to set selected value in code behind, I deleted SelectedValue='<%# Bind("CColorID") %>' and got rid of error.

    <asp:DropDownList ID="DdlColorName1" runat="server"
                                DataTextField="CColoName"
                                DataValueField="CColoID"
                                SelectMethod="DdlColorName_GetData"
                                >
                            </asp:DropDownList>

    Coult it be possible to start from there?

    Here's a pic of actual running program:

    Monday, February 24, 2014 5:16 PM
  • User22205941 posted

    What type of error you get? Can you post as text?

    Tuesday, February 25, 2014 7:09 AM
  • User-510141866 posted

    Hi  stevana,

     Before bind the Gridview , we need to fill the dropdown list in gridview using  FindControl() method.

    Get all values of colour table and bind it to dropdownlist using findcontrol method.

    then bind the gridview.

    Tuesday, February 25, 2014 7:29 AM
  • User-1367363180 posted

    Reply to Tamizhiniyan Natarajan:

    'DdlColorName1' has a SelectedValue which is invalid because it does not exist in the list of items.
    Parameter name: value

    Tuesday, February 25, 2014 12:05 PM
  • User-1818759697 posted

    Hi,

    For this situation, the value coming from <%# Bind("CColorID") %>, which is passed to the SelectedValue property, does not match an item in it's collection.  Most likely causes:

    • DropDownList has no items because the evaluation happens before the list gets bound
    • The list is bound but is missing this particular value
    • The value returned could be null

    Besides, you could refer to the following links for more information:

    http://stackoverflow.com/questions/14654220/has-a-selectedvalue-which-is-invalid-because-it-does-not-exist-in-the-list-of-it

    http://aspsnippets.com/Articles/Populate-DropDownList-with-Selected-Value-in-EditItemTemplate-of-GridView-in-ASPNet.aspx

    Regards

    Thursday, February 27, 2014 3:18 AM
  • User-1367363180 posted

    Sorry, but I need additional help on this.

    I was able to get exact colors which are missing with DDL and GetData Method as I've shown in earlier posts.

    Here is DDL:

    <asp:DropDownList ID="DdlColorName1" runat="server"
                                DataTextField="CColoName"
                                DataValueField="CColoID"
                                SelectMethod="DdlColorName_GetData"
                                >

    Here is GetData method:

    public IQueryable DdlColorName_GetData()
        {
            int chosen_pid = int.Parse(Request.QueryString["pid"]);
    
            // var result = db.CColoes;
            var result =
            (from c in db.CColoes
             where
               !
                 (from u in db.Uses_Color
                  where
                     u.ProductID == chosen_pid
                  select new
                  {
                      u.CColoID,
    
                  }).Contains(new { CColoID = c.CColoID })
             select new
             {
                 c.CColoID,
                 c.CColoName
             });
    
            return result.AsQueryable();
        }

    When I click on Update button, I need somehow to extract what has been selected in DDL in UpdateItem method. Unfortunately, ctext variable which represents SelectedValue from DDL, is always null. Any help on this one, please?

    public void GridView1_UpdateItem(Uses_Color uc)
        {
            try
            {
                DropDownList chosen_color = (DropDownList)GridView1.FindControl("DropDownList1");
                string ctext = chosen_color.SelectedValue.ToString();
            }
            catch (Exception ex)
            {
                Response.Write(ex.Message);
            }
            finally { }
        }

    Tuesday, March 4, 2014 4:37 PM
  • User-1818759697 posted

    Hi,

    DropDownList chosen_color = (DropDownList)GridView1.FindControl("DropDownList1");

    For this situation, the above codes couldn't get the dropdownlist. And you could refer to the following information:

    GridView is a control which repeats its rows based on the bound data, e.g in practise it creates a set of controls (one row in it) as many times as there are rows in data source. In order to keep IDs of these controls unique, GridView and its rows are naming containers (implement INamingContainer interface). Being a naming container means that a control provides a new naming scope for its child controls by appending it's ID into ID of its own naming container.

    And being a naming container means that in order to look for a control with its local ID (not the unique id) you need to run FindControl against its naming container. In this case you run it againt GridView but GridView is not the direct naming container (or parent) of the HiddenField but the corresponding row (GridViewRow) is.

    (DropDownList)GridView1.Rows[i].FindControl("DropDownList1")

    Besides, you could also refer to:

    http://www.codeproject.com/Articles/12021/Accessing-the-different-controls-inside-a-GridView

    Regards

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Tuesday, March 4, 2014 8:50 PM
  • User-1367363180 posted

    Sorry for beeing late with reply.

    Actually, with suggested change in code bellow:

    public void GridView1_UpdateItem(Uses_Color uc)
        {
            try
            {
    
                DropDownList chosen_color = (DropDownList)GridView1.Rows[0].FindControl("DropDownList1"); // I have only one row at the moment for per product
                uc.CColoID = Convert.ToInt16(chosen_color.SelectedValue.ToString());
            
                db.Entry(uc).State = EntityState.Modified;
                db.SaveChanges();
    
            }
            catch (Exception ex)
            {
                Response.Write(ex.Message);
            }
            finally { }
        }
    
    }

    I get next error:

    Store update, insert, or delete statement affected an unexpected number of rows (0). Entities may have been modified or deleted since entities were loaded. Refresh ObjectStateManager entries.

    When troubleshooting, I find that uc.CColoID has the correctly chosen ID in DropDownList1.

    Thanks again for help, kind regards
     

    Saturday, April 19, 2014 5:43 PM