Question

J'ai un contrôle ListView qui présente un comportement étrange - les lignes ne sont que partiellement mises à jour après une publication. J'espère que quelqu'un ici pourra nous expliquer pourquoi cela pourrait se produire.

Mon listview DataSource est lié à une liste d'éléments stockée dans l'état de session de la page. Cela est intentionnel, en partie pour expirer les vues obsolètes, car plusieurs utilisateurs visualisent les données. Sur une opération en clair, le tri est traité sur la page via javascript, et l'ordre des données de liste / session est synchronisé via des rappels. Callback vérifie également les niveaux d'autorisations. Sur une opération de villégiature particulière qui est plus compliquée, le javascript de la page crée une publication sur la page pour gérer la logique de tri. La liste / session est mise à jour comme dans le rappel, puis le contrôle listview est rebondi sur les données. La page se charge à nouveau et les lignes indiquent le nouvel ordre. Pas de problème, non?

Le problème est que certains éléments de la vue liste ne changent pas de valeur conformément au nouvel ordre. Alors que les liens hypertexte et le texte traité sur la page (par exemple & Lt;% # Eval (& "ProjectAbbrev &";))% & Gt;) sont mis à jour de manière appropriée, les cases à cocher, les littéraux et les menus déroulants dont les valeurs sont définies via la méthode d'événement OnItemDataBound ne sont pas - ils restent & "figés &"; en place, même si parcourir le code révèle que la méthode est exécutée au cours de la publication et que les contrôles DEVRAIENT être réglés sur leurs nouvelles valeurs. Si je vais et tronque manuellement la liste pour dire, la moitié de la taille d'origine, bien que seuls ces éléments soient remplis à nouveau, mais les cases à cocher et autres conservent leurs valeurs d'origine.

Ma question est donc la suivante: pourquoi ces éléments ne sont-ils pas mis à jour avec le reste des éléments de contrôle listview sur la publication? J'ai l'impression que je ne comprends pas bien le cycle de vie d'une page dans ASP.NET ou que j'ai rencontré un bogue quelconque.

À ce stade, je pense que je vais devoir déplacer l'opération de tri plus complexe sur la page en javascript, mais ce sera assez compliqué et j'aimerais éviter de le faire si possible.


UPDATE: J'ai essayé de définir EnableViewState sur false et cela ne résout pas le problème. Je ne pourrais en aucun cas utiliser cette tactique car d'autres parties de la page (save) reposent sur la lecture de l'état de la vue. MISE À JOUR: Je fournis des extraits de code dans l’espoir qu’ils jettent un éclairage sur ce problème:

Page: L'élément HyperLink sera mis à jour correctement après la publication, mais la case à cocher dont la valeur est affectée dans la méthode OnQueueRepeater_ItemDataBound restera la même.

<%@ Control Language="C#" AutoEventWireup="true" CodeBehind="TextProcessorProjects.ascx.cs" Inherits="ETD.UI.Controls.TextProcessorProjects" %>

<asp:ListView ID="QueueListView" runat="server" OnItemDataBound="OnQueueRepeater_ItemDataBound">
 <ItemTemplate>
  <tr>
   <td><asp:HyperLink runat="server" ID="ProjectIDLink"><%# Eval("ProjectAbbrev") %></asp:HyperLink></td>
   <td><asp:CheckBox runat="server" ID="ScannedCheckBox" BorderStyle="None" /></td>
  </tr>
 </ItemTemplate>
</asp:ListView>

Code derrière: à la publication, le code suivant est exécuté:

protected List<Book> QueueDataItems
{
 get { return (List<Book>)Session["Queue"]; }
 set { Session["Queue"] = value; }
}

else if (IsPostBack && !Page.IsCallback)
{
 // resort QueueDataItems List appropriately
 ResortQueue(Request.Params) 
 // rebind
 QueueListView.DataSource = QueueDataItems;
 QueueListView.DataBind();
}

protected void OnQueueRepeater_ItemDataBound(object sender, ListViewItemEventArgs e)
{
 // ...
 // ... other controls set
 CheckBox scannedCheckBox = e.Item.FindControl("ScannedCheckBox") as CheckBox;
 scannedCheckBox.Checked = book.Scanned;
}

UPDATE: J'ai renoncé à faire en sorte que cela fonctionne et a déplacé ma logique de tri du côté client avec javascript. Si quelqu'un a une idée quant à la raison de ce comportement étrange, je serais toujours très intéressé de l'entendre!

Était-ce utile?

La solution

par intérêt, sur quel point de la page utilisez-vous la liaison de données? Page_Load?

Essayez-le sur OnPreRender - pourrait vous aider.

Autres conseils

On dirait que ViewState est en train de démarrer et de repeupler les données. Dans tous les cas, si vous avez toujours lié la liaison de données à chaque publication, vous devez probablement définir EnableViewState de votre ListView sur false pour réduire la taille de la page.

Je pense que cela est lié à l'ordre dans lequel les différents événements sont déclenchés au cours du cycle de vie d'une page. Voir Présentation du cycle de vie d'une page ASP.NET . Vous devez effectuer une liaison de données dans Page_OnPreRender pour vous assurer que le repeuplement est effectué après les événements de contrôle (qui entraîneront la mise à jour des données) sur la page.

Peut-être votre QueueListView est-elle réattribuée pour une raison quelconque.

Essayez de réinitialiser la valeur de la source de données après le DataBind () pour voir ce qui se passe

QueueListView.DataBind();
QueueListView.DataSource = null;

Y a-t-il une chance que cela puisse être un problème de cache? J'ai rencontré un problème similaire en utilisant un listview avec un XMLDatasource. J'ai essayé d'éteindre tout le viewstate. Je voudrais lier la listview dans le code derrière et utiliser XPath pour tout écrire à l'écran sur ma page aspx. Cela a été utilisé dans une recherche .... la prochaine fois que j'ai fait une recherche, aucune des nouvelles informations ne s'est présentée. Cela est dû au fait que la mise en cache de XMLDatasource est activée par défaut. Dans mon cas, je touchais la base de données à chaque fois et je n'avais pas besoin de la mettre en cache. J'ai désactivé la mise en cache sur la source de données et tous mes problèmes ont été résolus.

Je ne mentionne cela que parce que l'erreur que j'ai eue semble identique à la vôtre. Je ne vois pas comment vous récupérez un livre dans itemdatabound - et vous n'utilisez pas une source de données XML en apparence, mais je pensais que le commentaire pourrait déclencher quelque chose pour vous. Bonne chance .... même si on dirait que vous êtes déjà passé: -).

Le contrôle de case à cocher ReadOnly = true ou Enabled = false?

J'ai eu des problèmes avec les contrôles avec l'une de ces propriétés définies comme ci-dessus qui n'étaient pas mises à jour, peu importe la façon dont j'essayais de gérer le contrôle dans le code. Je pense que la désactivation du viewstate contournerait aussi cette petite & "Fonctionnalité &"; ASP.NET, mais ça vaut le coup.

De plus, si les éléments sont triés via le code côté client, cet ordre est-il conservé dans la publication? Je ne pense pas que vous puissiez modifier l'objet CLR que vous avez en session via javascript.

Vous n’êtes pas sûr que cela aide, remplacez <% # Eval (" ProjectAbbrev "))% > avec le lien hypertexte.Text affecté dans la méthode OnQueueRepeater_ItemDataBound et voir si toutes les lignes sont remplies correctement.

Cela ne résoudra probablement pas votre problème, mais il sera intéressant de connaître le résultat.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top