Checkbox in TemplateField in Gridview loses checked on postback - c#

I have a gridview with a template field. In that template field is a checkbox. I have a submit button outside of the gridview to assign the records that were checked. On the postback no checkboxes register as being checked. Here is my Code:
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:CheckBox ID="cb" Checked="false" runat="server" />
<asp:Label ID="lblCFID" runat="server" Visible="false" Text='<%# Eval("ID") %>' />
</ItemTemplate>
</asp:TemplateField>
<asp:BoundField HeaderStyle-HorizontalAlign="Center" DataField="Name" HeaderText="Name" />
<asp:BoundField HeaderStyle-HorizontalAlign="Center" DataField="DOB" HeaderText="Date of Birth" />
<asp:BoundField HeaderStyle-HorizontalAlign="Center" HeaderText="Gender" DataField="Gender" />
<asp:BoundField HeaderStyle-HorizontalAlign="Center" HeaderText="Status" DataField="Status" />
<asp:BoundField HeaderStyle-HorizontalAlign="Center" HeaderText="Plan Name" DataField="PlanName" />
<asp:BoundField HeaderStyle-HorizontalAlign="Center" HeaderText="Type" DataField="ControlType" />
<asp:BoundField HeaderStyle-HorizontalAlign="Center" HeaderText="Date of Service" dataformatstring="{0:MMMM d, yyyy}" htmlencode="false" DataField="DateofService" />
</Columns>
protected void AssignRecords(object sender, EventArgs e)
{
int Rows = gvASH.Rows.Count;
for (int i = 0; i < Rows; i++)
{
//CheckBoxField cb = ((CheckBoxField)gvASH.Rows[i].Cells[1]).;
CheckBox cb = (CheckBox)gvASH.Rows[i].Cells[0].FindControl("cb");
Label lblID = (Label)gvASH.Rows[i].Cells[0].FindControl("lblCFID");
if (cb.Checked == true)
{
string ID = lblID.Text;
//Assign Code
}
}
}
I have a breakpoint set on the string ID = lblID.Text; but it never finds any that are checked.

I think what you are missing is, when you click on the button and your page is postback, you rebinding to gridview, you need to bind in this condition like
if (!Page.IsPostBack)
{
GridView1.DataSourceID = "yourDatasourceID";
GridView1.DataBind();
}

On a postback, the contents of the GridView are re-created from the postback Viewstate data between page_init and page_load. Perhaps try examining your Gridview in page_load to see what's there.

set the autopostback attribute of Checkbox
AutoPostBack="true"

Related

C# GridViewRow FindControl get/pass values

I have an asp:linkbutton. When it's pressed I want to get a list of DetailID's based on which of the checkboxes in my GridView are checked. I have a lblTesting to see the list of DetailID's that I'm generating. My goal is to get a list of DetailID's that I pass to an edit page.
I have looked at several examples on Stack Overflow but I cannot get any value other than the checkbox is checked.
Here is the link I have at the top of my page:
<span style="float:right;"><asp:Linkbutton ID="getURLLink" runat="server" Text="Edit Die Detail" OnClick="GetLink"></asp:Linkbutton></span>
<asp:Label runat="server" ID="lblTesting"></asp:Label>
Here is my GridView:
<asp:GridView ID="DieListDetailGridView" runat="server" AutoGenerateColumns="false" OnRowDataBound="DieListDetailGridView_RowDataBound" DataKeyNames="DieID" HeaderStyle-HorizontalAlign="Center" HorizontalAlign="Center" ForeColor="#333333" GridLines="Both">
<RowStyle BackColor="#F5F5DC" />
<AlternatingRowStyle BackColor = "White" ForeColor="#284775" />
<Columns>
<asp:TemplateField HeaderText="Edit" HeaderStyle-HorizontalAlign="Center">
<ItemTemplate>
<asp:CheckBox ID="chkBox" runat="server" />
</ItemTemplate>
</asp:TemplateField>
<asp:BoundField DataField="DieNum" HeaderText="Die Number" />
<asp:BoundField DataField="DieID" HeaderText="Die ID" Visible="false" />
<asp:BoundField DataField="DetailID" HeaderText="Detail ID" Visible="false" />
<asp:HyperLinkField DataTextField="DetailNum" HeaderText="Detail Number" DataNavigateUrlFields="DetailID" DataNavigateUrlFormatString="~/Tooling/DieDetail.aspx?DetailID={0}" />
<asp:BoundField DataField="Description" HeaderText="Description" />
<asp:BoundField DataField="MaterialType" HeaderText="Material Type" />
<asp:BoundField DataField="Hardness" HeaderText="Hardness" />
<asp:BoundField DataField="MinSpares" HeaderText="Min Spares" />
<asp:BoundField DataField="MaxSpares" HeaderText="Max Spares" />
<asp:BoundField DataField="CurrentSpares" HeaderText="Current Spares" />
<asp:BoundField DataField="DetailNotes" HeaderText="Detail Notes" />
</Columns>
</asp:GridView>
And my GetLink function:
protected void GetLink(object sender, EventArgs e)
{
// start off empty
string DetailIDList = "";
foreach (GridViewRow row in DieListDetailGridView.Rows) {
if (row.RowType == DataControlRowType.DataRow)
{
CheckBox chkBox = (row.Cells[0].FindControl("chkBox") as CheckBox);
string DetailID = row.Cells[3].Text;
if (chkBox.Checked)
{
DetailIDList = DetailIDList + DetailID + ",";
}
}
}
// Remove the last , from the list
DetailIDList = DetailIDList.Remove(DetailIDList.Length - 1, 1);
// comma delimeted list of checked Detail ID's
lblTesting.Text = DetailIDList;
//Response.Redirect("~/Tooling/DieDetail.aspx?DetailIDList=");
}
I can't figure out why my DetailID is empty.
I've tried doing row.Cells[0].FindControl("DetailID") but that also didn't work.
What I am expecting to get from the DetailID are integers like "28925", "16423" etc.
I was asked to not show the column on the page, which is why visible = false. I still need to reference the ID to pass it to the edit page. I need to do the same edit to multiple Detail ID's.
What am I doing wrong?
The answer to having a list of ID's even though the datafield is set to not be visible was found on another StackOverflow question: ASP.NET: GridView value set to null when column is not visible
The answer was to remove the "Visible=false" from the GridView and on each row created (after the column has the data added for the row) make it not visible.
This code fixed my issue:
protected void DieListDetailGridView_RowCreated(object sender, GridViewRowEventArgs e)
{
e.Row.Cells[2].Visible = false;
e.Row.Cells[3].Visible = false;
}

