Radio Button Dynamically in ASP.net using html.append - asp.net

I am adding values to html table from a database. What I want is to attach a radio button with each row such that if the user selects a row to be deleted he may do so. I am getting the value of my radio button as vehicle_syskey from the following code and not the numerical value that the variable stores. Below is my code. Please tell me how I can achieve this. Thanks in advance.
protected void Page_Load(object sender, EventArgs e)
{
if (!this.IsPostBack)
{
StringBuilder html = new StringBuilder();
html.Append("<table border=1");
//append headers
//Populating a DataTable from database.
<--Some Relevant Code Present Here>
int vehicle_syskey = 0;
string gm_ymm = null;
foreach (DataRow row in oemTable.Rows)
{
html.Append("<tr>");
vehicle_syskey = Convert.ToInt32(row[0]);
html.Append("<td>");
html.Append("<input type='radio' name='veh_key' class='my_button' value=vehicle_syskey ");
html.Append("</td>");
html.Append("<td>");
html.Append(vehicle_syskey);
html.Append("</td>");
gm_ymm = Convert.ToString(row[1]);
html.Append("<td>");
html.Append(gm_ymm);
html.Append("</td>");
html.Append("<td>");
//Another Query here
foreach (DataRow row1 in vcdbTable.Rows)
{
foreach (DataColumn column1 in vcdbTable.Columns)
{
html.Append(row1[column1.ColumnName]);
html.Append(" ");
}
html.Append("<br>");
}
html.Append("</td>");
}
conn.Close();
//Table end.
html.Append("</table>");
//Append the HTML string to Placeholder.
PlaceHolder1.Controls.Add(new Literal { Text = html.ToString() });
}
}
protected void match1_Click(object sender, EventArgs e)
{
string val = Request.Form["veh_key"].ToString();
Label l1 = new Label();
l1.Text = val;
}

Related

ASP.NET DropdownList Always insert the first item

I have dropdownlist on my website. When I select the any item to insert the database but it does not insert selected item always insert the first item inside the dropdown list. Please Help How can I solve that problem?
Here is my code:
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
GetCategory();
}
}
void GetCategory()
{
dlCategory.DataSource = Data.GetDataTable("SELECT * FROM tblCategory");
dlCategory.DataTextField = "CategoryName";
dlCategory.DataValueField = "ID";
dlCategory.DataBind();
dlCategory.Items.Insert(0, new ListItem("--Select--", "0"));
dlCategory.SelectedIndex = dlCategory.Items.IndexOf(dlCategory.Items.FindByText("--Select--"));
}
SqlConnection baglanti = Data.baglan();
SqlCommand tr = new SqlCommand("Insert tblProduct (CategoryID) values(#CategoryID)", baglanti);
tr.Parameters.AddWithValue("#CategoryID", dlCategory.SelectedValue);
tr.ExecuteNonQuery();
Your question is a bit blurry regarding the code, so correct me if I misunderstood, but I presume you want to do the following in WebForms:
Simply show all available categories that can be assigned to a
product
When the user selects the category and hits submit, it will be inserted to the DB assegnied to it
It is not quite elegant, but I would put something like this:
private SqlConnection _sqlConnection = new SqlConnection();
protected void Page_Load(object sender, EventArgs e)
{
_sqlConnection.ConnectionString = #".." //Assign whatever your ConnectionString is in Data.baglan();
_sqlConnection.Open();
if (!IsPostBack)
{
GetCategory();
}
else
{
//Define your insert something like this, and I would put this into the submit Button_Click event:
if (!String.IsNullOrEmpty(dlCategory.SelectedValue) && dlCategory.SelectedValue != "0")
{
SqlCommand tr = new SqlCommand("Insert tblProduct (CategoryID) values (#CategoryID)", _sqlConnection);
tr.Parameters.AddWithValue("#CategoryID", dlCategory.SelectedValue);
tr.ExecuteNonQuery();
}
else
{
//TODO: Handle wrong selection, eg display an error message..
}
}
}
void GetCategory()
{
dlCategory.DataSource = new SqlCommand("SELECT * FROM tblCategory", _sqlConnection).ExecuteReader();
dlCategory.DataTextField = "CategoryName";
dlCategory.DataValueField = "ID";
dlCategory.DataBind();
dlCategory.Items.Insert(0, new ListItem("--Select--", "0"));
dlCategory.SelectedIndex = dlCategory.Items.IndexOf(dlCategory.Items.FindByText("--Select--"));
}

