2

I have a GridView that is populated by a service and I have added a link on each line of this grid so that I may take action when that specific row is clicked. I want to get some of the items in the selected row but even if I add a onSelectedRowChanged event I am not getting that event to fire, just my link.

<asp:GridView ID="gvTransactionHistory" runat="server" 
    AutoGenerateColumns="false"  
    onselectedindexchanging="gvTransactionHistory_SelectedIndexChanging">
    <Columns>
        <asp:TemplateField>
            <ItemTemplate>
                <asp:Label ID="lblAmount" runat="server" Text='<%# Eval("preAuthAmount") %>'></asp:Label>
                <asp:LinkButton runat="server" Text="Assign+" OnClick="btnAssign"></asp:LinkButton>
            </ItemTemplate>
        </asp:TemplateField>
    </Columns>
</asp:GridView>

Here is my btnAssign click event, which works fine...

protected void btnAssign(object sender, EventArgs e)
{
    Response.Write("Works!");
}

I added this to see if I could trigger this event but I am not really changing index so what I need help with is understanding what event I can tie into that will allow me to click my link button, and get the values from THAT row.

protected void gvTransactionHistory_SelectedIndexChanging(object sender, System.Web.UI.WebControls.GridViewSelectEventArgs e)
{
    var amount = gvTransactionHistory.SelectedRow.Cells[3].Text;
    Response.Write(amount);
}

2 Answers 2

4

To use the btnAssign click event handler to get the row, then you need to get the NamingContainer (read: parent) of the button that was clicked, like this:

protected void btnAssign(object sender, EventArgs e)
{
    GridViewRow theClickedRow = ((LinkButton)sender).NamingContainer as GridViewRow;

    // Check to make sure the clicked row could be found before using it
    if(theClickedRow != null)
    {
        // Find the amount label control
        Label theAmountLabel = theClickedRow.FindControl("lblAmount") as Label;

        // Again, make sure we actually have something before using it
        if(theAmountLabel != null)
        {
            // Get the actual label's text here
            string theAmountLabelText = theAmountLabel.Text;
        }
    }
}
Sign up to request clarification or add additional context in comments.

2 Comments

Karl, that got me the row but when I try to do something like get the field, for example, var amount = theClickedRow.Cells[0].Text; I get empty text despite the data being rendered. I like this approach but I guess I am missing something....
@user2146538 - Use FindControl() to get to the server control, see updated answer.
1

I know the question has already been answered, but I figured I'd give an alternate option.

You can always add attributes to server controls, and just pull them later.

For example, I can add the preAuthAmount to the link button as an attribute named "preAuthAmount".

<asp:Label ID="lblAmount" runat="server" Text='<%# Eval("preAuthAmount") %>'></asp:Label>
<asp:LinkButton runat="server" Text="Assign+" preAuthAmount='<%# Eval("preAuthAmount") %>' itemID='<%# Eval("itemID") %>' OnClick="btnAssign"></asp:LinkButton>

Then just pull the attribute in the click event

protected void btnAssign(object sender, EventArgs e)
{
    string preAuthAmount= ((LinkButton)sender).Attributes["preAuthAmount"];
    string itemID= ((LinkButton)sender).Attributes["itemID"];
}

It's a lot less code and pretty easy to read.

A third option would be to use datakeys

In the markup of the gridview, add all the fields you want to be able to access to the gridview.

<asp:GridView ID="gvTransactionHistory" runat="server" 
    AutoGenerateColumns="false"  
    onselectedindexchanging="gvTransactionHistory_SelectedIndexChanging" 
    DataKeyNames="ID, preAuthAmount, AnyField">

These datakeys can be accessed in the code behind with the row index

protected void btnAssign(object sender, EventArgs e)
{

    var rowIndex = (((LinkButton)sender).NamingContainer as GridViewRow).RowIndex;
    var id = gvTransactionHistory.DataKeys[rowIndwx].Values["ID"];
    var preAuthAmount = gvTransactionHistory.DataKeys[rowIndwx].Values["preAuthAmount"];
}

The issue with the other answer is that it's a bit unstable. The "findcontrol" method only looks for direct descendants, and may not always work.

3 Comments

Javalsu, also a good suggestion, however, I want to access more than one field in the row. I limited my sample question to one item for simplicity.
There's no limit to the number of attributes you can add. You can add as many fields as you want.
I also added a third option. The findcontrol option works, but it's a bit wonky and can cause issues.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.