2009-05-04 10 views
5

Ich habe ein ListView-Steuerelement, das ein seltsames Verhalten zeigt - Zeilen werden nur teilweise nach einem Postback aktualisiert. Ich hoffe, dass hier jemand etwas Licht auf die Gründe dafür werfen kann.Listview nicht vollständig auf Datenind() nach Postback aktualisieren

Meine ListView DataSource ist an eine Liste von Elementen gebunden, die im Seitensitzungsstatus gespeichert ist. Dies ist beabsichtigt, um veraltete Ansichten teilweise zu veralten, da mehrere Benutzer die Daten anzeigen. Bei einer einfachen Resort-Operation wird die Sortierung auf der Seite über Javascript abgewickelt, und die Reihenfolge der Liste/Session-Daten wird über Callbacks synchronisiert. Callback überprüft auch die Berechtigungsstufen. Bei einer bestimmten Resort-Operation, die komplizierter ist, macht das Javascript auf der Seite ein Postback auf die Seite, um die Sortierlogik zu handhaben. Die Liste/Sitzung wird wie beim Rückruf aktualisiert. Anschließend wird das Steuerelement listview auf die Daten zurückgesetzt. Die Seite wird erneut geladen und die Zeilen zeigen die neue Reihenfolge an. Kein Problem, oder?

Das Problem ist, dass einig der Elemente in der Listenansicht nicht ändern Wert in Übereinstimmung mit der neuen Ordnung. Während die Hyperlinks und Texte, die auf der Seite verarbeitet werden (zB <% # Eval ("ProjectAbbrev")%>) korrekt aktualisiert werden, bleiben Checkboxen, Literale und Dropdowns, deren Werte über die OnItemDataBound-Ereignismethode gesetzt wurden, nicht erhalten "eingefroren" an Ort und Stelle, obwohl das Durchlaufen des Codes zeigt, dass die Methode während des Postbacks ausgeführt wird, und dass die Steuerelemente auf ihre neuen Werte gesetzt werden sollten. Wenn ich die Liste manuell lehne und sage, halb so groß wie die Originalgröße, dann werden nur diese Punkte neu gefüllt, aber die Checkboxen und solche behalten immer noch ihre ursprünglichen Werte.

Also meine Frage ist: Warum werden diese Elemente nicht zusammen mit dem Rest der listview Steuerelemente auf dem Postback aktualisiert? Ich habe das Gefühl, dass ich den Seitenlebenszyklus in ASP.NET entweder falsch verstanden habe oder dass ich auf einen Fehler gestoßen bin.

An diesem Punkt denke ich, dass ich die kompliziertere Sortieroperation auf die Seite in Javascript verschieben muss, aber das wird ziemlich schwierig sein, und ich möchte es vermeiden, wenn möglich zu tun.


UPDATE: Ich habe versucht, EnableViewState zu false und es nicht beheben. Ich konnte diese Taktik in keinem Fall verwenden, da andere Teile der Seite (speichern) darauf angewiesen sind, den Viewstatus am Ende zu lesen.
UPDATE: Ich habe einige Code-Schnipsel in der Hoffnung, vorausgesetzt, dass sie in dieser Frage etwas Licht könnte:

Seite: Das Element HyperLink richtig nach dem Postback aktualisiert wird, aber die CheckBox, die ihren Wert in der zugeordnet ist OnQueueRepeater_ItemDataBound-Methode bleibt gleich.

<%@ 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 hinter: Beim Postback der folgende Code ausgeführt:

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: Ich habe auf dem Erhalten dieser aufgegeben zu arbeiten und zog meine Sortierlogik auf die Client-Seite mit Javascript. Wenn jemand irgendwelche Ideen hat, warum dieses seltsame Verhalten passiert ist, würde ich immer noch sehr daran interessiert sein, sie zu hören!

Antwort

6

aus Interesse, welchen Punkt auf der Seite haben Sie Datenbindung auf? Page_Load?

Probieren Sie es auf OnPreRender - könnte helfen.

+0

Danke Tim! Ich bin davon ziemlich weit entfernt, aber wenn ich wieder auf dieses Problem stoße, werde ich das sicher tun. – patjbs

+0

Tim hat Recht - ich hatte genau das gleiche Problem und Page_PreRender funktioniert bei Postbacks :) – Jason

1

Klingt wie der ViewState tritt auf und repopuliert die Daten. Wenn Sie sowieso in jedem Postback Databinding sind, sollten Sie den EnableViewState Ihrer ListView wahrscheinlich auf false setzen, um die Seitengröße zu reduzieren.