Change row color of gridview by database Values

I am making a application in asp.net which shows the values in gridview from the database.In database i am having a colmn named as StatusId which has a value of 1 or 2 or 3.
I tried to show the grid view rows in different color by their statusId values. But it never works. How can i do it in asp.net.
Here is my code
protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e)
{
Connection.Open();
SqlCommand Command1 = Connection.CreateCommand();
Command1.CommandText = "Select statusColor from status where statusId=(Select statusId from fileInfo where userId=(Select userId from userInfo where email='" + Session["email"].ToString() + "'))";
for (int i = 0; i < GridView1.Rows.Count; i++)
{
using (SqlDataReader reader = Command1.ExecuteReader())
{
while (reader.Read())
{
statusId = reader["statusColor"].ToString();
}
GridView1.RowStyle.BackColor = Color.FromName(statusId);
}
}
foreach (GridViewRow row in GridView1.Rows)
{
row.BackColor = Color.Green;
}
SqlCommand com = new SqlCommand("gridcolor", Connection);
com.CommandType = CommandType.StoredProcedure;
com.Parameters.AddWithValue("#statusId", statusId);
com.Parameters.Add("#statusColor", SqlDbType.NVarChar, 30);
com.Parameters["#statusColor"].Direction = ParameterDirection.Output;
com.ExecuteNonQuery();
string msg = (string)com.Parameters["#statusColor"].Value;
Connection.Close();
}
What is the mistake i am doing here?
EDIT
I have the color codes which are stored in the database named as statusColor. I have to apply those color to these status.
You have statusId having values 1,2,3 and you are passing to Color.FromName which and 1,2,3 are not names of color you can use switch to assign different colors based on statusId .
Color rowColor = Color.Red;
switch(statusId)
{
case 1:
rowColor = Color.Green;
break;
case 2:
rowColor = Color.White;
break;
case 3:
rowColor = Color.Blue;
break;
}
GridView1.RowStyle.BackColor = rowColor ;
You are doing it the wrong way. You have to databind your gridview on either page load or a custom event (say click of a button) & not rowDataBound event. This event occurs when your row is bound with data & you want to change some attributes for each row (as in your case).
You can use Gridview DataBound event to assign colors in following way
protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
// Fetch status Id for current row
int statusId= Convert.ToInt32(DataBinder.Eval(e.Row.DataItem,"UnitsInStock"));
switch (statusId)
{
case (1):
e.Row.BackColor= System.Drawing.Color.Green;
break;
// other cases follow the same
}
}
}
Put the databinding code in either pageLoad or button click event.
protected void grdMyQ_RowDataBound(object sender, GridViewRowEventArgs e)
{
for (int i = 0; i < grdMyQ.Rows.Count; i++)
{
if (grdMyQ.Rows[i].Cells[13].Text.ToUpper() == "DISCHARGED_PROCESS")
{
grdMyQ.Rows[i].BackColor = Color.Red;
}
}
}

asp.net gridview outside button to save

