Asp.net user control item command event not firing - asp.net

I have a page which has user control in it.
The page data grid bound columns are populated from user control (user control has a data grid whose items are in the form of item templates).
This user control has a column which contains edit save cancel buttons.
The user control also has other columns which are check boxes,drop down lists inside (item templates).
I am using item command event and when Edit link is clicked it should get current row value of a column called "Description" and for testing purpose I am getting this value into a text box called 'Tdval'.
The Tdval textbox is empty and when I check break point it looks like item command event is not all firing( as break point is not hit).
I don't understand why.
The page is not posted back when I click Edit link.
Its just the user control link button. Please help me.
Excuse any mistakes and am new to this. Thanks in advance.
HTML:
<tr>
<asp:datagrid ID="dgDetails"
EnableViewState="true"
runat="server"
onItemCommand="dgDetails_ItemCommand"
allowpaging="false"
allowcustompaging="false"
autogeneratecolumns="false"
allowsorting="true"
backcolor="white"
Width="100%"
horizontalalign="center"
Font-bold="true"
Font-Names="Verdana"
Font-size="7pt"
BorderColor="Silver" >
<columns>
<asp:BoundColumn DataField="ID" Visible="true"></asp:BoundColumn>
<asp:TemplateColumn HeaderStyle-HorizontalAlign="Center"
ItemStyle-HorizontalAlign="Left"
HeaderText="Description"
HeaderStyle-Width="320px" >
<ItemTemplate>
<asp:Label ID="lblDescription" runat="server">
<%#DataBinder.Eval(Container.DataItem, "Description")%>
</asp:Label>
</ItemTemplate>
</asp:TemplateColumn>
<asp:TemplateColumn HeaderStyle-HorizontalAlign="Left"
ItemStyle-HorizontalAlign="Left"
HeaderText="Pr."
HeaderStyle-Width="20px" >
<ItemTemplate>
<asp:CheckBox ID="chkPrimary" runat="server" Enableviewstate="true">
</asp:CheckBox>
</ItemTemplate>
<asp:LinkButton ID="lnkEdit" runat="server"
CommandName="Edit">Edit
</asp:LinkButton>
</columns>
</asp:datagrid>
</tr>
<tr>
<td>
<asp:TextBox ID="Tdval" runat="server"> </asp:TextBox>
</td>
Code Behind:
Public Sub dgDetails_ItemCommand(ByVal source As Object, ByVal e As System.Web.UI.WebControls.DataGridCommandEventArgs) Handles dgDetails.ItemCommand
Select Case e.CommandName
Case "Edit"
Dim intRow As Integer
intRow = e.Item.ItemIndex
Dim dgRow As DataGridItem
dgRow=dgDetails.Items.Item(intRow)
Dim val As String
val=Ctype(dgRow.Cells(0).Text, String) (Description column)
Tdval.Text=val.Text
End Select
End Sub

I thing u can call bindGrid() method after check page.ispostback on page_load like this :
protected void Page_Load(object sender, EventArgs e)
{
if (Page.IsPostBack)
{
return;
}
BindGrid();
}

Related

How to code a button click event in a GridView that returns a value from its row in the GridView