+0

Deaktivierung der Viewstate löst das Problem leider nicht. – patjbs

0

Vielleicht wird Ihre QueueListView aus irgendeinem Grund neu gebunden.

Probieren Sie den Datasource-Wert nach dem DataBind Zurücksetzen(), um zu sehen, was passiert,

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

danke für den Gedanken aber leider kein Glück – patjbs

0

Jede Chance, dies könnte ein Caching-Problem sein? Ich stieß auf ein ähnliches Problem mit einem Listview mit einer XMLDatasource. Ich habe versucht, alle Viewstate auszuschalten. Ich würde die Listview in den Code hinter binden und XPath verwenden, um alles auf dem Bildschirm auf meiner aspx-Seite zu schreiben. Dies wurde in einer Suche verwendet .... als ich das nächste Mal eine Suche durchführte, tauchte keine neue Information auf. Der Grund dafür ist, dass für eine XMLDatasource die Zwischenspeicherung standardmäßig aktiviert ist. In meinem Fall habe ich jedes Mal die DB getroffen und musste sie nicht zwischenspeichern. Ich habe das Caching auf der Datenquelle ausgeschaltet und alle meine Probleme wurden behoben.

Ich erwähne das nur, weil der Fehler, den ich hörte, identisch mit Ihrem ist. Ich kann nicht sehen, wie Sie Buch in der ItemDatabound abrufen - und Sie verwenden nicht eine XML-Datenquelle nach dem Aussehen der Dinge ..... aber ich dachte, der Kommentar könnte etwas für Sie auslösen. Viel Glück .... obwohl es sich anhört als wärst du schon weitergezogen :-).

0

Ist das Kontrollkästchen ReadOnly = true oder Enabled = false?

Ich hatte Probleme mit Kontrollen mit einer dieser Eigenschaften wie oben festgelegt, nicht aktualisiert, egal wie ich versuche, die Steuerung in den Code hinterhandhaben. Ich würde denken, die Deaktivierung des Viewstate würde auch dieses kleine "Feature" von ASP.NET umgehen, aber es ist einen Versuch wert.

Wenn die Artikel auch über den clientseitigen Code sortiert werden, wird diese Reihenfolge beim Postback beibehalten? Ich glaube nicht, dass Sie das CLR-Objekt, das Sie in der Sitzung haben, über Javascript ändern können.

+0

Nicht festgelegt, nur zu lesen, und das Problem tritt sowohl für Benutzer, für die die Kontrollkästchen aktiviert sind, und diejenigen, für die sie nicht aktiviert sind. Interessante Idee, die ich mir ansehen könnte. Was die clientseitige Sortierung betrifft, wird beim Ausführen eines Resort eine Rückruffunktion ausgelöst, die die Server-Sitzungsdaten auf dem neuesten Stand hält, was der Client sieht. – patjbs

0

Nicht sicher, ob das hilft, ersetzen <% # Eval („ProjectAbbrev“)%> mit dem Hyperlink.Text in dem Verfahren OnQueueRepeater_ItemDataBound zugewiesen und sehen, ob alle Zeilen korrekt aufgefüllt bekommen.

Dies wird wahrscheinlich nicht Ihr Problem lösen, aber es wird interessant sein, das Ergebnis zu wissen.

+0

Dieses Feld wurde im obigen Code korrekt dargestellt. Es waren die Checkboxen und Dropdown-Menüs (nicht gezeigt), die zusammen mit dem Rest der Anzeige nicht korrekt neu geortet werden konnten. – patjbs

+0

Ja, ich habe verstanden, was du meinst. Übrigens, es wurden keine Dropdowns in Ihrem Code angezeigt. Wie wurde die Datenbindung durchgeführt? Versuchen Sie, nur Text/Label für die Kontrollkästchen und Dropdown-Menüs ohne die Steuerelemente zu rendern. Sehen Sie, ob die Werte gerendert werden. –

2

Ich denke, das hängt mit der Reihenfolge zusammen, in der die verschiedenen Ereignisse während des Seitenlebenszyklus ausgelöst werden. Siehe ASP.NET Page Life Cycle Overview. Sie sollten die Datenbindung in Page_OnPreRender durchführen, um sicherzustellen, dass die erneute Befüllung nach den Steuerungsereignissen (die zur Aktualisierung der Daten führen) auf der Seite erfolgt.

+0

Dies.FFS, wenn Sie DataBind erneut aufrufen, sollte es den ControlState ungültig machen? –

Verwandte Themen