Simple question regarding table(single column in this case) population.
As much as it may seem like an easy question, I've never been involved in the front-end area, so here it goes.
The layout is 2 columns and 8 rows.
Something like.
Name A
LastName B
Age C
BirthDate D
...
Column 1 are stable, "titles" if you want, that won't change.
A,B,C,D are the result of querys to a database. So, options I can think of are:
Draw a 2Column - 8Row table and place TextBoxes in A,B,C,D... fields. So later on they can be populated with the results of the query (This option is not the most "beautiful" one since TextBoxes alter the design intented to be absorved by the whole page using .CSS files.
Set a datagrid. The problem here I think is that some of the A,B,C,D fields will have to be changed for later query-usage. And I'm not sure if Datagrids are ment for that.
Is there a "good-way" for me to solve this issue?
Thanks in advance.
EDIT.
A,B,C,D data is held in a DataSet.
To me, the way you're describing the data doesn't really lend itself too well for a DataGrid. This control works best for data that you plan to display in a standard tabular style, where the column names go across the top and then you display the row(s) of values underneath. It's also a little unclear to me if you are intending to bind one or many instances of your Object (which I will just call Person for now) to the UI.
Let's go ahead and define that object:
public class Person {
public String Name { get; set; }
public String LastName { get; set; }
public int Age { get; set; }
public DateTime BirthDate { get; set; }
}
To bind a single instance of Person to your UI, a simple HTML table should work fine. I'm using TextBoxes to display the values here, but if you don't need to edit them then just use Labels instead.
<table>
<tr><td>Name:</td><td><asp:TextBox ID="txtName" runat="server" /></td></tr>
<tr><td>Last Name:</td><td><asp:TextBox ID="txtLastName" runat="server" /></td></tr>
<tr><td>Age:</td><td><asp:TextBox ID="txtAge" runat="server" /></td></tr>
<tr><td>Birthdate:</td><td><asp:TextBox ID="txtBirthDate" runat="server" /></td></tr>
</table>
It's pretty trivial at this point to bind the properties from Person to their respective controls on the page using the code-behind.
If you wanted to use this same layout to display multiple instances of Person on a page, go with the ASP.net Repeater. The markup for this would look more like:
<asp:Repeater ID="repPeople" runat="server">
<ItemTemplate>
<table>
<tr><td>Name:</td><td><asp:TextBox ID="txtName" runat="server" Text='<%# Eval("Name") %>' /></td></tr>
<tr><td>Last Name:</td><td><asp:TextBox ID="txtLastName" runat="server" Text='<%# Eval("LastName") %>' /></td></tr>
<tr><td>Age:</td><td><asp:TextBox ID="txtAge" runat="server" Text='<%# Eval("Age") %>' /></td></tr>
<tr><td>Birthdate:</td><td><asp:TextBox ID="txtBirthDate" runat="server" Text='<%# String.Format("{0:d}", Eval("BirthDate")) %>' /></td></tr>
</table>
</ItemTemplate>
</asp:Repeater>
In the code-behind, you just bind a collection of Person to the DataSource property on the Repeater:
protected void Page_Load(object sender, EventArgs e) {
// A simple example using Page_Load
List<Person> people = new List<Person>();
for (int i = 0; i < 10; i++) {
people.Add(new Person() {Name = "Test", Age = 10, BirthDate=DateTime.Now, LastName = "Test"});
}
if (!IsPostBack) {
repPeople.DataSource = people;
repPeople.DataBind();
}
}
Note: You could accomplish a similar layout using CSS instead of tables, however the same principles apply between binding a single vs multiple objects. Just replace the table layout in this example with whatever markup you ultimately define.
There's a table control in WebForms that you should be able to populate from a DataSet see the MSDN docs: http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.table.aspx
Related
I propose my case studies:I am developing a table in ASP.NET in which the fields taken from the DB are displayed (in this case Nome, Cognome, Azienda, Provincia) I find myself managing three functions: add, delete and update.
The first two solved without problems, but I'm having problems with the update.To manage it I developed a function in the back end (subsequently called by an AJAX on the client side) that does nothing but use a SELECT query to select the row taken into consideration (based on the ID) and check if it is present on the DB through a reader. Once this was done I thought I would retrieve the values of the fields of that row and insert them in the corresponding text areas.
I can't find a solution to complete the function. I tried with name.InnerHTML (regarding the name field) but it says the name field has no reference.
C# code:
[WebMethod]
public static void Popoladati(string ch)
{
int chiavInt = Convert.ToInt32(ch);
string queryString = "SELECT * FROM Elenco WHERE Id_Identificazione = #chiavInt";
int i = 0;
using (SqlConnection connection = new SqlConnection(ConfigurationManager.ConnectionStrings["coso"].ConnectionString))
{
connection.Open();
using (SqlCommand command = new SqlCommand(queryString, connection))
{
SqlParameter parameter = new SqlParameter("chiavInt" , chiavInt);
command.Parameters.Add(parameter);
SqlDataReader reader = command.ExecuteReader();
while (reader.Read())
{
i++;
}
reader.Close();
}
}
AJAX request:
function edit(chiav) {
let param = { ch: chiav };
$.ajax({
type: "POST",
url: "Update.aspx/Popoladati",
data: JSON.stringify(param),
contentType: "application/json; charset=utf-8",
dataType: "json",
global: false,
async: false,
function(a) {
return a.d;
}
});
window.location.href = "Update.aspx?Id_Identificazione=" + chiav;
}
I do not know if I have been clear, in case let me know that I will try to explain myself better
Well, you first should show how you displaying that table.
You can use gridview, listview, or a repeater. I HIGH recommend you use one of these for the display of data (since then you can with relative ease send the edited data back to the database).
So here is a example - I used listview. I dragged listview on the page. clicked on the listview, and used the builder to build the database query and connection.
I then delete the edit template, alternating template, and also delete the data source control that will be dropped on the page. (and REMOVE the data source setting in the list view control property sheet. I do this since this generates all the markup for me, and thus only takes less then 5 minutes of time.
so, now we have this mark up:
<asp:ListView ID="ListView1" runat="server" DataKeyNames="ID">
<ItemTemplate>
<tr style="">
<td><asp:TextBox ID="FirstName" runat="server" Text='<%# Eval("FirstName") %>' /></td>
<td><asp:TextBox ID="LastName" runat="server" Text='<%# Eval("LastName") %>' /></td>
<td><asp:TextBox ID="HotelName" runat="server" Text='<%# Eval("HotelName") %>' /></td>
<td><asp:TextBox ID="City" runat="server" Text='<%# Eval("City") %>' /></td>
<td><asp:CheckBox ID="Active" runat="server" Checked='<%# Eval("Active") %>' /></td>
</tr>
</ItemTemplate>
<LayoutTemplate>
<table id="itemPlaceholderContainer" runat="server" border="0" style="">
<tr runat="server" style="">
<th runat="server">FirstName</th>
<th runat="server">LastName</th>
<th runat="server">HotelName</th>
<th runat="server">City</th>
<th runat="server">Active</th>
</tr>
<tr id="itemPlaceholder" runat="server"></tr>
</table>
</LayoutTemplate>
</asp:ListView>
<br />
<asp:Button ID="cmdSave" runat="server" Text="Save" />
Ok, not much markup. The code to fill this view? We have this:
private DataTable rstTable = new DataTable();
protected void Page_Load(object sender, System.EventArgs e)
{
if (IsPostBack == false)
{
LoadGrid();
ViewState("MyTable") = rstTable;
}
else
rstTable = ViewState("MyTable");
}
public void LoadGrid()
{
string strSQL;
strSQL = "SELECT ID, FirstName, LastName, HotelName, City, Active from tblHotels ORDER BY HotelName";
using (SqlCommand cmdSQL = new SqlCommand(strSQL,
new SqlConnection(My.Settings.TEST3)))
{
cmdSQL.Connection.Open();
rstTable.Load(cmdSQL.ExecuteReader);
ListView1.DataSource = rstTable;
ListView1.DataBind();
}
}
}
Note careful how we have a class (form level) table variable - and we persist it in view state (you could also use session().
Ok, now, so far VERY VERY little code. When we run the above, we get this:
Ok, so now we need the code for the save button. The user can edit, change - in fact tab quite much around almost like a spreadsheet. To save the edits, then the user can hit the save button. The code for the save button is thus now this:
protected void cmdSave_Click(object sender, EventArgs e)
{
// move values from list view back to table.
foreach (ListViewDataItem vRow in ListView1.Items)
{
var OneRow = rstTable(vRow.DataItemIndex);
OneRow("FirstName") = (TextBox)vRow.FindControl("FirstName").Text;
OneRow("LastName") = (TextBox)vRow.FindControl("LastName").Text;
OneRow("HotelName") = (TextBox)vRow.FindControl("HotelName").Text;
OneRow("City") = (TextBox)vRow.FindControl("City").Text;
OneRow("Active") = (CheckBox)vRow.FindControl("Active").Checked;
}
// now send table chagnes back to database
using (SqlCommand cmdSQL = new SqlCommand("SELECT ID, FirstName, LastName, HotelName, City, Active from tblHotels where ID = 0", new SqlConnection(My.Settings.TEST3)))
{
SqlDataAdapter da = new SqlDataAdapter(cmdSQL);
SqlCommandBuilder sqlBuild = new SqlCommandBuilder(da);
da.Update(rstTable);
}
}
So what we do is pull the changes back from the list view into the table, and then use a data adaptor "update" command to save all of the changes back to the database in ONE shot!
You can of course toss in say a un-do button - that would simply just call load grid again, and thus un-do any edits.
So, as this point, you really don't need ajax, and you don't actually need MUCH code at all.
Also the above approach works equal well for a gridview, or Repater control.
I tend to like the listview - it does generate more mark-up out of the box, but I just go on a quite delete markup party for the list view. I prefer the listview since you do NOT need to wrap each standard .net control inside of a "template control" over and over - which I find a pain.
So the above concept?
You create a data table. Pull the data you want to edit into that table. You then bind the table to the gridview/listview/repeater for display (and this allows editing).
to save?
You pull data back from the data repeating item to the table. And then use the data adaptor to update ALL changes in ONE shot - this is not only faster, less code, less hassle, but the data adaptor is smart, and for rows not changed, then no update sql is generated behind the scenes.
The total code we write? VERY little, and we thus now have a data editing system that allows you to edit such data - and it behaves darn near like a spreadsheet, and you can even tab around to move the cursor.
So, this approach not only saves world poverty in terms of the amount of code, but it also means that you can edit the whole grid, and save the whole grid in one simple operation.
I have a table with headers(example): Group, DisplayName, EditableData, description.
I have been trying for the last few days to learn repeaters to sort the information based on the Group so I can get something that looks like the following layout. This is a user control I am trying to put together.
Group1
------------------
Name1 EditableData Some Description
Name2 EditableData Some Description
Group2
------------------
Name3 EditableData Some Description
Name4 EditableData Some Description
I have looked a the following other examples online:
Nested repeaters - grouping data and
Nested Repeaters in ASP.NET
I believe I do not properly understand how repeaters work enough to deal with nesting or datasource.
<asp:Repeater ID="Repeater1" runat="server">
<ItemTemplate>
Group: <%#Eval("Group")%><br />
<%--Nested Repeater would go here for all the children info for each "Group"--%>
</ItemTemplate>
</asp:Repeater>
Using DISTINCT in my SQL to just retrieve "Group" leaves me with the proper groups without repeats and I guess I could just instead set the groups in labels and then later make repeaters for each specific label... This seems terrible when I may later update editableData back to the database.
What I really want I guess is at least a link to a walkthrough that explains how repeaters work along with Eval() and datasources. I mean, code to do everything I need to complete this first step in my project would be perfect ;P But I also want to be able to understand these better as I am probably going to be using them often in the near future.
I once encountered the same issue where I was to sort the data by group and I had to display the common items in a grouped segment.
There are of-course multiple ways of how you retrieve data, for example, you can get Distinct Group Names and bind it to the repeater and then on ItemDataBound event you can execute and get other elements like this:
<asp:Repeater runat="server" ID="rptrGroups" OnItemDataBound="rptrGroups_ItemDataBound">
<ItemTemplate>
<asp:Label runat="server" ID="lblGroupName" Text='<%# Eval("GroupName") %>' />
<asp:GridView runat="server" ID="gv">
</asp:GridView>
</ItemTemplate>
</asp:Repeater>
protected void rptrGroups_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
if (e.Item.ItemType == ListItemType.Item)
{
var lblGroupName = (Label)e.Item.FindControl("lblGroupName");
GridView gv = (GridView)e.Item.FindControl("table");
var dataTable = FetchDataWithGroupName(lblGroupName.Text); // Method that fetches data with groupname.
gv.DataSource = dataTable;
gv.DataBind();
}
}
This is not a recommended way because it goes to database, runs query, and then fetches data for each item (if you are fetching this data from db). If you have thousands of Groups then it will make db calls for thousands of times which is a bad thing.
The second solution is, you design a model and feed a custom model that will do the job. Let me explain it by a sample model:
public class GroupedModel
{
public string GroupName {get; set;}
public List<NestedData> TableData {get; set;}
}
public class NestedData
{
public string Id {get; set;}
// Your columns here...
}
Then query and initialize list of GroupedModel class then feed it to the repeater. Let me do it with some dummy data.
var tableData = new List<NestedData>();
var nestedData1 = new NestedData { Id = "1" };
var nestedData2 = new NestedData { Id = "2" };
tableData.Add(nestedData1);
tableData.Add(nestedData2);
var groupedModel = new GroupedModel
{
GroupName = "Group1",
TableData = tableData
};
var listGroupedModel = new List<GroupedModel>();
listGroupedModel.Add(groupedModel);
rptrGroups.DataSource = listGroupedModel;
Then modify the markup like this:
<asp:Repeater runat="server" ID="rptrGroups">
<ItemTemplate>
<asp:Label runat="server" ID="lblGroupName" Text='<%# Eval("GroupName") %>' />
<asp:GridView runat="server" ID="gv" DataSource='<%# ((GroupedModel)Container.DataItem).TableData %>'>
</asp:GridView>
</ItemTemplate>
</asp:Repeater>
I find that just using a gridview or list view works rather nice. However, DO NOT attempt to use the grouping feature - as it is for placing items across the page, not down.
Lets make this really simple!
Ok, so I have a list of Hotels, but I want to group by city.
So, you build a query like this:
Dim strSQL As String =
"SELECT ID, FirstName, LastName, HotelName, City FROM tblHotels ORDER BY City, HotelName"
GridView1.DataSource = Myrst(strSQL)
GridView1.DataBind()
Ok, so that fills out our grid view. We get this:
So far, two lines of code!
But, we want to group by City.
So at the forms class level, add simple var:
Public Class HotelGroupGrid
Inherits System.Web.UI.Page
Dim LastCity As String <----- this one
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If IsPostBack = False Then
LastCity = ""
Call LoadGrid()
End If
End Sub
Ok, so now on the data item bind event, simply add a NEW row.
The code looks like this:
If e.Row.RowType = DataControlRowType.DataRow Then
' if grouping = 1 then create a new row!
Dim gvRow As DataRowView = DirectCast(e.Row.DataItem, DataRowView)
If gvRow("City") <> LastCity Then
LastCity = gvRow("City")
' insert a new row for grouping header
Dim MyRow As New GridViewRow(-1, -1, DataControlRowType.DataRow, DataControlRowState.Normal)
Dim MyCel As New TableCell()
'MyCel.Width = Unit.Percentage(100)
Dim MyTable As Table = e.Row.Parent
MyCel.ColumnSpan = MyTable.Rows(0).Controls.Count
Dim MyLable As New Label
MyLable.Text = "<h2>" & gvRow("City") & "</h2>"
MyCel.Controls.Add(MyLable)
MyRow.Cells.Add(MyCel)
MyTable.Rows.AddAt(MyTable.Rows.Count - 1, MyRow)
End If
End If
Now, above is a "bit" of a chunk to chew on - but still not a lot of code.
So, now when we run above, we get this:
Our grid view markup looks like this:
<asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False" DataKeyNames="ID">
<Columns>
<asp:BoundField DataField="City" HeaderText="City" InsertVisible="False" ReadOnly="True" SortExpression="ID" />
<asp:BoundField DataField="ID" HeaderText="ID" InsertVisible="False" ReadOnly="True" SortExpression="ID" />
<asp:BoundField DataField="FirstName" HeaderText="FirstName" SortExpression="FirstName" />
<asp:BoundField DataField="LastName" HeaderText="LastName" SortExpression="LastName" />
<asp:BoundField DataField="HotelName" HeaderText="HotelName" SortExpression="HotelName" />
</Columns>
</asp:GridView>
So, not too bad.
If you decide to use a listview? Then the code becomes quite a bit less, but the markup for listview is quite a handfull.
All we do is create a row that is our heading, and now show, or hide that row based on the start of new grouping.
So, if one decides to use a list view? Then we get this:
(I assume you use the databind wizards - your not possibly typing in the markup by hand - right? - saving world poverty here)
So, for a list view (and I think the list view is BETTER, since the layout options for that heading row is wide open to any kind markup and extra controls you dream up.
So, the markup (generated - and then chopped out the fat) is this:
<asp:ListView ID="ListView1" runat="server" DataKeyNames="ID">
<EmptyDataTemplate>
<table runat="server" style="">
<tr><td>No data was returned.</td></tr>
</table>
</EmptyDataTemplate>
<ItemTemplate>
<tr id="GroupHeading" runat="server" style="display:none">
<td colspan="4">
<h2><asp:Label ID="City" runat="server" Text='<%# Eval("City") %>' /></h2>
</td>
</tr>
<tr>
<td><asp:Label ID="IDLabel" runat="server" Text='<%# Eval("ID") %>' /></td>
<td><asp:Label ID="FirstNameLabel" runat="server" Text='<%# Eval("FirstName") %>' /></td>
<td><asp:Label ID="LastNameLabel" runat="server" Text='<%# Eval("LastName") %>' /></td>
<td><asp:Label ID="HotelNameLabel" runat="server" Text='<%# Eval("HotelName") %>' /></td>
</tr>
</ItemTemplate>
<LayoutTemplate>
<table id="itemPlaceholderContainer" runat="server" border="0" style="">
<tr runat="server">
<th runat="server">ID</th>
<th runat="server">FirstName</th>
<th runat="server">LastName</th>
<th runat="server">HotelName</th>
</tr>
<tr id="itemPlaceholder" runat="server">
</tr>
</table>
</LayoutTemplate>
</asp:ListView>
Now no question that the listview spits out a lot more markup - but we now have a full row for the heading. So we get this:
But, now our code simply will hide or show that "extra" row we have in the marketup.
And it quite simple now:
If e.Item.GetType = GetType(ListViewDataItem) Then
Dim MyRow As HtmlTableRow = e.Item.FindControl("GroupHeading")
Dim lblCity As Label = MyRow.FindControl("City")
If lblCity.Text <> LastCity Then
LastCity = lblCity.Text
' Hide/show group heading
MyRow.Style("display") = "normal"
Else
MyRow.Style("display") = "none"
End If
End If
So the trick in most cases is to simply layout that extra row item, and then on the item data bound event you simply hide or show that heading part.
Ok I have a many to many relationship like this:
Walk = {WalkID, title, ...., (Navigation Properties) Features}
Feature = {FeatureID, featureName, description, (Navigation Properties) DogWalks}
I do of course have a junction table, but EF assumes this thus it is not shown in my edmx diagram:
WalkFeatures = {WalkID, FeatureID} //junction, both FK
So using LINQ with EF, I am now trying to grab the features for the Walk at WalkID=xx.
This is my formview:
<asp:FormView ID="FormView1" runat="server" ItemType="Walks.DAL.Walk" SelectMethod="FormView1_GetItem">
<ItemTemplate>
<h1><%# Item.Title %></h1>
...
</ItemTemplate>
</asp:FormView
<asp:Label ID="lbFeatures" runat="server" Text="Label"></asp:Label>
And selectMethod:
public Walks.DAL.Walk FormView1_GetItem([QueryString("WalkID")] int? WalkID)
{
using (WalkContext db = new WalkContext())
{
var walk = (from n in db.Walks.Include("Features")
where n.WalkID == WalkID
select n).SingleOrDefault();
foreach(var f in walk.Features){
lbFeatures.Text += f.FeatureName + "<br/>";
}
return walk;
}
}
The code runs fine, but is there a way that I can display the Walk.Features directly inside the <ItemTemplate> of the formview rather than using a label and a loop? Can the attribute be directly binded like the other properties in the .aspx page?
I have also used this new feature not that extensively but just gave it a try for this particular scenario and this is what I have:-
Simply return walk from FormView1_GetItem method and don't manipulate your label control there. Now, you can use a Repeater control to display the lbFeatures control (since it is going to repeat dynamically) like this:-
<ItemTemplate>
<h1><%# Item.Title %></h1>
<asp:Repeater ID="lbFeatures" runat="server" DataSource='<%# Item.Features%>'>
<ItemTemplate>
<asp:Label ID="lblTest" runat="server"
Text='<%# Eval("FeatureName") %>'></asp:Label>
<br />
</ItemTemplate>
</asp:Repeater>
</ItemTemplate>
As you can see I am able to assign the datasouce of repater control as Item.Features, then use the conventional approach to bind the label. This looks clean and simple :)
Im using a repeater to display some products in an online shop for a school project. This is how the front end looks with the repeater
<asp:Repeater ID="Repeater1" runat="server" OnItemCommand="rptList_ItemCommand">
<ItemTemplate>
<span style="float:left; padding:25px;" class="backgrnd">
<asp:ImageButton ID="imgProd" runat="server" style="width:150px; height:150px;" ImageUrl='<%# DataBinder.Eval(Container.DataItem, "productImg")%>' CommandArgument='<%# DataBinder.Eval(Container.DataItem, "productID")%>' CommandName="ViewIndividProd"/><br />
<p style="clear:left;">
<asp:Label ID="lbName" runat="server" Text='<%# DataBinder.Eval(Container.DataItem, "productName")%>' /><br />
<asp:Label ID="lbUnitPrice" runat="server" Text='<%# DataBinder.Eval(Container.DataItem, "unitPrice")%>'/><br />
<asp:Label ID="lbRatings" runat="server" Text=''>Ratings</asp:Label><br />
<asp:LinkButton ID="linkCart" runat="server" CommandArgument='<%# DataBinder.Eval(Container.DataItem, "productID")%>' CommandName="AddToCart">Add to Cart</asp:LinkButton>
</p>
</span>
</ItemTemplate>
</asp:Repeater>
As you can see I've added on the OnItemCommand in the Repeater tag so that this is invoked whenever one of the buttons(image/link) is fired. That works perfectly fine for both commandname AddToCart and ViewIndividProd. However, i want to store the the productid of a specific item that was invoked by the particular button. In my case now, it only stores ONE productid in the arraylist at a time and 'forgets' the productid that was stored previously when another linkbutton is clicked.
Question How do i make it such that everytime a linkbutton in the repeater is fired, it remembers the productid pertaining to the linkbutton that was fired and save these ids into the arraylist?
This is how the back end looks
ArrayList cart = new ArrayList();
protected void rptList_ItemCommand(object sender, RepeaterCommandEventArgs e) {
if (e.CommandName == "ViewIndividProd") {
Session["productID"] = e.CommandArgument.ToString();
Response.Redirect("IndividProduct.aspx");
}
if (e.CommandName == "AddToCart") {
string prodid = e.CommandArgument.ToString();
cart.Add(prodid);
Session["ShoppingCart"] = cart;
Response.Redirect("IndividCat.aspx");
}
msg.Text = "Shopping cart: " + String.Join(",", cart.ToArray());
}
Your feedback would be much appreciated.
You need to understand the Asp.net Page life cycle.
A new instance of your Page object is created on every request.
Values from your input are populated into it.
Your array list is getting recreated every time.
If you want the values to persist, you will have to store your arraylist in the ViewState or the Session
Refer: How to: Save Values in View State
void Page_Load(object sender, EventArgs e)
{
if (ViewState["arrayListInViewState"] != null)
{
PageArrayList = (ArrayList)ViewState["arrayListInViewState"];
}
else
{
// ArrayList isn't in view state, so we need to create it from scratch.
PageArrayList = CreateArray();
}
// Code that uses PageArrayList.
}
We can store comma separated or JSON value in either Session or hidden variable (If you are on the same page and opening new page in different tab then we can use hidden variable also). So every time an button has been click we can append the product id.
I currently have a Gridview that displays
TypeID , Name , Description.
I would like to display the actual type name instead of the TypeID in the gridview. I created this function that takes in the ID and returns the Name but I am having trouble using it. There are 15-20 different types so How do I convert the TypeID to a Type Name so that it is displayed when the Gridview is rendered.
protected string GetGenericTypeByID(int genericTypeID)
{
string genericTypeName;
GenericType.Generic_TypeDataTable genericTypeNameDS = new GenericType.Generic_TypeDataTable();
genericTypeNameDS = GenericBO.Get_GenericTypeByID(genericTypeID);
genericTypeName = genericTypeNameDS[0]["Generic_Type_Name"].ToString();
return genericTypeName;
}
I thought I would be able to use the function in the ItemTemplate but it seems to be harder that I thought
<ItemTemplate>
<asp:Label ID="Label1" runat="server" Text='<%# Bind("GetGenericTypeByID("Generic_Type_ID")")%>'></asp:Label>
</ItemTemplate>
Thanks to Everyone who helped me solve this problem.
I ended up using the method below and it works perfectly.
GetGenericTypeByID( Convert.ToInt32(Eval("Generic_Type_ID")))
You've got the 'bind/eval' and method call inside out.
See Using Method inside a DataGrid or GridView TemplateField
<asp:TemplateField HeaderText=”Name”>
<ItemTemplate>
<a href='<%# FormatUrl(Eval(”email1″).ToString())%>'><%# Eval(”fname”) %>, <%# Eval(”lname”) %></a>
</ItemTemplate>
With the 'FormatUrl' function being:
public string FormatUrl(string email)
{
return “mailto:” + email;
}
Are you limited to a label tag? If not, Expanding on David HAust's answer try the following:
<ItemTemplate>
<%#GetGenericTypeByID(Eval(Generic_Type_ID))%>
</ItemTemplate>
Create a read-only property on the row class that you're using to populate the grid, and get this property to return the results of your function.