skip to Main Content

I have dynamically created a dropdown and everything is fine once the page loads. There is a button in each row of the gridview next to the dropdown. This button updates the table for the selected item. I’m getting my key, but I"m getting object reference not set to an instance. Is that because the id of the dropdown control is burried in ct100 stuff?

Dim ddluid As String = CType(FindControl("Ddlos"), DropDownList).SelectedItem.Value

This here I have swiped from the source of the page:

<select name="ctl00$ContentPlaceHolder2$GridView1$ctl02$Ddlos" id="ctl00_ContentPlaceHolder2_GridView1_ctl02_Ddlos">
                <option value="0">-Select-</option>
                <option value="503841a3-c615-4e4d-8cf5-20fbddbf7a7f">John Doe</option>
                <option value="9b38e9cd-f16f-4fdd-a82e-501c866f9e45">Sam Beacon</option>
                <option value="fe6158c5-a549-443f-b5ff-c011937db1d7">John Doey</option>
                <option value="295e9f85-6ea6-46ec-9c00-c38d64023517">Scot King</option>

 Protected Sub btnsaveinfo(sender As Object, e As EventArgs)
        Dim key As String = ""
        For Each row As GridViewRow In GridView1.Rows
            If row.RowType = DataControlRowType.DataRow Then
                key = GridView1.DataKeys(row.RowIndex).Value.ToString()
                Dim ddluid As String = CType(FindControl("Ddlos"), DropDownList).SelectedItem.Value
                'Dim idvalue As String = ddluid.SelectedValue
                'Dim louid As Guid =
                Dim cn As New SqlConnection(ConfigurationManager.ConnectionStrings("sqlConnectionString").ConnectionString)
                Dim cmdupdate As New SqlCommand("update Profiles SET [loanrepid] = @loanrepid WHERE ApplicantID=@ApplicantID", cn)
                cmdupdate.Parameters.AddWithValue("@loanrepid", "1")
                cmdupdate.Parameters.AddWithValue("@ApplicantID", key)
                cmdupdate.CommandType = System.Data.CommandType.Text
                cmdupdate.Connection = cn
                cn.Open()
                cmdupdate.ExecuteNonQuery()
                cn.Close()
            End If
        Next
        lblresult.Text = " Details Updated Successfully"
        lblresult.Visible = True
    End Sub



          <asp:TemplateField HeaderText="Loan Officer" SortExpression="Loan Officer" ItemStyle-HorizontalAlign="Center">
                <ItemTemplate>
                    <asp:DropDownList ID="Ddlos" runat="server" Visible="false"></asp:DropDownList>
                </ItemTemplate>
            </asp:TemplateField>

2

