Frage

Das ist es, was ich habe.Es klappt.Aber gibt es einen einfacheren oder besseren Weg?

ASPX-Seite…

<asp:Repeater ID="RepeaterBooks" runat="server">
    <HeaderTemplate>
        <table class="report">
            <tr>
                <th>Published</th>
                <th>Title</th>
                <th>Author</th>
                <th>Price</th>
            </tr>
    </HeaderTemplate>
    <ItemTemplate>
            <tr>
                <td><asp:Literal ID="LiteralPublished" runat="server" /></td>
                <td><asp:Literal ID="LiteralTitle" runat="server" /></td>
                <td><asp:Literal ID="LiteralAuthor" runat="server" /></td>
                <td><asp:Literal ID="LiteralPrice" runat="server" /></td>
            </tr>
    </ItemTemplate>
    <FooterTemplate>
        </table>
    </FooterTemplate>
</asp:Repeater>

ASPX.VB-Code dahinter…

Protected Sub Page_Load( ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
    Dim db As New BookstoreDataContext
    RepeaterBooks.DataSource = From b In db.Books _
                               Order By b.Published _
                               Select b
    RepeaterBooks.DataBind()
End Sub

Sub RepeaterBooks_ItemDataBound( ByVal sender As Object, ByVal e As System.Web.UI.WebControls.RepeaterItemEventArgs) Handles RepeaterBooks.ItemDataBound
    If e.Item.ItemType = ListItemType.Item Or e.Item.ItemType = ListItemType.AlternatingItem Then
        Dim b As Book = DirectCast(e.Item.DataItem, Book)
        DirectCast(e.Item.FindControl("LiteralPublished"), Literal).Text = "<nobr>" + b.Published.ToShortDateString + "</nobr>"
        DirectCast(e.Item.FindControl("LiteralTitle"), Literal).Text = "<nobr>" + TryNbsp(HttpContext.Current.Server.HtmlEncode(b.Title)) + "</nobr>"
        DirectCast(e.Item.FindControl("LiteralAuthor"), Literal).Text = "<nobr>" + TryNbsp(HttpContext.Current.Server.HtmlEncode(b.Author)) + "</nobr>"
        DirectCast(e.Item.FindControl("LiteralPrice"), Literal).Text = "<nobr>" + Format(b.Price, "c") + "</nobr>"
    End If
End Sub

Function TryNbsp(ByVal s As String) As String
    If s = "" Then
        Return "&nbsp;"
    Else
        Return s
    End If
End Function
War es hilfreich?

Lösung

@Geoff

Diese Art von Eval-Anweisung wurde tatsächlich in 2.0 hinzugefügt, aber wenn die Leistung wichtig ist, sollte Eval vermieden werden, da es Reflection verwendet.

Der Repeater ist eine ziemlich gute Möglichkeit, dies zu tun, obwohl es möglicherweise schneller ist, die Tabelle im Code zu generieren:

ASPX-Seite:

<table class="report" id="bookTable" runat="server">
        <tr>
            <th>Published</th>
            <th>Title</th>
            <th>Author</th>
            <th>Price</th>
        </tr>
 </table>

Code dahinter:

Protected Sub Page_Load( ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
    If Not Page.IsPostback Then
        BuildTable()
    End If
End Sub

Private Sub BuildTable()
    Dim db As New BookstoreDataContext
    Dim bookCollection = from b in db.Books _
                         Order By b.Published _
                         Select b
    Dim row As HtmlTableRow
    Dim cell As HtmlTableCell

    For Each book As Books In bookCollection
        row = New HtmlTableRow()
        cell = New HtmlTableCell With { .InnerText = b.Published.ToShortDateString }
        row.Controls.Add(cell)
        cell = New HtmlTableCell With { .InnerText = TryNbsp(HttpContext.Current.Server.HtmlEncode(b.Title)) }
        row.Controls.Add(cell)
        cell = New HtmlTableCell With { .InnerText = TryNbsp(HttpContext.Current.Server.HtmlEncode(b.Author))
        row.Controls.Add(cell)
        cell = New HtmlTableCell With { .InnerText = Format(b.Price, "c") }
        row.Controls.Add(cell)
        bookTable.Controls.Add(row)
    Next

Ich denke, es hängt davon ab, wie wichtig Geschwindigkeit für Sie ist.Der Einfachheit halber würde ich mich für den Repeater entscheiden.

Andere Tipps

Der Listenansicht Die mit Framework 3.5 eingeführte Steuerung könnte eine etwas bessere Lösung sein.Ihr Markup würde so aussehen:

<asp:ListView runat="server" ID="ListView1" 
    DataSourceID="SqlDataSource1">
  <LayoutTemplate>
    <table runat="server" id="table1" runat="server" >
      <tr runat="server" id="itemPlaceholder" ></tr>
    </table>
  </LayoutTemplate>
  <ItemTemplate>
    <tr runat="server>
      <td runat="server">
        <asp:Label ID="NameLabel" runat="server" 
          Text='<%#Eval("Name") %>' />
      </td>
    </tr>
  </ItemTemplate>
</asp:ListView>

In .Net 3.0+ können Sie Ihren ItemDataBound durch asp:Literal ersetzen, indem Sie Folgendes tun:

<ItemTemplate>
            <tr>
                <td><%# Eval("published") %></td>
                ...

Dabei ist „veröffentlicht“ der Name eines Felds in den Daten, die Sie an den Repeater gebunden haben

Bearbeiten:@Alassek:Ich denke, dass der Leistungserfolg der Reflexion oft überbetont wird.Natürlich müssen Sie die Leistung Ihrer App messen, aber der Erfolg der Evaluierung wird wahrscheinlich in Millisekunden gemessen.Sofern Ihre App nicht viele gleichzeitige Zugriffe bereitstellt, stellt dies wahrscheinlich kein Problem dar, und die Einfachheit des Codes mit Eval sowie die gute Trennung der Präsentation machen es zu einer guten Lösung.

Dafür ist GridView gedacht.

<asp:GridView runat="server" DataSourceID="SqlDataSource1">
   <Columns>
      <asp:BoundField HeaderText="Published" DataField="Published" />
      <asp:BoundField HeaderText="Author" DataField="Author" />
   </Columns>
</asp:GridView>

Ich würde ein GridView verwenden (oder DataGrid, wenn Sie eine ältere Version von ASP.NET verwenden).

<asp:GridView ID="gvBooks" runat="server" AutoGenerateColumns="False">
    <Columns>
        <asp:BoundField HeaderText="Published" DataField="Published" />
        <asp:BoundField HeaderText="Title" DataField="Title" />                     
        <asp:BoundField HeaderText="Author" DataField="Author" />
        <asp:BoundField HeaderText="Price" DataField="Price" />
    </Columns>
</asp:GridView>

Mit etwas CodeBehind:

Private Sub gvBooksRowDataBound(ByVal sender As Object, ByVal e As System.Web.UI.WebControls.GridViewRowEventArgs) Handles gvBooks.RowDataBound
     Select Case e.Row.RowType
        Case DataControlRowType.DataRow

            ''' Your code here '''

     End Select
End Sub

Sie können es auf ähnliche Weise binden.Das RowDataBound-Ereignis ist genau das, was Sie brauchen.

Ich stimme Geoff zu, das einzige Mal, das wir verwenden Literals ist, wenn wir etwas tun wollen anders mit den Daten.
Zum Beispiel möchten wir vielleicht eine DueDate Geben Sie in das Feld „Heute“ oder „Gestern“ anstelle des tatsächlichen Datums ein.

ALassek schrieb:

…die Tabelle im Code generieren…

Mir gefällt das Aussehen!Es ist VIEL unwahrscheinlicher, dass es aufgrund eines Tippfehlers oder einer Änderung des Feldnamens zu einer Laufzeitausnahme kommt.

Wenn Sie keine von ASP.NET verwalteten Bearbeitungsfunktionen benötigen, würde ich das tun Bleib weg aus dem DataGrid und dem GridView ...Sie liefern unnötiges Aufblähen.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top