Apologies for the slightly convoluted title.
Basically, I have a project where I have a database connected to it. I'm displaying some of the contents of the database using a GridView, which is all up and running, but the way I'm designing the page I need to be able to click a button in each row that in essence exports the value of one of the cells in the row to a subroutine.
I've tried googling it quite a bit and trying related things I found here, but nothing I could find would function like I would like it to.
The relevant code is below.
Markup:
<asp:GridView ID="Staffgv" runat="server" AutoGenerateColumns="false" OnRowCommand="Staffgv_RowCommand" AllowPaging="true" PageSize="20" OnPageIndexChanging="Staffgv_PageIndexChanging" BackColor="#f9f9f9" CssClass="gvStyle" >
<Columns>
<asp:TemplateField HeaderText="Start" InsertVisible="False" SortExpression="DateTimeStart">
<HeaderStyle Width="70px" CssClass="hdrGvStart"/>
<ItemTemplate>
<asp:Label ID="lblDateTimeStart" runat="server" Text='<%# Bind("DateTimeStart", "{0:t}") %>'></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="Finish" SortExpression="DateTimeEnd">
<HeaderStyle Width="70px" CssClass="hdrGvFinish"/>
<ItemTemplate>
<asp:Label ID="lblDateTimeEnd" runat="server" Text='<%# Bind("DateTimeEnd", "{0:t}") %>'></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="Forename" SortExpression="Forename">
<HeaderStyle Width="140px" CssClass="hdrGvForename"/>
<ItemTemplate>
<asp:Label ID="lblForename" runat="server" Text='<%# Bind("Forename") %>'></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="Surname" SortExpression="Surname">
<HeaderStyle Width="140px" CssClass="hdrGvSurname"/>
<ItemTemplate>
<asp:Label ID="lblSurname" runat="server" Text='<%# Bind("Surname") %>'></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderStyle CssClass="gvHeaderEdit" />
<ItemTemplate>
<asp:Button ID="Btnapptid" runat="server" Text="" CssClass="btnGVEdit" CommandName="FillStaffTables" CommandArgument="<%# CType(Container,GridViewRow).RowIndex %>"/>
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
And the relevant VB code:
Private Sub Staffgv_RowDataBound(sender As Object, e As GridViewRowEventArgs) Handles Staffgv.RowDataBound
Select Case e.Row.RowType
Case DataControlRowType.DataRow
Dim row = DirectCast(e.Row.DataItem, DataRowView)
Dim apptid As Integer = Integer.Parse(row("AppointmentID").ToString)
Dim Btnapptid = DirectCast(e.Row.FindControl("Btnapptid"), Button)
'Btnapptid.Text = apptid
Btnapptid.ToolTip = apptid
End Select
End Sub
Protected Sub Staffgv_RowCommand(ByVal sender As Object, e As GridViewCommandEventArgs)
If (e.CommandName = "FillStaffTables") Then
Dim index As Integer = Convert.ToInt32(e.CommandArgument)
lblTxtTester.Text = "AppointmentID"
TextboxTester.Text = index
End If
End Sub
If anyone would like more code like the code used to fill the GridView I'll post it, just didn't want to post too much irrelevant code.
Thanks
Solution A
When you only want 1 value from the gridview row when the button is clicked.
You could simply utilize the CommandArgument of your button (Btnapptid). This assumes that you don't need the gridview row index for when the button is clicked. If you do need this, then please see Solution B, otherwise continue here.
First, you'd need to modify your button's CommandArgument in the aspx page
ASPX
<asp:Button ID="Btnapptid" runat="server" Text="" CssClass="btnGVEdit"
CommandName="FillStaffTables" CommandArgument='<%# Bind("AppointmentID") %>'/>
Then you should be able to grab the AppointmentID like this
VB (inside Staffgv_RowCommand())
If (e.CommandName = "FillStaffTables") Then
txtAppointmentID.Text = e.CommandArgument
End If
Solution B
When you need more than 1 value from the gridview row when the button is clicked
Please note that this solution requires a couple changes on your end
Create an additional control (in the gridview) which should hold the value that you want to get when the button is clicked.
Fill said control with the value you want (via Bind() in the UI or in RowDataBound in the codebehind).
Next, in your RowCommand you'd be able to grab the newly created control with the help of the index variable (from your example) like so
Staffgv.Rows(index).FindControl("YOUR_CONTROLS_ID")
Example
Say that you decide to create a HiddenField control in which to store the value from your database
ASPX (hidden field should be somewhere inside the gridview - right under Btnapptid should be fine)
<asp:HiddenField ID="hfMyControl" runat="server" Visible="False"
Value='<%# Bind("SOME_DB_COLUMN") %>'/>
VB (inside Staffgv_RowCommand())
Dim hfMyControl As HiddenField = _
DirectCast(Staffgv.Rows(index).FindControl("hfMyControl"), HiddenField)
Then simply use the value of hfMyControl
hfMyControl.Value
You could also repeat all this using multiple controls in order to potentially access multiple DB values stored in controls in the gridview.

What is the preferred way to bind a radcombobox in a radgrid?

