how to get row values when checkbox is checked in gridview - c#

before I asked this I did some checking around to make sure that this doesn't turn out to be a duplicate and ways to get the row values from a row that has a checkbox in its template field...but I can't seem to get it working...So far I have tried
protected void Page_Load(object sender, EventArgs e)
{
Entities NW = new Entities();
var customers =
from c in NW.Customers
where (c.ContactName.StartsWith("Ma") || c.ContactName.StartsWith("An")
|| c.ContactName.StartsWith("T")
|| c.ContactName.StartsWith("V")
)
orderby c.ContactName ascending
select new
{
c.CustomerID,
c.ContactName,
c.CompanyName,
c.City
};
gv1.DataSource = customers.ToList();
gv1.DataBind();
}
protected void Button1_Click(object sender, EventArgs e)
{
foreach (GridViewRow row in gv1.Rows)
{
if (row.RowType == DataControlRowType.DataRow)
{
CheckBox chkRow = (row.Cells[0].FindControl("CB") as CheckBox);
if (chkRow.Checked)
{
Label1.Text = row.Cells[2].Text;
}
}
}
}
I have stepped through the button click event and when it gets to
if (chkRow.Checked)
its showing as null and skips over it..
my markup is
<asp:GridView ID="gv1" runat="server">
<HeaderStyle BackColor="SkyBlue" />
<AlternatingRowStyle BackColor="Yellow" />
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:CheckBox ID="CB" runat="server" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
when I look at the source after I run, the checkboxes are all named differently than what I gave them the ID of "CB", attached is the pic of the source when its running
I am not sure what I am doing wrong with this

Your GridView should have more columns, because you are referencing Cell[2] in your code.
You might try to use row object to look for your control:
CheckBox chkRow = (row.FindControl("CB") as CheckBox);

Related

how to find button inside gridview

i have gridview in my project and there is one button inside that gridview.
i want to change that button's property according to gridview cell value
below is my gridview with button
<div class="row">
<div class="col-md-12">
<h1 style="color:red" id="payDetailH" runat="server" visible="false">Payment Details</h1>
<br />
<asp:Panel ID="Panel2" runat="server" ScrollBars="Auto">
<asp:GridView ID="gvPayemenDetailNew" CssClass="table table-hover" GridLines="None" runat="server"
OnRowCommand="gvPayemenDetailNew_RowCommand" OnRowDataBound="gvPayemenDetailNew_RowDataBound" >
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:Button ID="btnGenNew" runat="server" CommandName="GJobID" CommandArgument="<%# ((GridViewRow) Container).RowIndex %>" Text="Ceate Job" CssClass="btn" Enabled="False" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
<HeaderStyle Height="50px" HorizontalAlign="Center" VerticalAlign="Middle" />
</asp:GridView>
</asp:Panel>
</div>
</div>
and this is my code behind
protected void gvPayemenDetailNew_RowDataBound(object sender, GridViewRowEventArgs e)
{
foreach (GridViewRow row in gvPayemenDetailNew.Rows)
{
if (row.RowType == DataControlRowType.DataRow)
{
Button btn = e.Row.FindControl("btnGenNew") as Button;
if (PayStatus == "Approved")
{
btn.Enabled = true;
}
}
}
}
i got this error
System.NullReferenceException: Object reference not set to an instance of an object.
click here to see my screens
you must use [row] in loop :
protected void gvPayemenDetailNew_RowDataBound(object sender,
GridViewRowEventArgs e)
{
foreach (GridViewRow row in gvPayemenDetailNew.Rows)
{
if (row.RowType == DataControlRowType.DataRow)
{
Button btn = row.FindControl("btnGenNew") as Button;
if (PayStatus == "Approved")
{
btn.Enabled = true;
}
}
}
}
You don't need to loop the GridView in the RowDataBound event. It is already executing per row when data is bound to the GridView. And when in a loop you set all the buttons based on the last row value, not per row.
So this should be the correct way, assuming PayStatus is a column in the dataset bound to the GridView.
protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e)
{
//check if the row is a datarow
if (e.Row.RowType == DataControlRowType.DataRow)
{
//cast the row back to a datarowview
DataRowView row = e.Row.DataItem as DataRowView;
//find the button with findcontrol
Button btn = e.Row.FindControl("btnGenNew") as Button;
//use the paystatus of the current row to enable the button
if (row["PayStatus"].ToString() == "Approved")
{
btn.Enabled = true;
}
}
}
Everything looks really good in your code. This the correct way to find controls. Just one suggestion but not sure if its going to work, You can change the way you typecast the button
Button btn = (Button)e.Row.FindControl("btnGenNew");