Showing and hiding of gridview button based on the value of a cell in the same row

I have a gridview in my ASP.NET. in my gridview columns, i want the button on each row to show or hide if the value of a cell is the same cell is empty or null. for example, i want a button to show on each row that has Signout_Time as null or empty. i have written the code below. the issue i'm having is that the codes works in an opposite way. Buttons are showed on the rows with "Signout_Time" while the button on rows without a value for "Signout_Time" visibility becomes false. it shouldn't be so. I have also tried changing my if conditions, it still didnt work
protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e) {
switch (e.Row.RowType) {
case DataControlRowType.DataRow:
DataRowView myDataRowView = (DataRowView)e.Row.DataItem;
if (String.IsNullOrEmpty(myDataRowView["Signout_Time"].ToString())) {
Button status = (Button)e.Row.FindControl("out");
if (status != null) {
status.Visible = true;
}
}
break
}
}
<Columns>
<asp:BoundField HeaderText="S/N" DataField="SN" />
<asp:BoundField HeaderText="First Name" DataField="FirstName" />
<asp:BoundField HeaderText="Address" DataField="Address" />
<asp:BoundField HeaderText="Phone Number" DataField="PhoneNumber" />
<asp:BoundField HeaderText="Sex" DataField="Sex" />
<asp:BoundField HeaderText="Reason" DataField="Reason" />
<asp:BoundField HeaderText="SignIn" DataField="SignIn_Time" />
<asp:BoundField HeaderText="SignOut" DataField="Signout_Time" />
<asp:TemplateField HeaderText="Action" Visible="True">
<ItemTemplate>
<asp:Button ID="out" runat="server" Text="Sign out" CommandName="SignOut" CommandArgument='<%#Eval("SN") %>'/>
</ItemTemplate>
</asp:TemplateField>
</Columns>
<PagerSettings FirstPageText="First" LastPageText="Last" Mode="NumericFirstLast" PageButtonCount="5" />
</asp:GridView>
You can set the button Visibility directly in the GridView Template:
<asp:Button Visible='<%# string.IsNullOrEmpty(Eval("Signout_Time").ToString()) %>' runat="server" Text="Sign out" ID="out" CommandName="SignOut" CommandArgument='<%#Eval("SN") %>'/>

Add Read more button to view Gridview Description text