I've seen a lot of questions close to this but haven't found my answer. Here's the key points of my example below:
RadGrid has a GridTemplateColumn
GridTemplateColumn has a RadComboBox in it's EditItemTemplate
RadComboBox is bound to an ObjectDataSource and had a RequiredFieldValidator
SelectedValue='<%#Bind("SomeValue")%>' seems to work but causes validation issues
Setting RadComboBox1.SelectedValue in ItemDataBound event seems to be working
Is binding with code in the ItemDataBound the best way to do this? What's interesting is that setting SelectedValue='<%#Bind("SomeValue")%>' on the aspx page has the SelectedValue already set by the time I get the ItemDataBound but for some reason, a RequiredFieldValidator fails in edit mode when doing this unless I set the value AGAIN in ItemDataBound. Below is a stripped down version of my code.
<telerik:RadGrid ID="rgTasks" runat="server" AllowAutomaticInserts="false" AllowAutomaticUpdates="false" AutoGenerateColumns="False">
<MasterTableView DataKeyNames="Id">
<CommandItemSettings ShowRefreshButton="False"></CommandItemSettings>
<Columns>
<telerik:GridEditCommandColumn ButtonType="ImageButton" UniqueName="EditCommandColumn"></telerik:GridEditCommandColumn>
<telerik:GridBoundColumn DataField="Id" ReadOnly="True" UniqueName="Id" DataType="System.Int32" Visible="false"></telerik:GridBoundColumn>
<telerik:GridTemplateColumn UniqueName="TaskTypeId" HeaderText="Task" DataField="TaskTypeId" DefaultInsertValue="">
<ItemTemplate>
<%# Eval("TaskType.Name")%>
</ItemTemplate>
<EditItemTemplate>
<telerik:RadComboBox ID="rcbTaskTypeId" runat="server" EmptyMessage="Select TaskType..."
DataSourceID="odsTaskTypes" DataValueField="Id" DataTextField="Name" SelectedValue='<%#Bind("TaskTypeId")%>'>
</telerik:RadComboBox>
<asp:RequiredFieldValidator ID="rfvTaskTypeId" runat="server" ControlToValidate="rcbTaskTypeId" ErrorMessage="Task Type is required" Display="Dynamic"></asp:RequiredFieldValidator>
</EditItemTemplate>
</telerik:GridTemplateColumn>
</Columns>
</MasterTableView>
</telerik:RadGrid>
<asp:ObjectDataSource ID="odsTaskTypes" runat="server" SelectMethod="GetTaskTypes" TypeName="CAPAModel.CAPARepo.DataRepo"></asp:ObjectDataSource>
Protected Sub rgTasks_ItemDataBound(sender As Object, e As GridItemEventArgs) Handles rgTasks.ItemDataBound
If ((TypeOf e.Item Is GridEditableItem) AndAlso e.Item.IsInEditMode) Then
If Not String.IsNullOrEmpty(DataBinder.Eval(e.Item.DataItem, "TaskTypeId").ToString) Then
Dim rcbTaskTypeId As RadComboBox = e.Item.FindControl("rcbTaskTypeId")
rcbTaskTypeId.SelectedValue = DataBinder.Eval(e.Item.DataItem, "TaskTypeId")
End If
End If
End Sub
I saw some relevant questions but am looking for an explanation of how I SHOULD be doing this and why. Thanks.
The error occured because you have set two different datafield as DataValueField and SelectedValue. I suppose you want to show another field as selected other than data in DataValueField and DataTextField. Please take a look into the following code snippet.
ASPX:
<telerik:GridTemplateColumn DataField="test" FilterControlAltText="Filter RegistryValue column" HeaderText="test" SortExpression="test" UniqueName="test">
<EditItemTemplate>
<telerik:RadComboBox ID="RadComboBox1" Runat="server" DataSourceID="odsTaskTypes" DataTextField="Name" DataValueField="Id" >
</telerik:RadComboBox>
</EditItemTemplate>
<ItemTemplate>
<asp:Label ID="RegistryValueLabel" runat="server" Text='<%# Eval("RegistryValue") %>'></asp:Label>
</ItemTemplate>
</telerik:GridTemplateColumn>
C#:
protected void gridiew1_ItemDataBound(object sender, GridItemEventArgs e)
{
if (e.Item is GridEditableItem && e.Item.IsInEditMode)
{
GridEditableItem editItem = (GridEditableItem)e.Item;
RadComboBox combo = (RadComboBox)editItem.FindControl("RadComboBox1");
combo.SelectedItem.Text = (string)DataBinder.Eval(e.Item.DataItem, "TaskTypeId").ToString();
}
}
So I've gone back and forth with Telerik support on this and their suggestion was to just do it the way I'm doing it. Considering that I'm binding the control in the code, I can probably get rid of SelectedValue='<%#Bind("TaskTypeId")%>' like so:
<telerik:RadComboBox ID="rcbTaskTypeId" runat="server"
DataSourceID="odsTaskTypes" DataValueField="Id" DataTextField="Name" >
</telerik:RadComboBox>
...and then just keep the code as is:
Protected Sub rgTasks_ItemDataBound(sender As Object, e As GridItemEventArgs) Handles rgTasks.ItemDataBound
If ((TypeOf e.Item Is GridEditableItem) AndAlso e.Item.IsInEditMode) Then
If Not String.IsNullOrEmpty(DataBinder.Eval(e.Item.DataItem, "TaskTypeId").ToString) Then
Dim rcbTaskTypeId As RadComboBox = e.Item.FindControl("rcbTaskTypeId")
rcbTaskTypeId.SelectedValue = DataBinder.Eval(e.Item.DataItem, "TaskTypeId")
End If
End If
End Sub