Answers


  1. Chosen as BEST ANSWER

    thank you for your advice on the problem. Yes, I have it as one button now. I had a couple things there that were causing it to not work. I figure just one button to resave the selections on the page.

     Protected Sub btnsaveinfo_Click(sender As Object, e As EventArgs) Handles btnsaveinfo.Click
            Dim key As String = ""
            For Each grow As GridViewRow In GridView1.Rows
                If grow.RowType = DataControlRowType.DataRow Then
                    key = GridView1.DataKeys(grow.RowIndex).Value.ToString()
                    Dim ddlo As DropDownList = grow.FindControl("Ddlos")
                    Dim selectedlo As String = ddlo.SelectedValue
                    Dim result As Int16 = ddlo.SelectedIndex
                    If result = 0 Then
                        lblresult.Text = "You must select a Loan Officer for each loan"
                        lblresult.ForeColor = Drawing.Color.Red
                        lblresult.Visible = True
                        Exit Sub
                    End If
                    Dim loguid As Guid = Guid.Parse(selectedlo)
                    Dim ddproc As DropDownList = grow.FindControl("ddlprocessor")
                    Dim selectedproc As String = ddproc.SelectedValue
                    Dim cn As New SqlConnection(ConfigurationManager.ConnectionStrings("sqlConnectionString").ConnectionString)
                    Dim cmdupdate As New SqlCommand("update Loanapps SET [loanrepid] = @loanrepid WHERE ApplicantID=@ApplicantID", cn)
                    cmdupdate.Parameters.AddWithValue("@loanrepid", loguid)
                    cmdupdate.Parameters.AddWithValue("@ApplicantID", key)
                    cmdupdate.CommandType = System.Data.CommandType.Text
                    cmdupdate.Connection = cn
                    cn.Open()
                    cmdupdate.ExecuteNonQuery()
                    cn.Close()
                    If ddproc.SelectedIndex <> 0 Then
                        Dim procguid As Guid = Guid.Parse(selectedproc)
                        Dim cmdupdate2 As New SqlCommand("update Loanapps SET [processorid] = @processorid WHERE ApplicantID=@ApplicantID", cn)
                        cmdupdate2.Parameters.AddWithValue("@processorid", procguid)
                        cmdupdate2.Parameters.AddWithValue("@ApplicantID", key)
                        cmdupdate2.CommandType = System.Data.CommandType.Text
                        cmdupdate2.Connection = cn
                        cn.Open()
                        cmdupdate2.ExecuteNonQuery()
                        cn.Close()
                    End If
                End If
            Next
    
    
            ' Response.Redirect("default.aspx")
            lblresult.Text = " Details Updated Successfully"
            lblresult.ForeColor = Drawing.Color.Green
            lblresult.Visible = True
            Page.ClientScript.RegisterStartupScript(Me.GetType(), "alertscript", "<script>$('.TempAlert1').hide(8000);</script>")
        End Sub
    

  2. A a few things.

    You could have the user make all changes, and the below the grid, one save button.

    however, since you have a button on each row, to save the row back to database?

    Then no need exists to loop all rows in the one save button row????

    However, what happens if the user changes several rows – forgets to hit save, and then does hit save? In other words, the user going to be somewhat confused here?

    So, it not clear that clicking on the save button should only save the current row?

    If that is the goal, then we could have say this setup:

            <asp:GridView ID="GHotels" runat="server" AutoGenerateColumns="False"
                DataKeyNames="ID" CssClass="table" Width="50%">
                <Columns>
                    <asp:BoundField DataField="FirstName" HeaderText="FirstName"     />
                    <asp:BoundField DataField="LastName" HeaderText="LastName"       />
                    <asp:BoundField DataField="HotelName" HeaderText="HotelName"     />
                    <asp:BoundField DataField="Description" HeaderText="Description" />
    
                    <asp:TemplateField HeaderText="Rate">
                        <ItemTemplate>
                        <asp:DropDownList ID="cboRank" runat="server"
                            DataValueField="ID"
                            DataTextField="Rating" >
                        </asp:DropDownList>
                        </ItemTemplate>
                    </asp:TemplateField>
    
                    <asp:TemplateField HeaderText="Save" ItemStyle-HorizontalAlign="Center">
                        <ItemTemplate>
                            <asp:Button ID="cmdSave" runat="server" Text="Save" CssClass="btn" Width="60"
                              OnClick="cmdSave_Click"  />                          
                        </ItemTemplate>
                    </asp:TemplateField>
                </Columns>
            </asp:GridView>
    

    And code to load would be:

    Dim rstRank As New DataTable ' to load cbo box
    
    Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
    
        If Not IsPostBack Then
    
            LoadData()
    
        End If
    
    End Sub
    
    Sub LoadData()
    
        ' load combo box data
        rstRank = MyRst("SELECT ID, Rating from tblRating ORDER BY ID")
    
        Dim strSQL As String =
            "SELECT ID, FirstName, LastName, HotelName, Description, Ranking from tblHotels"
    
        GHotels.DataSource = MyRst(strSQL)
        GHotels.DataBind()
    
    End Sub
    
    Function MyRst(strSQL As String) As DataTable
    
        Dim rst As New DataTable
    
        Using conn As New SqlConnection(My.Settings.TEST4)
            Using cmdSQL As New SqlCommand(strSQL, conn)
                conn.Open()
                rst.Load(cmdSQL.ExecuteReader)
            End Using
        End Using
    
        Return rst
    
    End Function
    
    Protected Sub GHotels_RowDataBound(sender As Object, e As GridViewRowEventArgs) Handles GHotels.RowDataBound
    
        If e.Row.RowType = DataControlRowType.DataRow Then
    
            Dim cboRank As DropDownList = e.Row.FindControl("cboRank")
            cboRank.DataSource = rstRank
            cboRank.DataBind()
            ' add blank row
            cboRank.Items.Insert(0, New ListItem("Select", "0"))
    
            Dim v As Object = e.Row.DataItem
            Dim rData As DataRowView = e.Row.DataItem
    
            If Not IsDBNull(rData("Ranking")) Then
                cboRank.SelectedValue = rData("Ranking")
            End If
    
        End If
    
    End Sub
    

    and we now have this:

    enter image description here

    Ok, so the save button – to save the one row?

    this works:

    Protected Sub cmdSave_Click(sender As Object, e As EventArgs)
    
        Dim btn As Button = sender
        Dim gRow As GridViewRow = btn.NamingContainer
    
        Dim cboRank As DropDownList = gRow.FindControl("cboRank")
        Dim strSQL As String = "UPDATE tblHotels SET Ranking = @Rating WHERE ID = @ID"
    
        Using conn As New SqlConnection(My.Settings.TEST4)
            Using cmdSQL As New SqlCommand(strSQL, conn)
                cmdSQL.Parameters.Add("@ID", SqlDbType.Int).Value = GHotels.DataKeys(gRow.RowIndex).Value
                cmdSQL.Parameters.Add("@Rating", SqlDbType.Int).Value = cboRank.SelectedItem.Value
                conn.Open()
                cmdSQL.ExecuteNonQuery()
            End Using
    
        End Using
    
    End Sub
    

    So, as you can see, no real need to loop and save ALL rows, is there?

    I would think that if you want ONE save button?

    Then move the save button OUT of the grid, and then save have this:

            <asp:GridView ID="GHotels" runat="server" AutoGenerateColumns="False"
                DataKeyNames="ID" CssClass="table" Width="50%">
                <Columns>
                    <asp:BoundField DataField="FirstName" HeaderText="FirstName"     />
                    <asp:BoundField DataField="LastName" HeaderText="LastName"       />
                    <asp:BoundField DataField="HotelName" HeaderText="HotelName"     />
                    <asp:BoundField DataField="Description" HeaderText="Description" />
                    <asp:TemplateField HeaderText="Rate">
                        <ItemTemplate>
                        <asp:DropDownList ID="cboRank" runat="server"
                            DataValueField="ID"
                            DataTextField="Rating" >
                        </asp:DropDownList>
                        </ItemTemplate>
                    </asp:TemplateField>
                </Columns>
            </asp:GridView>
            <br />
            <asp:Button ID="cmdSave" runat="server" Text="Save" CssClass="btn" Width="60"
            OnClick="cmdSave_Click"  />                          
    

    And now this:

    enter image description here

    And the one save button (which I think after saving should say navagate to some other page – since we are done). That code to now save all rows, would be:

    Protected Sub cmdSave_Click(sender As Object, e As EventArgs)
    
        Using conn As New SqlConnection(My.Settings.TEST4)
    
            Dim strSQL As String = "UPDATE tblHotels SET Ranking = @Rating WHERE ID = @ID"
    
            conn.Open()
    
            For Each gRow As GridViewRow In GHotels.Rows
    
                Dim cboRank As DropDownList = gRow.FindControl("cboRank")
    
                Using cmdSQL As New SqlCommand(strSQL, conn)
                    cmdSQL.Parameters.Add("@ID", SqlDbType.Int).Value = GHotels.DataKeys(gRow.RowIndex).Value
                    cmdSQL.Parameters.Add("@Rating", SqlDbType.Int).Value = cboRank.SelectedItem.Value
                    cmdSQL.ExecuteNonQuery()
                End Using
            Next
    
        End Using
    
    End Sub
    

    So, again the code is rather simular for saving "all" rows, or just the one row.

    However, we could also drop in a button beside "save" called "un-do" or "cancel"

    So, the above shows how to get the row click – for ONE row save, and the 2nd code shows how do to this for all rows.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search