views:

69

answers:

3

I've ported a page from classic ASP to ASP.net. Part of what happens in this page is that a collection of custom types is generated and then displayed via Response.Write() commands. I'd like to get the business logic separated out into a code behind file (and maybe move this all into a user control), but I can't seem to figure out how I'd actually display the collection once it's been generated. I want to specify a master page here, too, so the code can't stay inline. Here's a very stripped down version of the current code:

<%
Dim objs as ArrayList = New ArrayList()

For i = 0 To 2
    Dim obj as Obj = New Obj()

obj.setProp1("ASDF")
obj.setProp2("FDSA")

objs.Add(obj)
Next i
%>

<table>
<thead>
    <tr>
        <th scope="col">Property 1</th>
        <th scope="col">Property 2</th>
    </tr>
</thead>
<tbody>
<%
For Each obj As Obj In objs
Dim objProp1 As String = obj.getProp1
Dim objProp2 As String = obj.getProp2
%>                  
    <tr>
        <td><% Response.Write(objProp1)%></td>
        <td><% Response.Write(objProp2)%></td>
    </tr>
<%
Next
%>
</tbody>
</table>

What is the ".net" way of doing this?

A: 

I would use something like a repeater or datagrid and bind it to a List<> that you can create in your Business Logic layer.

derek
+2  A: 

You can also take a look at the ListView control which is a newer version of the repeater that Joe R mentioned. There's a great tutorial on what you can do with a ListView on ScottGu's blog.

Your code would basically turn into something along these lines:

<asp:ListView id="ListView1" runat="server" enableviewstate="false">
    <LayouTemplate>
        <table>
            <thead>
                <tr>
                    <th scope="col">Property 1</th>
                    <th scope="col">Property 2</th>
                 </tr>
             </thead>
             <tbody>
                 <asp:Placeholder runat="server" id="ItemPlaceholder" />
             </tbody>
        </table>
    </LayouTemplate>
    <ItemTemplate>
        <tr>
            <td><%# Eval("objProp1" )%></td>
            <td><%# Eval("objProp2" )%></td>
        </tr>
    </ItemTemplate>
</asp:ListView>

These guys consider using Eval to not be a good practice, but it made writing the example easier. If you're presenting read only data, don't forget to turn off ViewState or your pages will get very big very quickly.

EDIT Also found a feature comparison chart between the different list style controls here.

R0MANARMY
This is all in the LayoutTemplate. This has no item to repeat. You are missing the ItemTemplate and the itemPlaceholder that needs to go in the LayoutTemplate (in .NET3.5 - .NET4 you dont need too ;)) Other than that you are right - ListView over Repeater any day.
BritishDeveloper
@BritishDeveloper: You're absolutely right, my bad. Fixed.
R0MANARMY
@R0MANARMY downvote revoked :)
BritishDeveloper
Okay, so I'm going with the ListView. It seems the most flexible and I have the option of stepping up to v3.5. Thanks.
bshacklett
+2  A: 

In .NET2 your best bet it the repeater. Something like this:

<asp:Repeater id="rpt1" runat="server" EnableViewState="false"> 
    <HeaderTemplate> 
        <table> 
            <thead> 
                <tr> 
                    <th scope="col">Property 1</th> 
                    <th scope="col">Property 2</th> 
                 </tr> 
             </thead> 
             <tbody> 
    </HeaderTemplate>
    <ItemTemplate>
                 <tr> 
                     <td><%# Eval("objProp1" )%></td> 
                     <td><%# Eval("objProp2" )%></td> 
                 </tr>
    </ItemTemplate>
    <FooterTemplate>
             </tbody> 
        </table> 
    </FooterTemplate>
</asp:Repeater> 

and in your code behind you bind the data like this:

rpt1.DataSource = objs;
rpt1.DataBind();

This would be c# though - hope that's okay

BritishDeveloper