ASP.NET Gridview button onclick not firing

Hi all I have a simpe ASP button inside a grid. But the onclick event doesn't seem to fire. Where did I go wrong?
Here's the first line of my aspx page.
<%# Page Title="Trainer Data" Language="vb" AutoEventWireup="false" MasterPageFile="~/Site.Master" CodeFile="TrainerData.aspx.vb" Inherits="TrainerData"%>
And the button inside my gridview..
<asp:GridView ID ="gvExecSummary" runat="server" CssClass="gridview" AllowSorting="false" AllowPaging="false" AutoGenerateColumns="false" Width="98%" >
<RowStyle Height="22px" />
<AlternatingRowStyle Height="22px" CssClass="bg" BackColor="LightGray"/>
<HeaderStyle Height="22px" BackColor="#4b6c9e" Font-Bold="true"/>
<Columns>
<asp:TemplateField HeaderStyle-HorizontalAlign="Left" HeaderStyle-Width="5%" HeaderText="Action">
<ItemTemplate>
<asp:Button ID="btnExecutiveGenerate" runat="server" Text="Generate" OnClientClick="btnExecutiveGenerate_Click" />
</ItemTemplate>
</asp:TemplateField>
P.S. I tried even onclick but it doesn't work either.
EDIT: My code for server side.
Protected Sub btnExecutiveGenerate_Click(sender As Object, e As EventArgs)
Dim gvrow As GridViewRow = CType(CType(sender, Control).Parent.Parent, GridViewRow)
Dim lblSchoolId As System.Web.UI.WebControls.Label = gvrow.FindControl("lblSchoolMasterID")
Dim lblFacultyId As System.Web.UI.WebControls.Label = gvrow.FindControl("lblFacultyMasterID")
Dim btnExecutiveGenerate As System.Web.UI.WebControls.Button = gvrow.FindControl("btnExecutiveGenerate")
PDF_Creation_Executive(Val(lblSchoolId.Text), Val(lblFacultyId.Text))
End Sub
Use Command Argumnet,
<asp:TemplateField>
<ItemTemplate>
<asp:Button ID="AddButton" runat="server"
CommandName="AddToCart"
CommandArgument="<%# CType(Container,GridViewRow).RowIndex %>"
Text="Add to Cart" />
</ItemTemplate>
</asp:TemplateField>
add code page side
Protected Sub GridView1_RowCommand(ByVal sender As Object, _ByVal e As System.Web.UI.WebControls.GridViewCommandEventArgs)
If (e.CommandName = "AddToCart") Then
' Retrieve the row index stored in the CommandArgument property.
Dim index As Integer = Convert.ToInt32(e.CommandArgument)
' Retrieve the row that contains the button
' from the Rows collection.
Dim row As GridViewRow = GridView1.Rows(index)
' Add code here to add the item to the shopping cart.
End If
End Sub
You need to handle the button click event of Gridview in RowCommand event
NOTE: Please see the CommandName & CommandArgument properties added to the button.
<asp:GridView ID ="gvExecSummary" runat="server" CssClass="gridview" AllowSorting="false" AllowPaging="false" AutoGenerateColumns="false" Width="98%" >
<RowStyle Height="22px" OnRowCommand="gvExecSummary_RowCommand" />
<AlternatingRowStyle Height="22px" CssClass="bg" BackColor="LightGray"/>
<HeaderStyle Height="22px" BackColor="#4b6c9e" Font-Bold="true"/>
<Columns>
<asp:TemplateField HeaderStyle-HorizontalAlign="Left" HeaderStyle-Width="5%" HeaderText="Action">
<ItemTemplate>
<asp:Button ID="btnExecutiveGenerate" runat="server" Text="Generate" CommandName="GenerateExecutive" CommandArgument="<%#((GridViewRow)Container).RowIndex %>" />
</ItemTemplate>
</asp:TemplateField>
And and RowCommand event will be..
protected void gvExecSummary_RowCommand(object sender, GridViewCommandEventArgs e)
{
if (e.CommandName == "GenerateExecutive")
{
// button click code goes here
}
}
change OnClientClick event to OnClick if btnExecutiveGenerate_Click is vb.net event handler
<asp:Button ID="btnExecutiveGenerate" runat="server" Text="Generate"
OnClick="btnExecutiveGenerate_Click"/>
OnClientClick event use to execute client-side script, if you have given OnClientClick event with OnClick event, then if OnClientClick return true only it will call OnClick event.
so make sure you are returning true or false from OnClientClick event if you using it.
note that if you are loading data in page laod, do as below
Sub Page_Load
If Not IsPostBack
LoadGridViewData()
End If
End Sub
This may help someone, but I was experiencing edit buttons not firing the event within rows (and not footer).
The cause was a gridview containing a label, which had the same ID as one elsewhere on the page.
Seemingly this did not cause problems for the footer row, which did not contain any such labels.
I hope this helps someone.