I have a Gridview that fetches Description text from the database and once it's over some text limit, I want the Gridview to let users click "Read more" from where they can see the full text without having to navigate to a new url. Thank you in advance.
My Gridview Columns are as follows:
<asp:BoundField DataField="Id" HeaderText="Id" SortExpression="Id" InsertVisible="False" ReadOnly="True" />
<asp:BoundField DataField="Name" HeaderText="Name" SortExpression="Name" />
<asp:BoundField DataField="Address" HeaderText="Address" SortExpression="Address" />
<asp:BoundField DataField="Phone" HeaderText="Phone" SortExpression="Phone" />
<asp:BoundField DataField="Email" HeaderText="Email" SortExpression="Email" />
<asp:BoundField DataField="Source" HeaderText="Source" SortExpression="Source" />
<asp:BoundField DataField="Message" HeaderText="Message" SortExpression="Message" />
<asp:BoundField DataField="Date" HeaderText="Date" DataFormatString="{0:dd/MM/yyyy}" SortExpression ="Date" />
Add ItemTemplate with a Lable Control and LinkButton as read more in Gridview Like:
<asp:TemplateField>
<ItemTemplate>
<asp:Label ID="Label20" runat="server" Text='<%#((string)Eval("ColumnName")).Length<20?Eval("ColumnName"):((string)Eval("ColumnName")).Substring(0,20)+"..." %>' ToolTip='<%#Eval("question") %>' Width="100"></asp:Label>
<asp:LinkButton ID="LinkButton1" runat="server" Visible='<%#SetVisibility(Eval("ColumnName"),20) %>' OnClick="LinkButton1_Click">Read More...</asp:LinkButton>
</ItemTemplate>
</asp:TemplateField>
Here Lable text it will contain only 20 char and link button will show Read More but Lable tooltip contain all characters of that column. On Link Button click we fire an event to show all data in that Label.
protected void LinkButton1_Click(object sender, EventArgs e)
{
//Read More Link Button from Gridview on Click
LinkButton lb = (LinkButton)sender;
GridViewRow row = lb.NamingContainer as GridViewRow;
//Finding the description Text Lable
Label qst = row.FindControl("Label20") as Label;
// Setting Link Button Text
lb.Text = (lb.Text == "Read More...") ? "Hide..." : "Read More...";
//Swaping tooltip value to text and vices versa as Tooltip has all charecters
string temp = qst.Text;
qst.Text = qst.ToolTip;
qst.ToolTip = temp;
}
protected bool SetVisibility(object Desc, int length)
{
return Desc.ToString().Length > length;
}
Hope this will help you to find out your solution.
Updates:
It seems Your Column has null value to handle this you can check for null and then convert :
<asp:TemplateField>
<ItemTemplate>
<asp:Label ID="Label20" runat="server" Text='<%#Eval("ColumnName")==DBNull.Value ? string.Empty :(((string)Eval("ColumnName")).Length<20?Eval("ColumnName"):((string)Eval("ColumnName")).Substring(0,20)+"...") %>' ToolTip='<%#Eval("question") %>' Width="100"></asp:Label>
<asp:LinkButton ID="LinkButton1" runat="server" Visible='<%# Eval("ColumnName")==DBNull.Value ? false :SetVisibility(Eval("ColumnName"),20) %>' OnClick="LinkButton1_Click">Read More...</asp:LinkButton>
</ItemTemplate>
</asp:TemplateField>
I would suggest using a linkbutton and binding the message in the ItemTemplate:
<asp:TemplateField HeaderText="Message">
<ItemTemplate>
<%# Bind("Message") %> - <asp:linkbutton id="btnReadMore" runat="server" causesvalidation="false" commandname="readmore" commandargument="<%# Bind("MessageId") %>" />
</ItemTemplate>
</asp:TemplateField>
The logic for the link button can then popup a
protected void GridView1_RowCommand(object sender, GridViewCommandEventArgs e)
{
if (e.CommandName == "readmore")
{
Session["messageid"] = e.CommandArgument.ToString();
Response.Redirect("popuppage.aspx?id=" + Session["messageid"].ToString() + "");
}
}
In the popuppage.aspx will be logic to fetch the complete message using the messageid from the Query string.

Making values inside column clickable (fires click_event)

