eval dans la déclaration if?

 <% if(Eval("SaveDate") != DBNull.Value){ %>
     do magic                           
 <%} %>

Me donne une erreur: les méthodes de liaison de données telles que Eval (), XPath () et Bind() ne peuvent être utilisées que dans le contexte d'un contrôle databound.

Je pourrais écrire:

Je sais que je devrais ajouter # pour utiliser Eval, mais je ne suis pas sûr de la syntaxe correcte.

21
demandé sur Stewie Griffin 2010-08-11 23:37:54

2 réponses

Une solution consiste à envelopper le contenu dans une balise runat="server" avec une valeur Visible, par exemple,

<div runat="server" Visible='<%# Eval("SaveDate") != DBNull.Value %>'>
   do magic
</div>

div peut être n'importe quelle balise HTML, mais <asp:Panel> et <asp:PlaceHolder> peut également être utilisé. Notez que "do magic" est toujours databound, donc ce n'est pas une solution parfaite si elle contient du code coûteux ou du code qui pourrait générer une erreur if Eval("SaveDate") == DBNull.Value.

Notez que Visible="false" omettra la balise et tout son contenu du HTML généré, cela signifie qu'il est très différent de style="display:none" ou style="visible:hidden", alors ne vous inquiétez pas à ce sujet.

Mais, si votre "do magic" est raisonnablement complexe, une autre solution plutôt simple (un peu de hack) est: utilisez un répéteur (ou FormView) avec sa source de données définie sur un tableau d'un élément (visible) ou aucun élément (caché):

<asp:Repeater runat="server" DataSource='<%# ElementIfTrue(Eval("SaveDate") != DBNull.Value) %>'
    <ItemTemplate>
        do magic
    </ItemTemplate>
</asp:Repeater>

protected IEnumerable ElementIfTrue(bool condition) 
{
    if (condition)
        return new object[] { Page.GetDataItem() };
    else
        return new object[0];
}

Le contenu réel du tableau datasource est vide (masqué) ou l'élément auquel vous étiez déjà lié. Cela garantit que vous pouvez toujours appeler <%# Eval(...) %> dans ItemTemplate.

Avec cette approche, votre "faire de la magie" est un modèle qui ne sera exécuté que si DataSource a un ou plusieurs éléments. Qui est pris en charge par ElementIfTrue. Il est un peu d'un esprit bender, mais il peut vous sauver de temps en temps.

Comme une note de côté: l'emballage de votre "faire de la magie" dans un contrôle utilisateur peut également réduire la complexité. Vous n'avez pas vraiment besoin de changer une chose dans votre mélange de balises HTML/ASP.NET (<%# Eval("...") %> fonctionne toujours même à l'intérieur d'un contrôle utilisateur).

30
répondu Ruben 2010-08-11 21:35:04

J'ajoute généralement une fonction protégée renvoyant une chaîne au code-behind pour générer le contenu:

Sur la page:

<%# Eval("SaveDate") != DBNull.Value ? GenerateContent() : string.Empty %>

Dans ma classe:

protected string GenerateContent()
{
    return "Hello, World!"
}
8
répondu kbrimington 2010-08-11 19:41:52