ASP.NET Out of bound exception accessing a row in gridview

I have this asp.net control:
<div class="field" style="text-align: center;">
<asp:GridView ID="gvTags" runat="server" AutoGenerateColumns = "false"
OnRowDataBound="OnRowDataBound" OnRowDeleting="OnRowDelete">
<Columns>
<asp:BoundField DataField="tagId" HeaderText="Id" />
<asp:BoundField DataField="name" HeaderText="<%$ Resources:Common, tlblTags %>" />
<asp:CommandField ShowDeleteButton="True" ButtonType="Button" />
</Columns>
</asp:GridView>
</div>
And I bind my datasource like this from a collection retrieved from database:
this.gvTags.DataSource = product.Tags;
this.gvTags.DataBind();
In the OnRowDataBound I create a popup to show up when the delete button is clicked, so the code is this:
protected void OnRowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
string item = e.Row.Cells[1].Text;
foreach (Button button in e.Row.Cells[2].Controls.OfType<Button>())
{
if (button.CommandName == "Delete")
{
button.Attributes["onclick"] = "if(!confirm('Do you want to delete " + item + "?')){ return false; };";
}
}
}
}
This is working fine, I can see the three rows in my browser and all works as expected (the popup is showing with the correct information etc). But the problem is when I accept the popup so the OnRowDelete event is fired.
I want to remove a Tag from the database with a specific tagId, so I need to get the position 0 at the current row, so this is my code to do that:
protected void OnRowDelete(object sender, GridViewDeleteEventArgs e)
{
int index = Convert.ToInt32(e.RowIndex);
GridViewRow row = this.gvTags.Rows[index];
long tagId = Convert.ToInt64(row.Cells[0].Text);
/* Remove the tag */
productService.RemoveTag(productId, tagId);
/* Delete the row from gridview */
this.gvTags.DeleteRow(index);
}
The error I'am getting is in this line: GridViewRow row = this.gvTags.Rows[index];. I'm getting System.ArgumentOutOfRangeException but I don't understand why. The index variable takes a valid int value like 0, 1...
Any ideas on what I'am doing wrong? Thanks.

How to fetch values from cells inside Grid View