I have a grid and I want to make the values in the first column "clickable" so that they fire a click event. The values in this first column are populated from a sql server query.
What would be the best way to accomplish this?
Below is my grid:
<asp:GridView runat="server" ID="HSMGrid"
AutoGenerateColumns="false"
DataKeyNames="Status"
OnRowCommand="grdvwSearchDepositTransaction_RowCommand" OnRowDataBound="grdSearch_RowDataBound" ShowHeaderWhenEmpty="true"
CssClass="grid" Width="550">
<Columns>
<asp:BoundField DataField="TransactionGroupsEntry.groupID" HeaderText="BatchID" ItemStyle-CssClass="mediumColumn columnCenter" />
<asp:BoundField DataField="TransactionGroupsEntry.bankNumber" HeaderText="Bank" ItemStyle-CssClass="mediumColumn columnCenter" />
<asp:BoundField DataField="TransactionGroupsEntry.branchNumber" HeaderText="Branch" ItemStyle-CssClass="mediumColumn columnCenter" />
<asp:BoundField DataField="TransactionGroupsEntry.cashInTicketAmount" HeaderText="Cash-In Ticket Amount" ItemStyle-CssClass="mediumColumn columnCenter" />
<asp:BoundField DataField="TransactionGroupsEntry.createdBy" HeaderText="Created By" ItemStyle-CssClass="mediumColumn columnCenter" />
<asp:BoundField DataField="TransactionGroupsEntry.dateCreated" HeaderText="Date Created" ItemStyle-CssClass="mediumColumn columnCenter" />
</Columns>
<EmptyDataTemplate>
<span style="font-weight: bold;">No Transactions have been entered</span>
</EmptyDataTemplate>
</asp:GridView>
Edit::
This is what I currently have following the advise of the first answer:
You would need to convert the first column into a template field. The template field's ItemTemplate would then contain a server side control (i.e LinkButton). This control could then have a server side OnClick event attached to it that would handle the server side logic. Below is an example:
<asp:TemplateField HeaderText="BatchID">
<ItemTemplate>
<asp:LinkButton runat="server" ID="btnBatchId" CommandArgument='<%# DataBinder.Eval(Container.DataItem, "TransactionGroupsEntry.groupID") %>' OnClick="btnBatchId_Click" Text='<%# DataBinder.Eval(Container.DataItem, "TransactionGroupsEntry.groupID") %>' />
</ItemTemplate>
</asp:TemplateField>
In your code behind file your click event could look like the below example. I have added the ability to parse out/get at the id that is associated to the LinkButton:
protected void btnBatchId_Click(object sender, EventArgs e) {
var linkButton = sender as LinkButton;
if (linkButton != null) {
var batchId = 0;
if (int.TryParse(linkButton.CommandArgument, out batchId)) {
// batchId variable should contain a valid integer value
}
}
}

Delete GridView Rows in button cick without RowDeleting that not saved in DB

I have a gridview,
When Button ADD is clicked the textboxs values will be added to gridview.
After adding values to gridview i want to select a row and click delete button but error occurs to me on deleting.
My GridView Code
<asp:GridView ClientIDMode="Static" ID="GridPesonal" runat="server" AutoGenerateColumns="False" Class="GrdSty" Width="100%" DataKeyNames="RowNumber">
<Columns>
<asp:BoundField DataField="RowNumber" HeaderText="ردیف">
</asp:BoundField>
<asp:BoundField DataField="StartDate" HeaderText="از تاریخ">
</asp:BoundField>
<asp:BoundField DataField="EndDate" HeaderText="تا تاریخ">
</asp:BoundField>
<asp:BoundField DataField="SherkatName" HeaderText="نام شرکت،سازمان یا موسسه" >
</asp:BoundField>
<asp:BoundField DataField="WorkUnitName" HeaderText="واحد محل کار">
</asp:BoundField>
<asp:BoundField DataField="Sharh" HeaderText="شرح دقیق شغل/سمت/مسئولیت" >
</asp:BoundField>
<asp:BoundField DataField="WorkTime" HeaderText="زمان کار" >
</asp:BoundField>
<asp:BoundField DataField="Description" HeaderText="توضیحات">
</asp:BoundField>
<asp:TemplateField>
<ItemTemplate>
<asp:CheckBox ID="SavabegSelect" runat="server" AutoPostBack="True" OnCheckedChanged="SavabegSelect_CheckedChanged" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
<EmptyDataTemplate>
موردی ثبت نشده است.
</EmptyDataTemplate>
</asp:GridView>
Btn Delete Code
<asp:Button ClientIDMode="Static" ID="BtnDelete" CssClass="btnregister" runat="server" Text="حذف" OnClick="BtnDelete_Click" />
Code behind of btn Delete
protected void BtnDelete_Click(object sender, EventArgs e)
{
foreach (GridViewRow gvrow in GridPesonal.Rows)
{
CheckBox chkdelete = (CheckBox)gvrow.FindControl("SavabegSelect");
if (chkdelete.Checked)
{
GridPesonal.DeleteRow(gvrow.RowIndex);
}
}
}
When execute above code this error show
The GridView 'GridPesonal' fired event RowDeleting which wasn't handled.
Have you used command-name as Delete on BtnDelete.
Remove that from Delete Button it will work.
If you have like this
<asp:GridView ID="gvRoute" DataKeyNames="Route" runat="server" AutoGenerateColumns="false"
AllowPaging="true" Width="30%"
onrowdeleting="gvRoute_RowDeleting">
Remove onrowdeleting="gvRoute_RowDeleting
or wirte event for
protected void gvRoute_RowDeleting(object sender, GridViewDeleteEventArgs e)
{
\\
}
or Use the "CommandName" property "Delete"
Or Use OnClick
<asp:GridView ClientIDMode="Static" ID="GridPesonal" runat="server" AutoGenerateColumns="False" Class="GrdSty" Width="100%" DataKeyNames="RowNumber" OnClick="BtnDelete">

Categories

Resources