I have a GridView on my page and on a button_OnClick event I'm wanting to add a new row to the grid.
I can add a row to the table using the following code, which works fine, but as I'm binding the DataTable to the grid any previous entries are lost.
string selectedProduct= ddlProducts.SelectedItem.Text;
DataTable dataTable = new DataTable();
dataTable.Columns.Add("Product");
DataRow dataRow;
dataRow = dataTable.NewRow();
dataRow["Product"] = selectedProduct;
dataTable.Rows.Add(dataRow);
grdSelectedProducts.DataSource = dataTable;
grdSelectedProducts.DataBind();
So whilst I understand why this is causing the data loss, I'm not really sure how to get around it.
How can I add a new row to the GridView on each button click whilst retaining the previously added row? The data is not stored anywhere other than the grid itself, so there is no real datasource.
There are options such as Add row to gridview on client side which uses Jquery, but I have read that it isn't a great idea to use that when adding / removing items from the grid. Perhaps that is wrong? Or there is this Add new row to gridview but there isn't much detail there.
You need to store the Products into ViewState (or SessionState or Database) so that it can persist on post back.
For example,
private DataTable ProductDataTable
{
get { return ViewState["ProductDataTable"] as DataTable ?? new DataTable(); }
set { ViewState["ProductDataTable"] = value; }
}
protected void AddRowButton_Click(object sender, EventArgs e)
{
string selectedProduct = ddlProducts.SelectedItem.Text;
// Get the data from ViewState
DataTable dataTable = ProductDataTable;
dataTable.Columns.Add("Product");
DataRow dataRow;
dataRow = dataTable.NewRow();
dataRow["Product"] = selectedProduct;
dataTable.Rows.Add(dataRow);
// Save the data back to ViewState
ProductDataTable = dataTable;
grdSelectedProducts.DataSource = dataTable;
grdSelectedProducts.DataBind();
}
Here is a sample you can try:
DataTable dt = new DataTable();
if (ViewState["CurrentTable"]!=null)
{
dt = (DataTable)ViewState["CurrentTable"];
}
else
{
dt.Columns.Add(new DataColumn("Col1", typeof(string)));
dt.Columns.Add(new DataColumn("Col2", typeof(string)));
}
DataRow dr = null;
dr = dt.NewRow();
dr["Col1"] = "tes";
dr["Col2"] = "test";
dt.Rows.Add(dr);
ViewState["CurrentTable"] = dt;
GridView1.DataSource = dt;
GridView1.DataBind();
Sorry for bad formatting, typed this with my cellphone. Hope it helps! :-)
// OnButten click
function addrow(sender, args) {
// td add as per your column required
$("#GridView1 tbody").append('<tr><td>00001</td><td>Mr.</td><td>LOKESH N</td></tr>');
}
Related
Here is my code:
protected void Page_Load(object sender, EventArgs e)
{
DataTable dt = new DataTable();
dt=PrepareFirstGridViewRow(); //function below
DataRow dr = dt.NewRow();
dr["Index"] = index;
index++;
dr["Telephone"] = Telephone;
dr["Amount"] = Amount;
dr["Comment"] = Comment;
Button BTN = new Button();
BTN.Click += GridButton_Click;
BTN.OnClientClick = "GridButton_Click";
BTN.Text = "Sell";
BTN.Attributes.Add("CId", j.ToString());
BTN.Style.Value = "display:inline-block;";
BTNF.ButtonType = ButtonType.Button;
dr["Sell"] = BTN;
dt.Rows.Add(dr);
ContractsGrid.DataSource = dt;
ContractsGrid.DataBind();
ContractsGrid.Columns.Add(new DataControlField);
connection.Close();
}
And the function Prepare:
private DataTable PrepareFirstGridViewRow()
{
DataTable dt = new DataTable();
dt.Columns.Add(new DataColumn("Index", typeof(string)));
dt.Columns.Add(new DataColumn("Telephone", typeof(string)));
dt.Columns.Add(new DataColumn("Amount", typeof(string)));
dt.Columns.Add(new DataColumn("Comment", typeof(string)));
dt.Columns.Add(new DataColumn("Sell", typeof(Button)));
return dt;
}
Everything works fine, except insertion of Buttons in last column, which do not appear at all (neither the header nor the button). When I replace ("Sell", typeof(Button)) with ("Sell", typeof(string)) and dr["Sell"] = "something"; the grid is created properly.
Question is simple: Why?
I tried the following solution:
protected void Page_Load(object sender, EventArgs e)
{
try
{
Button btn = new Button();
btn.Text = "Click";
btn.ID = "btn_click";
btn.Click += new EventHandler(btnevent_Click);
btn.OnClientClick = "Hello('" + "a" + "')";
form1.Controls.Add(btn);
}
catch (Exception)
{ }
}
And the above code produces buttons on the page event though it is in page_load event. So the problem must be not about the event, but the grid view.
Code below also works perfectly fine, but the button is added to whole grid (I am conscious about that). So it is not about the event but insertion of button into grid.
Button BTNo = new Button();
BTNo.Click += GridButton_Click;
BTNo.OnClientClick = "GridButton_Click";
BTNo.Text = "Sell";
BTNo.Attributes.Add("CId", "1");
BTNo.Style.Value = "display:block;";
ContractsGrid.DataSource = dt;
ContractsGrid.DataBind();
ContractsGrid.Controls.Add(BTNo);
connection.Close();
This is because of the asp.net page lifecycle. Controls are created before the"page_load" event. Try creating the button in an earlier event such as "page_init".
Solution is not to use datatable, gridview is also a bad idea, and my efforts to find the correct combination of lines of code were insufficient so i found a semi-solution: You can replace gridview with simple asp.net table component where you can put simply anthing. It does not resolve the problem the way I would like to, but it works and is clearer than datatables and binding it to gridviews.
Here is the working code:
TableRow tRow = new TableRow()
Tab.Rows.Add(tRow);
Tab.Rows.Add(tRow);
// Create a new cell and add it to the row.
TableCell tCell = new TableCell();
tCell.Text = "Row ";
Button bt = new Button();
bt.Text = "Click Me";
bt.OnClientClick = "TabButton_Click";
tCell.Controls.Add(bt);
tRow.Cells.Add(tCell);
I have a gridview with paging (page size 10), which contains Course details. when i am saving gridview data into database it save only 10 record (according to page).
is there any to get all gridview all rows.
e.g. if my gridview contains 25 rows with paging and when i save data into database then all 25 rows data insert into database?
please help...
Here is my code
DataTable dt = new DataTable();
dt.Columns.Add("row_index");
dt.Columns.Add("edited_value");
IList<int?> SeqNos = new List<int?>();
foreach (GridViewRow gvr in gvViolationCodes.Rows)
{
TextBox tb = (TextBox)gvr.FindControl("txtSeqNo");
Label lblSysid = (Label)gvr.FindControl("lblSysID");
HiddenField hf = (HiddenField)gvr.FindControl("HiddenField1");
if (tb.Text != hf.Value)
{
DataRow dr = dt.NewRow();
SeqNos.Add(Convert.ToInt32(tb.Text));
dr["row_index"] = lblSysid.Text;
dr["edited_value"] = tb.Text;
dt.Rows.Add(dr);
}
}
You need to save the data in temporary storage in PageIndexChanging event of GrIdView. On final save send the datatable to Sql Server Procedure or loop through the datatable and save it in database. Follow the steps:
protected void grdView_PageIndexChanging(object sender, GridViewPageEventArgs e)
{
fnStoreGridData();
}
private void fnStoreGridData()
{
DataTable TempDataTable = new DataTable();
if(Session["Data"]!=null){
TempDataTable = Session["Data"] as DataTable;
}
else{
TempDataTable.Columns.Add("exCourse", typeof(string)) ;
TempDataTable.Columns.Add("exUniversityCourse", typeof(string)) ;
}
foreach (GridViewRow row in gvExportCourse.Rows)
{
Label exCourse = (Label)row.FindControl("gvlblCourseName");
Label exUniversityCourse = (Label)row.FindControl("gvlblUniversityCourseName");
if (exCourse != null)
{
if (!string.IsNullOrEmpty(exCourse.Text))
{
TempDataTable.Rows.Add(exCourse.Text, exUniversityCourse.Text);
//TempDataTable is your datatable object. Make sure that datatable contains these columns
}
}
}
}
In Final Save:
protected void button_Click(object s, EventArg e)
{
fnStoreGridData(); //Here this will bind the data of current page
DataTable TempDataTable = new DataTable();
if(Session["Data"]!=null){
TempDataTable = Session["Data"] as DataTable;
}
//Now loop through datatable and store the values
foreach(DataRow in TempDataTable.Rows)
{
CourseInformation course = new CourseInformation();
course.AddCourseMaster(dr["exCourse"].ToString(), dr["exUniversityCourse"].ToString());
}
label1.Text = "Course saved successfully.";
}
I've implemented a drop down list in my webpage and bind it to a data source that I created But no matter what I chose in the page, the dropdownlist.selectedItem always get me the first element and SelectedIndex is always 0. I've contracted my code with other examples and could not find out why.
here is the code of data source creation and binding:
public void bindLanguage() {
DropDownList1.DataSource = CreateDataSource();
DropDownList1.DataTextField = "language";
DropDownList1.DataValueField = "value";
DropDownList1.DataBind();
}
public ICollection CreateDataSource()
{
string[] allLan = System.IO.File.ReadAllLines(MyGlobal.LanFile);
DataTable dt = new DataTable();
DataRow dr;
dt.Columns.Add(new DataColumn("language", typeof(string)));
dt.Columns.Add(new DataColumn("value", typeof(string)));
foreach (string lan in allLan)
{
dr = dt.NewRow();
dr[0] = lan.Split(',')[0];
dr[1] = lan.Split(',')[1];
dt.Rows.Add(dr);
}
DataView dv = new DataView(dt);
return dv;
}
And I call bindLanguage() in page_load.
Here's the code in my aspx :
<asp:DropDownList ID="DropDownList1" runat="server" ForeColor="Black">
</asp:DropDownList>
I had a similar problem .The problem is you are filling your 1st drop-down list in form load and every time some event happens it loads the form i guess u have not kept update panel so again it fills your first drop down and causes selected index changed event to fire which makes your DropDownList1 selected index 0 again and again.
public void bindLanguage() {
if(!Page.IsPostBack)
{
DropDownList1.DataSource = CreateDataSource();
DropDownList1.DataTextField = "language";
DropDownList1.DataValueField = "value";
DropDownList1.DataBind();
}
}
Try this .
Maybe you should add AutoPostBack="false" in the markup-code of the DropDownList.
If this ist not set or true, then the page_load will be triggered everytime you change the object in the dropdown list.
this was always a reason for such issues in my projects.
Change the AutoPostBack property of the dropdownlist to true. Check if error remains.
add this code if (IsPostBack) return; to your Page_Load method.
I have an asp.net page that has the following form fields:
Dropdown 1. This drop down receives the data via SQL data source.
Dropdown 2. Based on the selection of the drop down 1, this drop down queries to the database using SQL datasource and is populated.
A panel control that is placed below drop down list 2 and it has a set of the controls.
My problem is there may be a situation when nothing is returned from the datasource of drop down 2, I want to show an Item "No Data found" in the dropdown list 2 and simultaneously hide the panel that is placed below dropdown 2.
Can someone please let me know how this situation can be handled.
Appreciate the help.
Thanks,
Yagya
Add the following code to your dropdownlist1 selected index change event.
protected void DropDownList1_SelectedIndexChanged(object sender, EventArgs e)
{
// Run this code when your sql datasource 2 does not return record, you can also place an IfElse condition
DataTable dt = new DataTable();
dt.Columns.Add("ID");
dt.Columns.Add("Value");
DataRow row = dt.NewRow();
row[0] = "-1";
row[1] = "Data Not Found";
dt.Rows.Add(row);
DropDownList2.DataSource = dt;
DropDownList2.DataTextField = "Value";
DropDownList2.DataValueField = "ID";
DropDownList2.DataBind();
}
Updated answer: ( Try this one )
You can also place it in your sqldatasource2 selecting event.
protected void SqlDataSource2_Selecting(object sender, SqlDataSourceSelectingEventArgs e)
{
if (e.Arguments.TotalRowCount == 0)
{
DataTable dt = new DataTable();
dt.Columns.Add("ID");
dt.Columns.Add("Value");
DataRow row = dt.NewRow();
row[0] = "-1";
row[1] = "Data Not Found";
dt.Rows.Add(row);
DropDownList2.DataSource = dt;
DropDownList2.DataTextField = "Value";
DropDownList2.DataValueField = "ID";
DropDownList2.DataBind();
}
}
The above code will add a Item to your dropdownlist having Text = "Data Not Found"
In my asp.net gridview, I am placing a template column which displays an image.
Inside the template column I added an image control, and it successfully displaying the images from the database. I am also using paging.
Paging also happening but when I do paging images are not coming in the gridview in proper order for example first three pages it diplays suppose a.jpg, b.jpg,c.jpg and when I click on page number it repeats the same picture instead of remaining pictures, i am using if(!ispostback) in the load event also. please help me out.
my code in page load event is:
da = new SqlDataAdapter("select * from t1", con);
ds = new DataSet();
da.Fill(ds);
path = Server.MapPath(#"~\images");
if (!IsPostBack)
{
GridView1.DataSource = ds;
GridView1.DataBind();
ASCIIEncoding asc = new ASCIIEncoding();
int j = GridView1.Rows.Count;
for (int i = 0; i < j; i++)
{
GridViewRow r=GridView1.Rows[i];
b = (byte[])ds.Tables[0].Rows[i]["photo"];
string name = asc.GetString(b);
Image img = (Image)r.FindControl("Image1");
img.ImageUrl = path + #"\" + name;
}
}
and my code in paging event is
GridView1.PageIndex = e.NewPageIndex;
GridView1.DataSource = ds;
GridView1.DataBind();
ASCIIEncoding asc = new ASCIIEncoding();
int j = GridView1.Rows.Count;
for (int i = 0; i < j; i++)
{
GridViewRow r=GridView1.Rows[i];
b = (byte[])ds.Tables[0].Rows[i]["photo"];
string name = asc.GetString(b);
Image img = (Image)r.FindControl("Image1");
img.ImageUrl = path + #"\" + name;
}
thank in advance
sangita
When you write your paging method you still need to re-query the datasource and rebind your gridview (along with setting the PageIndex).
assuming that you have only the image name stored in the database you can do this in the Image Control in you template column
set the databinding for the image url as
String.Format("images/{0}",Eval("photo"))
and as boon has said
When you write your paging method you
still need to re-query the datasource
and rebind your gridview (along with
setting the PageIndex).
you can declare a method that fetches the records from the database as
protected void fillData()
{
da = new SqlDataAdapter("select * from t1", con);
ds = new DataSet();
da.Fill(ds);
GridView1.DataSource = ds;
GridView1.DataBind();
}
and use it to bind data to your gridview
and in your paging_indexChanging function
GridView1.PageIndex = e.NewPageIndex;
fillData();
Please verify the image paths in pagination. If the images paths are same, then disable the browser cache.