I have used grid view in my ASP.NET application.
<asp:GridView ID="grdView" runat="server">
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:CheckBox ID="chkbox" runat="server" />
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="Jurisdiction">
<ItemTemplate>
<asp:Label ID="lblJurisdiction" runat="server" />
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="License Number">
<ItemTemplate>
<asp:TextBox ID="txtLicenseNumber" runat="server" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
in cs file
protected void btnSave_Click(object sender, EventArgs e)
{
foreach (GridViewRow row in grdView.Rows)
{
for (int i = 0; i < grdView.Columns.Count; i++)
{
String cellText = row.Cells[i].Text;
}
}
}
Note that the above grid will be populated by data. Now I need to get data from already populated gridview. The above code is not working. Also I need to retrieve from labels, textboxes, checkboxes values inside grid. Please help !!!
You can use FindControl method to retrieve the control's data:-
protected void btnSave_Click(object sender, EventArgs e)
{
foreach (GridViewRow row in grdView.Rows)
{
CheckBox chkbox = row.FindControl("chkbox") as CheckBox;
Label lblJurisdiction = row.FindControl("lblJurisdiction") as Label;
..and so on
//Finally retrieve the data like your normal control
string labelText = lblJurisdiction.Text;
}
}
Use GridViewRow.FindControl method.
foreach (GridViewRow row in grdView.Rows)
{
// return you the check-box control from current row
var chkbox = row.FindControl("chkbox");
}
Check whether the row type is DataControlRowType.DataRow.
protected void btnSave_Click(object sender, EventArgs e)
{
foreach (GridViewRow row in grdView.Rows)
{
if (row.RowType == DataControlRowType.DataRow)
{
for (int i = 0; i < grdView.Columns.Count; i++)
{
String cellText = row.Cells[i].Text;
}
}
}
}
To get the TextBox, CheckBox value from the grid use this,
string TextBoxvalue = ((TextBox)GridViewID.Rows[i].FindControl("TextBoxName")).Text;
string CheckBoxvalue = ((CheckBox)GridViewID.Rows[i].FindControl("CheckBoxName")).Text;
In your code .cs file, you are missing to check only for datarow. As it will check all 3 places:-
1. Header
2. Body
3. Footer
Might any one place, any exception can occur.
Please add one more if condtion just after the for loop, as below.
if (row.RowType == DataControlRowType.DataRow)
{
Hope this post will help's you :).
Use
cells[i].EditedFormatedValue

How to delete a row without using OnRowDeleted/OnRowDeleting in gridview

Code Behind
public void lbDelete_Click(object sender, EventArgs e)
{
LinkButton lb = sender as LinkButton;
GridViewRow gvrow = lb.NamingContainer as GridViewRow;
gvsize.DeleteRow(gvrow.RowIndex);
}
GridView:
<asp:GridView ID="gvsize" runat="server" ShowFooter="True" CellPadding="1" CellSpacing="2" AutoGenerateColumns="false" GridLines="Horizontal">
<asp:TemplateField HeaderText="Action">
<ItemTemplate>
<asp:LinkButton ID="lnkdelete" runat="server" ForeColor="Blue" OnClick="lbDelete_Click">Delete</asp:LinkButton>
</ItemTemplate>
</asp:TemplateField>
</asp:GridView >
There are 2 rows in my gridview which I need to delete the row using the function above.
It throws an error "gvsize" RowDeletingEvent was not handled properly.
Is that necessary to use OnRowDeleted/OnRowDeleting in gridview which I feel not necessary??
As stated in How to delete row from gridview?
You are deleting the row from the gridview but you are then going and
calling databind again which is just refreshing the gridview to the
same state that the original datasource is in.
Either remove it from the datasource and then databind, or databind
and remove it from the gridview without redatabinding.
You can use row databound event to accomplish this task.
<asp:LinkButton ID="lnkBtnDel" runat="server" CommandName="DeleteRow" OnClientClick="return confirm('Are you sure you want to Delete this Record?');"">Delete</asp:LinkButton>
and in the rowdatabound event you can have
protected void GridView1_RowCommand(object sender, GridViewCommandEventArgs e)
{
if (e.CommandName == "DeleteRow")
{
//incase you need the row index
int rowIndex = ((GridViewRow)((LinkButton)e.CommandSource).NamingContainer).RowIndex;
//followed by your code
}
}
Try this to delete row
protected void GridView1_RowDeleting(object sender, GridViewDeleteEventArgs e)
{
dt.Rows.RemoveAt(e.RowIndex);
GridView1.DataSource = dt;
GridView1.DataBind();
}
You can also delete row from another method using Template Column
ASPX
<asp:TemplateField HeaderText="Delete">
<ItemTemplate>
<asp:ImageButton ID="imgDelete" runat="server" CommandName="deletenotice" ImageUrl="~/images/delete1.gif" alt="Delete"
OnClientClick="return confirm('Are you sure want to delete the current record ?')">
</asp:ImageButton>
</ItemTemplate>
</asp:TemplateField>
C# Code
protected void gvNoticeBoardDetails_RowCommand(object sender, GridViewCommandEventArgs e)
{
if (e.CommandName.ToLower().Equals("deletenotice"))
{
GridViewRow row = (GridViewRow)(((ImageButton)e.CommandSource).NamingContainer);
NoticeBoard notice = new NoticeBoard();
HiddenField lblCust = (HiddenField)row.FindControl("hdngvMessageId");//Fetch the CourierId from the selected record
auditTrail.Action = DBAction.Delete;
Service simplyHRClient = new Service();
MessageClass messageClass = simplyHRClient.SaveNoticeBoard(notice, auditTrail);
if (messageClass.IsSuccess)
{
this.Page.AddValidationSummaryItem(messageClass.MessageText, "save");
showSummary.Style["display"] = string.Empty;
showSummary.Attributes["class"] = "success-message";
if (messageClass.RecordId != -1)
lblCust.Value = messageClass.RecordId.ToString();
}
else
{
this.Page.AddValidationSummaryItem(messageClass.MessageText, "save");
showSummary.Style["display"] = string.Empty;
showSummary.Attributes["class"] = "fail-message";
}
//Bind Again grid
GetAllNoticeBoard();
}
}
Hope it helps you

How to keep CheckBox checked state in DataList after postback?

I'm creating a really simple "tag cloud" function for a project database. I want the user to be able to check various tags and, then, with an autopostback on the checked box(es), display the associated projects that have those tags.
It works, but the checkboxes are resetting after postback. I want the checkboxes to remain checked (or unchecked, as the case may be) so the user can select multiple tags.
I've searched and seen that some say to put the databinding event within an if(!isPostBack). I've tried that, but it doesn't seem to matter.
aspx code:
<asp:DataList ID="TagDataList" runat="server" OnDataBinding="databindthesucker" DataKeyField="TagName">
<ItemTemplate>
<asp:CheckBox AutoPostBack="true" ID="TagCheckbox" runat="server" Text='<%#Eval ("dZTagName") %>' />
<asp:HiddenField ID="TagNameHidden" runat="server" Value='<%#Eval ("dZTagName") %>'/><br />
</ItemTemplate>
</asp:DataList>
<asp:DataList ID="ProjectDataList" runat="server" DataKeyField="projectID">
<ItemTemplate>
<asp:HyperLink ID="ProjectLink" runat="server" NavigateUrl='<%# "/Project/Default.aspx?PID=" + Eval ("projectID") %>' Text='<%# Eval ("projectID") + ": " + Eval ("projectName") %>'> </asp:HyperLink><br />
</ItemTemplate>
</asp:DataList>
and then the cs...
protected void Page_Load(object sender, EventArgs e)
{
displaytags(sender, e);
}
protected void displaytags(object sender, EventArgs e)
{
var qrygettags = (from t in db.TagTables
select new { t.TagName }).Distinct().ToList();
TagDataList.DataSource = qrygettags;
TagDataList.DataBind();
CheckBox TagCheckbox = (CheckBox)TagDataList.Items[0].FindControl("TagCheckbox");
}
protected void databindthesucker(object sender, EventArgs e)
{
foreach (DataListItem item in TagDataList.Items)
{
if (item.ItemType == ListItemType.Item || item.ItemType == ListItemType.AlternatingItem)
{
CheckBox TagCheckbox = (CheckBox)item.FindControl("TagCheckbox");
HiddenField TagNameHidden = (HiddenField)item.FindControl("TagNameHidden");
string Tagstring = TagNameHidden.Value.ToString();
if (TagCheckbox.Checked)
{
var qrygetprojects = (from p in db.projects
join pt in db.TagTables on p.projectID equals pt.projectID
where pt.TagName == Tagstring
select new
{
pt.projectID,
p.projectName
}).ToList();
ProjectDataList.DataSource = qrygetprojects;
ProjectDataList.DataBind();
}
}
}
}
Any ideas?

Categories

Resources