14 Nov
2006

HTMLElement-Scrollposition bei einem PostBack merken

 

Heute in den Newsgroups [2], es fragte Fabian Nowothnik danach wie man nach einem Postback die Scrollpositionen von einzelnen Elementen wieder herstellen kann.

Für die Scrollposition der Seite gibt es dies ja seit ASP.NET 2.0 schon in der Serienausstattung. Ein Scrolling innerhalb eines DIV-Elements "passiert" ja schnell, in dem innerhalb eine DIV-Elements mehr reinpackt als die festgesetzen Ausmaße zulassen. Nun einfach den CSS-Style "overflow:auto;" oder "overlow:scroll;" gesetzt dann kann man darin scrollen, jedoch verliert sich die Scroll-Position nach dem Postback. Das ist schade.

Prinzipiell sollte es doch ganz einfach sein etwas dagegen zu machen. Position der Elemente vor dem Postback merken und dann direkt einfach beim neuladen wieder herstellen. Wäre doch auch nett wenn man dies dann einfach via kleinem Control machen kann einfach auf jeder Seite einsetzen kann. Gesagt getan, hier ist das Ergebnis das "RememberElementScrollPosition" WebControl für ASP.NET 2.0 :).

Gleich vorweg, dazu ist JavaScript notwendig, ohne geht's nicht. Die Anwendung selbst ist denkbar einfach. Nachdem man den Quelltext [1] in eine Assembly oder App_Code Ordner gepackt hat muss man das Control dem Web bekannt machen, dazu in der Web.config zu der Controls-Auflistung hinzufügen, hier ein Beispiel, es muss den eigenen Gegebenheiten angepasst werden.

<system.web> 
  <pages> 
    <controls> 
      <add namespace="DerAlbert.Community.Web.UI.WebControls" 
           assembly="DerAlbert.Community.Web" 
           tagprefix="dac" /> 
    </controls> 
  </pages> 
</system.web>

Auf der Seite dann folgendes

<dac:rememberelementscrollposition id="RESP1" runat="server"> 
    <dac:controlid>MyPanel</dac:controlid> 
    <dac:controlid>Div1</dac:controlid> 
</dac:rememberelementscrollposition>

Für jedes Element/Control ein <dac:ControlID/> hinzufügen. Es wird erst das passenden Server-Control gesucht und verwendet, wird keins gefunden so wird die angegebene ID direkt als ClientID verwendet. So das man

<asp:panel id="MyPanel" runat="server">Der rieisige Inhalt</asp:panel> 

oder auch

<div id="Div1">Größer, schneller weiter</div>

verwenden kann. Je nach Vorliebe, aber eine ID muss vorhanden sein. Mehr muss man nicht machen.

Damit ich vor dem Postback die Daten auslesen kann Registriere ich mir mit ClientScript.RegisterOnSubmitStatement() eine Javascript Anweisung welche das sammeln der Scrollpositionen aufruft und in einem HiddenField ablegt, damit diese den Postback ohne weitere Tricks überleben. Beim wiederladen der Seite sollen die gespeicherten Positionen wieder gesetzt werden, dafür muss wieder eine JavaScript Anweisung registriert werden diesmal mit ClientScript.RegisterStartupScript(). Damit wird die übergebenen Anweisung ans Ende der Seite gelegt und automatisch aufgerufen nachdem der eigentliche Seiteninhalt schon vorhanden ist.

Das JavaScript selbst ist objektorientiert aufgebaut, sollte jedoch nicht so schwer sein zu verstehen. Es merkt sich die scrollTop und scrollLeft Werte des HTML-Elements und packt diese zusammen mit der ID des Elements in das Hiddenfield. Selbstverständlich für alle angebenen Elemente, jedoch nur wenn man die Element auch wirklich in einem "gescrolltem" Zustand sind. Nun genug geredet. Nutzt das Teil wenn Ihr wollt.

[1] Download Quelltext

[2] Newsgroup-Anfrage


Der Eintrag ist mir etwas Wert
 

Feedback

# re: HTMLElement-Scrollposition bei einem PostBack merken

left by Adrian Stern at 1/16/2008 1:21 PM Gravatar
Alternativ kann man die web.conf auch unangetastet lassen.

Hierzu die Dateien RememberElementScrollPosition.cs und ControlID.cs ins App_Code verzeichnis kopieren und in der *.aspx datei Folgendes angeben:

[CODE]
<%@ Register Namespace="DerAlbert.Community.Web.UI.WebControls" TagPrefix="dac" %>

<script type="text/javascript" src="RememberElementScrollPosition.js"></script>
[/CODE]
Somit können die Klassen verwendet werden:
[CODE]
<dac:RememberElementScrollPosition ID="RESP1" runat="server">
<dac:ControlID>div1</dac:ControlID>
<dac:ControlID>div2</dac:ControlID>
</dac:RememberElementScrollPosition>
[/CODE]

# re: HTMLElement-Scrollposition bei einem PostBack merken

left by WhoAmI at 12/18/2008 2:28 PM Gravatar
Hallo,

Keine Ahnung ob die Seite hier noch wer anschaut oder so aber ich hätte eine Frage bzw ein Problem.

Es geht darum, dass ich in einem asp:panel mit overflow:auto einen Treeview habe welcher mit OnDemand befüllt wird. Damit dies richtig funktioniert musste ich EnableClientScript="false" setzen.

Nun funktioniert das mit diesem Control nicht!
Es funktioniert zwar mit befüllen und allem aber der Tree reagiert nicht mehr auf das SelectedNodeChanged Event


Kann man da dagegen was machen?

# re: HTMLElement-Scrollposition bei einem PostBack merken

left by Der Albert at 12/18/2008 2:39 PM Gravatar
Ohne ClientScript funktioniert weder das TreeView richtig noch das auf dieser Seite vorgestellte Control.

Bei overflow:auto sollte man auch eine Höhe für das Panel angeben.

# re: HTMLElement-Scrollposition bei einem PostBack merken

left by WhoAmI at 12/18/2008 3:03 PM Gravatar
Erstmals danke für die schnelle Antwort!

Mein Problem ist, dass wenn ich das EnableClientscript auf true setze mein Tree beim klicken auf eine Node auf letzter Ebene sich komplett zusammenklappt und alle Nodes entfernt!
Darum hatte ich testhalber das EnableScript mal auf false gesetzt und dann hat es funktioniert!

Jetzt ist mein Problem, dass wenn ich das Control einbinde der Tree nicht mehr auf mein SelectedNodeChanged Event reagiert... (dazu habe ich enablescript auf true gesetzt)

Bin leider aspx Neuling und kann mich nicht wirklich gut ausdrücken sry...

# re: HTMLElement-Scrollposition bei einem PostBack merken

left by GRooive at 4/1/2010 4:51 PM Gravatar
Hallo Zusammen,
Super Sache das Script, vielen Dakn dafür.
Hatte mir zwar auch schon ein Javascript gebastelt, dies war jeoch nicht so flexibel.

Ein Problem habe ich noch. Gibt es für Java Script auch ein Ereignis für einen XML Request (Ajax) der vor dem verschicken abfgefangen werden kann? ... Ansonsten bekomme ich meinen Ajax Chat nicht hin, da dies keine richtigen Postbacks sind.

Danke und Gruß

Comments have been closed on this topic.