ASP.net GridView: get LinkItem's row

I want to show "Delete" link in GridView to registred users, therefore I am using templateField:
<asp:GridView ID="GridView1" runat="server" AllowSorting="True" OnSorting="GridView_Sort">
<Columns>
<asp:TemplateField HeaderText="Control">
<ItemTemplate>
<asp:LinkButton ID="LinkButton1" runat="server" onClick="deleteEntry()" Text="Delete"></asp:LinkButton>
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
Now in my deleteEntry() function how can I know anything about the row in which "Delete" link was clicked? How to ge for e.g. rowindex?
You could approach this slightly different. You see, when a control is placed inside a gridview, any event raised from that control raises also the RowCommand on the GridView.
To get what you want you could then add both CommandName and CommandArgument to your LinkButton and then catch it in the GridView's RowCommand.
<asp:LinkButton id="LinkButton1" runat="server" commandName="LinkButtonClicked" commandArgument='Eval("myObjectID")' />
where myObjectID is the name of the ID column of your object you bind the grid to.
Then
void GridView1_RowCommand( object sender, GridViewCommandEventArgs e )
{
if ( e.CommandName == "LinkButtonClicked" )
{
string id = e.CommandArgument; // this is the ID of the clicked item
}
}

How to access a button inside a listview? specifically using the button_click to carry out an action

I have this simplified code:
<asp:ListView ID="ListView1" runat="server" DataSourceID="sqldatasource1">
<ItemTemplate>
<asp:Button ID="ButtonTest" runat="server" BackColor="Silver" Text="Add to Cart" />
</ItemTemplate>
</asp:ListView>
I am trying to run some code behind the button but I don't know how. I can't access it within the listview. Not that this is important, but im trying to get information from the current listview(the product ID) and pass it to the next page.
Anybody know how to approach this, with the exact code? Thanks!
You want the ItemCommand event. You would give your button a command name, a command argument (if you want), then listen for the ItemCommand event on the ListView
<asp:ListView ID="ListView1" runat="server" OnItemCommand="DoTheCommand" DataSourceID="sqldatasource1">
<ItemTemplate>
<asp:Button CommandName="Foo" CommandArgument='<%#Eval("SomeDataBoundProperty")%>' ID="ButtonTest" runat="server" BackColor="Silver" Text="Add to Cart" />
</ItemTemplate>
</asp:ListView>
And in your code behind:
void DoTheCommand(object sender, ListViewCommandEventArgs e) {
string commandName = e.CommandName;
object commandArg = e.CommandArgument;
ListViewItem selectedItem = e.Item;
int dataItemIndex = selectedItem.DataItemIndex;
if (commandName == "Foo") {
//and so on
}
}
U can use ListView's ItemCommand Event in codebehind with commandName and command argument set in aspx.
<asp:ListView ID="ListView1" runat="server" DataSourceID="sqldatasource1">
<ItemTemplate>
<asp:Button ID="ButtonAdd" runat="server" BackColor="Silver" CommandName="cAdd" CommandArgument= '<%# Eval("ProductId") %>' Text="Add to Cart" />
Protected Sub ListView1_OnItemCommand(ByVal sender As Object, _
ByVal e As ListViewCommandEventArgs) Handles Listview1.ItemCommand
If String.Equals(e.CommandName, "cAdd") Then
Dim ProductId as integer = e.CommandArgument
'your code
End If
End Sub

Resources