11

我在 aspx 页面中有一个 div,溢出设置为自动。div 的内容是动态创建的,由链接按钮列表组成。

<div id="div1" style="overflow: auto; height: 100%;">
.....
</div>

当我在 div 中向下滑动并单击任何链接按钮时,页面重新加载会丢失 div 内的滚动位置并将我带到 div 的顶部。有什么办法可以防止这种情况发生吗?

请注意,这是针对页面内的 div 的。Page.MaintainScrollPositionOnPostBack()不起作用。

4

5 回答 5

15

正如 Jeff S 提到的处理这种情况的一种方法是使用 javascript 来跟踪 div 的滚动位置,并且每次页面加载时都会将滚动位置重置为其先前的值。

这是一些示例代码:

<html>
<body onload="javascript:document.getElementById('div1').scrollTop = document.getElementById('scroll').value;">
    <form id="form1" runat="server">
    <input type="hidden" id="scroll" runat="server" />
    <div id="div1" style="overflow: auto; height: 100px;" onscroll="javascript:document.getElementById('scroll').value = this.scrollTop">
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        ...........<br />
        <asp:LinkButton ID="LinkButton1" runat="server" Text="test2"></asp:LinkButton>
    </div>
    <asp:LinkButton ID="LinkButton2" runat="server" Text="test1"></asp:LinkButton>
    </form>
</body>
</html>

在实践中,我不会将 javascript 直接放在元素中,而这只是一个示例。您也可以将滚动位置存储在 cookie 中。

于 2009-07-08T13:51:05.043 回答
6

最简单的方法是将控件包装在 UpdatePanel 中。

于 2009-07-07T21:04:02.823 回答
3
using System;
using System.ComponentModel;
using System.Web.UI;
using System.Web.UI.WebControls;

[ParseChildren(true, "Content")]
public class ScrollSaverPanel: WebControl
{
    [TemplateInstance(TemplateInstance.Single)]
    [PersistenceMode(PersistenceMode.InnerProperty)]
    [DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
    public ITemplate Content { get; set; }

    private HiddenField HiddenField { get; set; }

    protected override HtmlTextWriterTag TagKey
    {
        get
        {
            return HtmlTextWriterTag.Div;
        }
    }

    protected override void OnInit(EventArgs e)
    {
        HiddenField = new HiddenField();

        var metaContainer = new WebControl(HtmlTextWriterTag.Div);
        metaContainer.Controls.Add(HiddenField);
        metaContainer.Style.Add(HtmlTextWriterStyle.Display, "none");

        Controls.Add(metaContainer);

        var contentContainer = new WebControl(HtmlTextWriterTag.Div);
        Controls.Add(contentContainer);

        Content.InstantiateIn(contentContainer);

        this.Style.Add(HtmlTextWriterStyle.Overflow, "auto");
        this.Attributes.Add("onscroll", string.Format("javascript:document.getElementById('{0}').value = this.scrollTop;", HiddenField.ClientID));

        base.OnInit(e);
    }

    protected override void OnPreRender(EventArgs e)
    {
        ScriptManager.RegisterStartupScript(this, this.GetType(), "setscroll", string.Format("javascript:document.getElementById('{0}').scrollTop = '{1}';", this.ClientID, HiddenField.Value), true);
        base.OnPreRender(e);
    }
}

用法:

<general:ScrollSaverPanel runat="server">
    <Content>
        <stwrw:Group runat="server" ID="rootGroup"/>
    </Content>
</general:ScrollSaverPanel>

由于有些人不想仅出于保存滚动位置的目的而使用更新面板... :)

于 2013-03-14T16:56:09.090 回答
1

一种方法是在 div 的 onscroll 事件中捕获来自 scrollLeft 和 scrollTop 属性的值。将这些值保存在隐藏的文本框中。在回发时,使用文本框中的值重置属性。

于 2009-07-07T21:15:00.977 回答
0

按下链接按钮时会发生什么?回发过程中会发生什么处理?

根据对这些问题的回答,您可能想要调查完全摆脱回发并纯粹在客户端执行必要的操作。

(我目前正在为客户执行这种转换。)

于 2009-07-07T21:07:25.237 回答