From my database I am retriving data table like below after making a query to DB.
I my asp.net web form application I am having GridView and it is having BoundField and DropDownList.
I want to bind LectureID to the BoundField and subjects of pariculat lecture into DropDownList.
Have no idea how to do the required binging.
LectureID SubjectName
1 Sub1
1 Sub2
1 Sub3
1 Sub4
2 Sub1
2 Sub4
<asp:GridView ID="grdvDetail" runat="server">
<Columns>
<asp:BoundField HeaderText="LectureID" DataField="LectureID" SortExpression="LectureID">
<HeaderStyle HorizontalAlign="Center" />
<ItemStyle Font-Size="11px" />
</asp:BoundField>
<asp:TemplateField>
<ItemTemplate>
<asp:DropDownList ID="ddlSubject" runat="server">
</asp:DropDownList>
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
DataTable dt = new DataTable();
//Fill DataTable Using SQL Query
grdvDetail.DataSource = dt;
grdvDetail.DataBind();
for (int i = 0; i < grdvDetail.Rows.Count; i++)
{
DropDownList ddlSubject = ((DropDownList)grvProduct.Rows[i].FindControl("ddlSubject"));
DataTable dtDDL = new DataTable();
//Fill DataTable Using SQL Query
ddlSubject.DataSource = dtDDL;
ddlSubject.DataTextField = "SubjectName";
ddlSubject.DataValueField = "SubjectName";
ddlSubject.DataBind();
}
}
}
May be it is not perfect solution. Idea is to create a Key, Value collection from given datatable.
A Dictionary collection is used to keep lecture id as Key and related subjects in a List<string> as Value.
GridView is bind with Dictionary and in RowDataBound event of GridView each dropdownlist is populated as required.
Markup:
<asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False"
onrowdatabound="GridView1_RowDataBound">
<Columns>
<asp:BoundField DataField="Key" HeaderText="Lecture ID" />
<asp:TemplateField HeaderText="Subject Name">
<ItemTemplate>
<asp:DropDownList ID="ddlSubject" runat="server" >
</asp:DropDownList>
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
Code Behind:
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
//test data
DataTable dt = new DataTable();
dt.Columns.Add("LectureID", typeof(int));
dt.Columns.Add("SubjectName");
dt.Rows.Add(1, "Sub1");
dt.Rows.Add(1, "Sub2");
dt.Rows.Add(1, "Sub3");
dt.Rows.Add(1, "Sub4");
dt.Rows.Add(2, "Sub1");
dt.Rows.Add(2, "Sub4");
dt.AcceptChanges();
//Bind with GridView with Dictionary collection
GridView1.DataSource = GetDictionary(dt);
GridView1.DataBind();
}
}
//get a dictionary of distinct lectureID
private Dictionary<int, List<string>> GetDictionary(DataTable dt)
{
var dictionary = new Dictionary<int, List<string>>();
foreach (DataRow dr in dt.Rows)
{
int iKey = Convert.ToInt32(dr["LectureID"]);
if (dictionary.ContainsKey(iKey))
{
List<string> lst = dictionary[iKey] as List<string>;
lst.Add(dr["SubjectName"].ToString());
dictionary[iKey] = lst;
}
else
{
var lst = new List<string>();
lst.Add(dr["SubjectName"].ToString());
dictionary.Add(iKey, lst);
}
}
return dictionary;
}
Row Data Bound Event:
protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow &&
e.Row.DataItem != null)
{
DropDownList ddl = e.Row.FindControl("ddlSubject") as DropDownList;
ddl.DataSource = ((KeyValuePair<int, List<string>>)e.Row.DataItem).Value;
ddl.DataBind();
}
}
Result Distinct LectureID with respective Subjects in DropDownList:
Related
This is a basic question but i didn't find appropriate answers : I have a dataset that is shown in dataGridview and it contains a column Is_Alarm of type bit (boolean) , i want to insert a Select all checkbox in that column.
I have seen many solutions but they are all about inserting a new checkbox in datagridView .
What i want is insert it after columns are shown , here's my code :
SqlDataAdapter adap= new SqlDataAdapter(select_query,con);
ds = new DataSet();
adap.Fill(ds, "Event_test");
dataGridView1.DataSource = ds.Tables[0];
I had same issue what I did might be useful for you
This is code used for gridview
<asp:GridView ID="GridView1" runat="server" EnableModelValidation="True">
<Columns>
<asp:TemplateField>
<EditItemTemplate>
<asp:CheckBox ID="CheckBox1" runat="server" />
</EditItemTemplate>
<ItemTemplate>
<asp:CheckBox ID="CheckBox1" runat="server" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
Next I Loaded data( MyTable field had id,username,email etc)
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
con.Open();
SqlDataAdapter adap = new SqlDataAdapter("Select * From UserInfo", con);
DataSet ds = new DataSet();
adap.Fill(ds);
con.Close();
GridView1.DataSource = ds.Tables[0];
GridView1.DataBind();
}
}
For getting Ids of selected records I used few lines which is described here
http://www.aspsnippets.com/Articles/GridView-with-CheckBox-Get-Selected-Rows-in-ASPNet.aspx and modified in this way
protected void btnCheckSelected_Click(object sender, EventArgs e)
{
foreach (GridViewRow row in GridView1.Rows)
{
if (row.RowType == DataControlRowType.DataRow)
{
CheckBox chkRow = (row.Cells[0].FindControl("CheckBox1") as CheckBox);
if (chkRow.Checked)
{
string ids = row.Cells[1].Text;
ListBox1.Items.Add(ids);
}
}
}
}
I have created one gridview with custom column and want to perform sorting on them. When I click on column then no event is firing for sorting.
Below is the code which I have written
For .aspx page
<asp:GridView ID="grdConfigureCustomers" runat="server" AlternatingRowStyle- BackColor="Aqua" Width="1300px"
OnRowCommand="grdConfigureCustomers_RowCommand" OnRowEditing="grdConfigureCustomers_RowEditing"
OnRowUpdating="grdConfigureCustomers_RowUpdating" OnRowCancelingEdit="grdConfigureCustomers_RowCancelingEdit"
AutoGenerateColumns="false" AllowPaging="true" PageSize="5"
OnRowDeleting="grdConfigureCustomers_RowDeleting" ShowFooter="true"
onpageindexchanging="grdConfigureCustomers_PageIndexChanging" OnSorting="grdConfigureCustomers_Sorting" AllowSorting="true">
<HeaderStyle BackColor="AliceBlue" />
<Columns>
<asp:TemplateField HeaderText="Customer ID">
<ItemTemplate>
<asp:Label ID="lblCustomerId" runat="server" Text='<%# Eval("Customer_ID") %>'></asp:Label>
</ItemTemplate>
<FooterTemplate>
<asp:TextBox ID="txtAddCustomerId" runat="server"></asp:TextBox><span style="color:Red;">*</span>
</FooterTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
For .aspx.cs page
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
LoadCustomerConfigurationGridView();
}
}
private void LoadCustomerConfigurationGridView()
{
DataTable dt = new DataTable();
dt = sqlHelper.GetCustomerListInformation();
grdConfigureCustomers.DataSource = dt;
grdConfigureCustomers.DataBind();
Session["data"] = dt;
}
private void LoadCustomerConfigurationGridView(string srtexpr, string direc)
{
DataTable dt = new DataTable();
dt = sqlHelper.GetCustomerListInformation();
DataView dv = new DataView(dt);
dv.Sort = srtexpr + " " + direc;
grdConfigureCustomers.DataSource = dv;
grdConfigureCustomers.DataBind();
Session["data"] = dt;
}
protected void grdConfigureCustomers_Sorting(object sender, GridViewSortEventArgs e)
{
switch (e.SortExpression)
{
case "DateLogged":
if (e.SortDirection == SortDirection.Ascending)
{
LoadCustomerConfigurationGridView("DateLogged", "ASC");
}
else
{
LoadCustomerConfigurationGridView();
}
break;
}
}
Please let me know what I missed for sorting. Thanks in advance.
You need to specify the SortExpression property in the TemplateField like this:
<asp:TemplateField HeaderText="Customer ID" SortExpression="Customer_ID">
You need to enable sorting. EnableSorting="true" in your asp.net:Gridview.
I want to add a new blank row to the gridview after binding as seen in the picture when clicking the link button below. The textboxes inside the gridview should remain the same if there is any data entered in it. I just want to add one row.
you can try the following code
protected void Button1_Click(object sender, EventArgs e)
{
DataTable dt = new DataTable();
if (dt.Columns.Count == 0)
{
dt.Columns.Add("PayScale", typeof(string));
dt.Columns.Add("IncrementAmt", typeof(string));
dt.Columns.Add("Period", typeof(string));
}
DataRow NewRow = dt.NewRow();
NewRow[0] = TextBox1.Text;
NewRow[1] = TextBox2.Text;
dt.Rows.Add(NewRow);
GridView1.DataSource = dt;
GridViewl.DataBind();
}
here payscale,incrementamt and period are database field name.
You can run this example directly.
aspx page:
<asp:GridView ID="grd" runat="server" DataKeyNames="PayScale" AutoGenerateColumns="false">
<Columns>
<asp:TemplateField HeaderStyle-HorizontalAlign="Left" HeaderText="Pay Scale">
<ItemTemplate>
<asp:TextBox ID="txtPayScale" runat="server" Text='<%# Eval("PayScale") %>'></asp:TextBox>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderStyle-HorizontalAlign="Left" HeaderText="Increment Amount">
<ItemTemplate>
<asp:TextBox ID="txtIncrementAmount" runat="server" Text='<%# Eval("IncrementAmount") %>'></asp:TextBox>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderStyle-HorizontalAlign="Left" HeaderText="Period">
<ItemTemplate>
<asp:TextBox ID="txtPeriod" runat="server" Text='<%# Eval("Period") %>'></asp:TextBox>
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
<asp:Button ID="btnAddRow" runat="server" OnClick="btnAddRow_Click" Text="Add Row" />
C# code:
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
grd.DataSource = GetTableWithInitialData(); // get first initial data
grd.DataBind();
}
}
public DataTable GetTableWithInitialData() // this might be your sp for select
{
DataTable table = new DataTable();
table.Columns.Add("PayScale", typeof(string));
table.Columns.Add("IncrementAmount", typeof(string));
table.Columns.Add("Period", typeof(string));
table.Rows.Add(1, "David", "1");
table.Rows.Add(2, "Sam", "2");
table.Rows.Add(3, "Christoff", "1.5");
return table;
}
protected void btnAddRow_Click(object sender, EventArgs e)
{
DataTable dt = GetTableWithNoData(); // get select column header only records not required
DataRow dr;
foreach (GridViewRow gvr in grd.Rows)
{
dr = dt.NewRow();
TextBox txtPayScale = gvr.FindControl("txtPayScale") as TextBox;
TextBox txtIncrementAmount = gvr.FindControl("txtIncrementAmount") as TextBox;
TextBox txtPeriod = gvr.FindControl("txtPeriod") as TextBox;
dr[0] = txtPayScale.Text;
dr[1] = txtIncrementAmount.Text;
dr[2] = txtPeriod.Text;
dt.Rows.Add(dr); // add grid values in to row and add row to the blank table
}
dr = dt.NewRow(); // add last empty row
dt.Rows.Add(dr);
grd.DataSource = dt; // bind new datatable to grid
grd.DataBind();
}
public DataTable GetTableWithNoData() // returns only structure if the select columns
{
DataTable table = new DataTable();
table.Columns.Add("PayScale", typeof(string));
table.Columns.Add("IncrementAmount", typeof(string));
table.Columns.Add("Period", typeof(string));
return table;
}
protected void TableGrid_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowIndex == -1 && e.Row.RowType == DataControlRowType.Header)
{
GridViewRow gvRow = new GridViewRow(0, 0, DataControlRowType.DataRow,DataControlRowState.Insert);
for (int i = 0; i < e.Row.Cells.Count; i++)
{
TableCell tCell = new TableCell();
tCell.Text = " ";
gvRow.Cells.Add(tCell);
Table tbl = e.Row.Parent as Table;
tbl.Rows.Add(gvRow);
}
}
}
try using the cloning technique.
{
DataGridViewRow row = (DataGridViewRow)yourdatagrid.Rows[0].Clone();
// then for each of the values use a loop like below.
int cc = yourdatagrid.Columns.Count;
for (int i2 = 0; i < cc; i2++)
{
row.Cells[i].Value = yourdatagrid.Rows[0].Cells[i].Value;
}
yourdatagrid.Rows.Add(row);
i++;
}
}
This should work. I'm not sure about how the binding works though. Hopefully it won't prevent this from working.
If you are using dataset to bind in a Grid, you can add the row after you fill in the sql data adapter:
adapter.Fill(ds);
ds.Tables(0).Rows.Add();
I am trying to place an asp gridview inside an asp datalist. For each item in the datalist I would like certain values from another database table to be returned.
I have written the following code, but the gridview returns not data (I can confirm there is records in the database and the stored procedure is correct). The asp datalist is working fine.
What am I doing wrong that is not populating the gridview?
<asp:DataList runat="server" id="listResponses" DataKeyField="QuestionID" CssClass="confirm" OnItemDataBound="listResponses_ItemDataBound">
<ItemTemplate>
<h3 class="confirm new">Question <asp:Label ID="lblaOrder" runat="server" Text='<%# Container.ItemIndex + 1 %>'></asp:Label></h3>
<div class="confirm_question">
<asp:Label ID="lblOrder" runat="server" Text='<%# Container.ItemIndex + 1 %>'></asp:Label>
<p class="confirm"><%# DataBinder.Eval(Container.DataItem, "QuestionText") %></p>
</div> <!-- end confirm_question -->
<asp:GridView runat="server" ID="gridResponses" DataKeyNames="QuestionID"">
<Columns>
<asp:BoundField DataField="AnswerTitle" HeaderText="ID" HeaderStyle-Width="80px" ItemStyle-CssClass="bo"></asp:BoundField>
<asp:BoundField DataField="Responses" HeaderText="Response Count" HeaderStyle-Width="150px" />
</Columns>
</asp:GridView>
</ItemTemplate>
</asp:DataList>
And here is the code behind.
public partial class questionnaire_responses : System.Web.UI.Page
{
OsqarSQL GetData;
DataTable DT;
private string _productConnectionString;
private SqlConnection _productConn;
protected void Page_Load(object sender, EventArgs e)
{
string questionnaireId = Session["qID"].ToString();
int qid = Convert.ToInt32(questionnaireId);
GetData = new OsqarSQL();
string name = GetData.GetQuestionnaireName(qid);
lblQuestionnaireName.Text = name;
if (!IsPostBack)
{
DT = GetData.GetQuestionNameDataList(qid);
listResponses.DataSource = DT;
listResponses.DataBind();
}
}
private void BindGrid(GridView GridView, int questionId)
{
DataTable dt = new DataTable();
GetData.GetAnswerTitle(questionId);
GridView.DataSource = dt;
GridView.DataBind();
}
protected void listResponses_ItemDataBound(object sender, DataListItemEventArgs e)
{
GridView gridResponses=(GridView)e.Item.FindControl("gridResponses");
BindGrid(gridResponses, (int)listResponses.DataKeys[e.Item.ItemIndex]);
}
}
//Method from the data access class
public DataTable GetAnswerTitle(int QuestionId)
{
string returnValue = string.Empty;
SqlCommand myCommand = new SqlCommand("GetAnswer", _productConn);
myCommand.CommandType = CommandType.StoredProcedure;
,yCommand.Parameters.Add(new SqlParameter("#QUESTION_ID", SqlDbType.Int));
myCommand.Parameters[0].Value = QuestionId;
return createDataTable(getData(myCommand));
}
You've created an empty DataTable as DataSource for your GridView.
Replace
DataTable dt = new DataTable();
GetData.GetAnswerTitle(questionId);
GridView.DataSource = dt;
with this
DataTable dt = GetData.GetAnswerTitle(questionId);
GridView.DataSource = dt;
I have a data table which already has some values, plus it is getting values from a textbox below.
Now my problem is when i dont enter a value in the textbox it still enters in the data table.
I dont want it to do that..
The code can run on any machine... any suggestions????
Thanks
public partial class WebForm6 : System.Web.UI.Page
{
DataTable dt;
protected void Page_Load(object sender, EventArgs e)
{
// Initialize a DataTable
if (!Page.IsPostBack)
{
dt = new DataTable();
// Initialize DataColumn
DataColumn myDataColumn = new DataColumn();
//// initialize a new instance of DataColumn to add another column with different properties.
//myDataColumn = new DataColumn();
myDataColumn.ColumnName = "firstName";
// set DataType property of the column as String
myDataColumn.DataType = System.Type.GetType("System.String");
// Add and Create a Second DataColumn
dt.Columns.Add(myDataColumn);
// create a new row using NewRow() function of DataTable.
// dataRow object will inherit the schema of myDataTable to create a new row
DataRow dataRow = dt.NewRow();
dataRow["firstName"] = "John";
// add new data row to the data table.
dt.Rows.Add(dataRow);
// similarly adds the second row to the DataTable
dataRow = dt.NewRow();
dataRow["firstName"] = "Will";
dt.Rows.Add(dataRow);
Session["data"] = dt;
GridView1.DataSource = dt;
GridView1.DataBind();
}
}
protected void btnSubmit_Click(object sender, EventArgs e)
{
if (Session["Data"] == null)
{
dt.Columns.Add("firstName");
BindtoGridViewFromTextBoxes(dt);
ClearControls();
}
else
{
dt = (DataTable)Session["Data"];
BindtoGridViewFromTextBoxes(dt);
ClearControls();
}
} private void ClearControls()
{
txtName.Text = String.Empty;
}
private void BindtoGridViewFromTextBoxes(DataTable dt)
{
DataRow dr;
dr = dt.NewRow();
dr["firstName"] = txtName.Text.ToString();
dt.Rows.Add(dr);
Session["Data"] = dt;
GridView1.DataSource = dt;
GridView1.DataBind();
}
and on .aspx page
<asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False">
<asp:TemplateField>
<EditItemTemplate>
<asp:CheckBox ID="CheckBox1" runat="server" />
</EditItemTemplate>
<ItemTemplate>
<asp:CheckBox ID="CheckBox1" runat="server" />
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="First Name">
<EditItemTemplate>
<asp:TextBox ID="TextBox1" runat="server" Text='<%# Bind("firstName") %>'></asp:TextBox>
</EditItemTemplate>
<ItemTemplate>
<asp:Label ID="Label1" runat="server" Text='<%# Bind("firstName") %>'></asp:Label>
</ItemTemplate>
</asp:TemplateField>
any help....??
Change your method to be this:
private void BindtoGridViewFromTextBoxes(DataTable dt)
{
if (!String.IsNullOrEmpty(txtname.Text))
{
DataRow dr = dt.NewRow();
dr["firstName"] = txtName.Text;
dt.Rows.Add(dr);
Session["Data"] = dt;
}
GridView1.DataSource = dt;
GridView1.DataBind();
}