I have gridview built dynamically at run-time bind to datatable, and button to save gridview data placed outside gridview
1- Create GridView
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
CreateGrid();
}
}
void CreateGrid()
{
int nTransID = Convert.ToInt32(Session["trans_id"]);
//
string strSQL = #"EXEC [dbo].[sp_GetTransaction] " + nTransID;
DataTable dtData = clsGlobal.GetDataTable(strSQL);
//
if (ViewState["dtTransDetail"] == null) ViewState.Add("dtTransDetail", dtData);
else ViewState["dtTransDetail"] = dtData;
//
foreach (DataColumn dc in dtData.Columns)
{
if (dc.ColumnName.Contains("!;"))
{
TemplateField tField = new TemplateField();
tField.ItemTemplate = new AddTemplateToGridView(ListItemType.Item, dc.ColumnName);
//\\ --- template contain textbox
tField.HeaderText = dc.ColumnName;
GridView1.Columns.Add(tField);
}
}
}
This is my template class:
public class AddTemplateToGridView : ITemplate
{
ListItemType _type;
string _colName;
public AddTemplateToGridView(ListItemType type, string colname)
{
_type = type;
_colName = colname;
}
void ITemplate.InstantiateIn(System.Web.UI.Control container)
{
switch (_type)
{
case ListItemType.Item:
TextBox text = new TextBox();
text.ID = "txtAmount";
text.DataBinding += new EventHandler(txt_DataBinding);
container.Controls.Add(text);
break;
}
}
void txt_DataBinding(object sender, EventArgs e)
{
TextBox textBox = (TextBox)sender;
GridViewRow container = (GridViewRow)textBox.NamingContainer;
object dataValue = DataBinder.Eval(container.DataItem, _colName);
if (dataValue != DBNull.Value)
{
textBox.Text = dataValue.ToString();
}
}
}
So i have a gridview with textboxe's all open to edit at once
The problem is, when i click on Save button "which is outside gridview" all textboxe's gone
protected void btnSave_Command(object sender, CommandEventArgs e)
{
for (int nRow = 0; nRow < GridView1.Rows.Count; nRow++)
{
for (int nCol = 0; nCol < GridView1.Columns.Count; nCol++)
{
if (GridView1.Rows[nRow].Cells[nCol].Controls.Count == 0) continue;
//\\ --- Controls.Count always = 0
//\\ --- However each cell contain textbox
//\\ --- textbox disappear after save button clicked
TextBox txt = (TextBox)GridView1.Rows[nRow].Cells[nCol].Controls[0];
}
}
}
It looks like you are not creating the GridView after a postback, and the Save button is causing a postback. You need to dynamically create the GridView on each page load. Also, I have found this documentation on the ASP.NET page lifecycle helpful on numerous occasions.
In the documentation, you will see the slightly unintuitive reason why your code isn't working as you would like - btnSave_Command is not run until after a postback and Page_Load.

Reading selected ITEMS from Dynamically Created ListBox in asp.net

i have created ListBox's Dynamically in a panel and i want to read the selected item from the Listbox created dynamically . below is the code that i used to create the Dynamic Listbox. can anyone please help me how to get the dynamically created listbox and then read the item selected. 'protected void GotoReport_Click(object sender, ImageClickEventArgs e)
{
foreach (TreeNode tndim in tvCubedef.CheckedNodes)
{
lbFilter.Items.Add(tndim.Text);
}
foreach (ListItem item in lbFilter.Items)
{
item.Selected = true;
}
panFilter.Controls.Clear();
connstr2 = System.Configuration.ConfigurationManager.ConnectionStrings["ConnString"].ConnectionString;
conn2.ConnectionString = connstr2;
conn2.Open();
CubeCollection CubeList = conn2.Cubes;
string cb = ddlCubeList.SelectedItem.Text;
foreach (ListItem li in lbFilter.Items)
{
ListBox listb = new ListBox();
ListItem Memlist = new ListItem();
listb.SelectionMode = System.Web.UI.WebControls.ListSelectionMode.Multiple;
listb.Height = 150;
listb.Width = 250;
string Repl1 = li.Value.Replace("[", "");
string Repl2 = Repl1.Replace("]", "");
string[] DimMember = Repl2.Split('.');
foreach (Member dimem in CubeList[cb].Dimensions[DimMember[0]].Hierarchies[DimMember[1]].Levels[DimMember[2]].GetMembers())
{
Memlist.Text = dimem.Name;
listb.Items.Add(Memlist);
panFilter.Controls.Add(listb);
}
}
} '
You need to add the event-handler dynamically:
listb.SelectedIndexChanged += new EventHandler(listb_SelectedIndexChanged);
Of course you also need to provide this method:
protected void listb_SelectedIndexChanged(Object sender, EventArgs e)
{
ListBox listb = (ListBox) sender;
}
Are you recreating this ListBox on every postback (as you should) in page_load at the latest and with same ID as before?

How to get the cell value by column name not by index in GridView in asp.net

I am having a gridview in asp.net and now I want the cell value by the column name but not by the cell index.
How would be it possible by retrieving the cell value by the cell column name
GridView does not act as column names, as that's it's datasource property to know those things.
If you still need to know the index given a column name, then you can create a helper method to do this as the gridview Header normally contains this information.
int GetColumnIndexByName(GridViewRow row, string columnName)
{
int columnIndex = 0;
foreach (DataControlFieldCell cell in row.Cells)
{
if (cell.ContainingField is BoundField)
if (((BoundField)cell.ContainingField).DataField.Equals(columnName))
break;
columnIndex++; // keep adding 1 while we don't have the correct name
}
return columnIndex;
}
remember that the code above will use a BoundField... then use it like:
protected void GridView_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
int index = GetColumnIndexByName(e.Row, "myDataField");
string columnValue = e.Row.Cells[index].Text;
}
}
I would strongly suggest that you use the TemplateField to have your own controls, then it's easier to grab those controls like:
<asp:GridView ID="gv" runat="server">
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:Label ID="lblName" runat="server" Text='<%# Eval("Name") %>' />
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
and then use
string columnValue = ((Label)e.Row.FindControl("lblName")).Text;
Although its a long time but this relatively small piece of code seems easy to read and get:
protected void GridView1_SelectedIndexChanged(object sender, EventArgs e)
{
int index;
string cellContent;
foreach (TableCell tc in ((GridView)sender).HeaderRow.Cells)
{
if( tc.Text.Equals("yourColumnName") )
{
index = ((GridView)sender).HeaderRow.Cells.GetCellIndex(tc);
cellContent = ((GridView)sender).SelectedRow.Cells[index].Text;
break;
}
}
}
You can use the DataRowView to get the column index.
void OnRequestsGridRowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
var data = e.Row.DataItem as DataRowView;
// replace request name with a link
if (data.DataView.Table.Columns["Request Name"] != null)
{
// get the request name
string title = data["Request Name"].ToString();
// get the column index
int idx = data.Row.Table.Columns["Request Name"].Ordinal;
// ...
e.Row.Cells[idx].Controls.Clear();
e.Row.Cells[idx].Controls.Add(link);
}
}
}
For Lambda lovers
protected void GridView_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
var boundFields = e.Row.Cells.Cast<DataControlFieldCell>()
.Select(cell => cell.ContainingField).Cast<BoundField>().ToList();
int idx = boundFields.IndexOf(
boundFields.FirstOrDefault(f => f.DataField == "ColName"));
e.Row.Cells[idx].Text = modification;
}
}
Based on something found on Code Project
Once the data table is declared based on the grid's data source, lookup the column index by column name from the columns collection. At this point, use the index as needed to obtain information from or to format the cell.
protected void gridMyGrid_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
DataTable dt = (DataTable)((GridView)sender).DataSource;
int colIndex = dt.Columns["MyColumnName"].Ordinal;
e.Row.Cells[colIndex].BackColor = Color.FromName("#ffeb9c");
}
}
Header Row cells sometimes will not work. This will just return the column Index. It will help in a lot of different ways. I know this is not the answer he is requesting. But this will help for a lot people.
public static int GetColumnIndexByHeaderText(GridView gridView, string columnName)
{
for (int i = 0; i < gridView.Columns.Count ; i++)
{
if (gridView.Columns[i].HeaderText.ToUpper() == columnName.ToUpper() )
{
return i;
}
}
return -1;
}
A little bug with indexcolumn in alexander's answer:
We need to take care of "not found" column:
int GetColumnIndexByName(GridViewRow row, string columnName)
{
int columnIndex = 0;
int foundIndex=-1;
foreach (DataControlFieldCell cell in row.Cells)
{
if (cell.ContainingField is BoundField)
{
if (((BoundField)cell.ContainingField).DataField.Equals(columnName))
{
foundIndex=columnIndex;
break;
}
}
columnIndex++; // keep adding 1 while we don't have the correct name
}
return foundIndex;
}
and
protected void GridView_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
int index = GetColumnIndexByName(e.Row, "myDataField");
if( index>0)
{
string columnValue = e.Row.Cells[index].Text;
}
}
}
We can get it done in one line of code. No need to loop through anything or call other methods.
protected void GridView_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
string cellValue = e.Row.Cells[e.Row.Cells.GetCellIndex(e.Row.Cells.Cast<DataControlFieldCell>().FirstOrDefault(cell => cell.ContainingField.HeaderText == "columnName"))].Text;
}
}
//get the value of a gridview
public string getUpdatingGridviewValue(GridView gridviewEntry, string fieldEntry)
{//start getGridviewValue
//scan gridview for cell value
string result = Convert.ToString(functionsOther.getCurrentTime());
for(int i = 0; i < gridviewEntry.HeaderRow.Cells.Count; i++)
{//start i for
if(gridviewEntry.HeaderRow.Cells[i].Text == fieldEntry)
{//start check field match
result = gridviewEntry.Rows[rowUpdateIndex].Cells[i].Text;
break;
}//end check field match
}//end i for
//return
return result;
}//end getGridviewValue
It is possible to use the data field name, if not the title so easily, which solved the problem for me. For ASP.NET & VB:
e.g. For a string:
Dim Encoding = e.Row.DataItem("Encoding").ToString().Trim()
e.g. For an integer:
Dim MsgParts = Convert.ToInt32(e.Row.DataItem("CalculatedMessageParts").ToString())
protected void CheckedRecords(object sender, EventArgs e)
{
string email = string.Empty;
foreach (GridViewRow gridrows in GridView1.Rows)
{
CheckBox chkbox = (CheckBox)gridrows.FindControl("ChkRecords");
if (chkbox != null & chkbox.Checked)
{
int columnIndex = 0;
foreach (DataControlFieldCell cell in gridrows.Cells)
{
if (cell.ContainingField is BoundField)
if (((BoundField)cell.ContainingField).DataField.Equals("UserEmail"))
break;
columnIndex++;
}
email += gridrows.Cells[columnIndex].Text + ',';
}
}
Label1.Text = "email:" + email;
}
protected void gvResults_PreRender(object sender, EventArgs e)
{
var gridView = (GridView)sender;
gridView.GetColumnByName("YourDataBoundDataField").Visible = true;
}
Extension:
public static DataControlField GetColumnByName(this GridView gridView, string columnName)
{
int columnIndex = -1;
for (int i = 0; i < gridView.Columns.Count; i++)
{
if (gridView.Columns[i].HeaderText.Trim().Equals(columnName, StringComparison.OrdinalIgnoreCase))
{
columnIndex = i;
break;
}
}
if (columnIndex == -1)
{
throw new ArgumentOutOfRangeException("GridViewRow does not have the column with name: " + columnName);
}
return gridView.Columns[columnIndex];
}
The primary reason this would be difficult is because gridview cells do not have accessible cell names (ugh).
In order to work around this handicap you can make an extension method (mine is in VB.NET, but #Дмитрийh seems to have a similar solution in C#).
To work around this ensure the HeaderText of the gridview cells have the same value as the cellnames and grab the values via that HeaderText name.
Here is extension methods you would need for strings and integers in a VB.NET code snippet that I made
Public Shared Function GetStringByCellName(pGridViewRow As GridViewRow, pCellName As String) As String
For Each myCell As DataControlFieldCell In pGridViewRow.Cells
If myCell.ContainingField.ToString() = pCellName Then
Return myCell.Text
End If
Next
Return Nothing
End Function
And the difference for integers being a parse/cast
Public Shared Function GetIntegerByCellName(pGridViewRow As GridViewRow, pCellName As String) As Integer
For Each myCell As DataControlFieldCell In pGridViewRow.Cells
If myCell.ContainingField.ToString() = pCellName Then
Return Integer.Parse(myCell.Text)
End If
Next
Return Nothing
End Function
And calling the functions would look like this if it were in a class.
Dim columnNamesStringValue As String = ExtensionMethodsClassName.GetStringByCellName(pGridViewRow, "stringOfColumnName")
Dim columnNamesIntegerValue As Integer = ExtensionMethodsClassName.GetIntegerByCellName(pGridViewRow, "stringOfColumnName")
have in mind that you may not always get a value, and instead may get Nothing
Before you (perhaps try to put the value in your database), ensure it is not nothing first by checking that it is not nothing. If you wanted to insert into the database, however, it may be better to return a System.DBNull instead of Nothing from the extension methods I provided.
(DO NOT CHECK AND INSERT THE OTHER NULLS or Nothing AS DBNull'S. DIFFERENT TYPES OF NULL'S AND NOTHINGS ARE NOT EQUAL)
If (columnNamesStringValue IsNot Nothing)

Resources