I have a asp.net data grid view with a button field. After clicking the button field whole page refreshes and moves to the top of the grid view. I need to stay at the last click position.
I’ve tried the following and its not working.MaintainScrollPositionOnPostback="true"
c# code Behind
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Data;
using MCS.IT.USER;
namespace McsComplain
{
public partial class GrantFunction : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
UserClass obj = new UserClass();
if (!Page.IsPostBack)
{
//if (string.IsNullOrEmpty(Session["USER_ID"] as string)) Response.Redirect("UserLogin.aspx");
grdAllFunctions.DataSource = null;
DataSet ds = new DataSet();
ds.Merge(obj.userroles());
ddlUser.DataSource = ds.Tables[0];
ddlUser.DataTextField = "USER_ROLE_NAME";
ddlUser.DataValueField = "USER_ROLE_ID";
ddlUser.DataBind();
ddlUser.Items.Insert(0, new ListItem("Select the Role", "0"));
}
}
private void errorHandle(bool con, string message)
{
dvMessage.Visible = true;
if (con)
{
lblErrorMsg.Text = "";
lblMessage.Text = message;
dvMessage.Attributes.Add("class", "alert alert-success custom-centered");
}
else
{
lblErrorMsg.Text = "";
lblMessage.Text = message;
dvMessage.Attributes.Add("class", "alert alert-danger custom-centered");
}
}
protected void ddlUser_SelectedIndexChanged(object sender, EventArgs e)
{
int roleid = Convert.ToInt32(ddlUser.SelectedValue);
UserClass obj = new UserClass();
DataSet dg = new DataSet();
dg.Merge(obj.ungrantedfunctions(roleid));
if (dg.Tables[0].Rows.Count > 0)
{
dvMessage.Visible = false;
grdAllFunctions.DataSource = null;
grdAllFunctions.DataSource = dg.Tables[0];
grdAllFunctions.DataBind();
}
else
{
dvMessage.Visible = true;
grdAllFunctions.DataSource = null;
grdAllFunctions.DataSource = dg.Tables[0];
grdAllFunctions.DataBind();
errorHandle(false, "All functions have been granted to this role");
}
DataSet ds = new DataSet();
ds.Merge(obj.grantedfunctions(roleid));
if (ds.Tables[0].Rows.Count > 0)
{
dvMessage.Visible = false;
grdGrantedFunctions.DataSource = ds.Tables[0];
grdGrantedFunctions.DataBind();
}
else
{
dvMessage.Visible = true;
grdGrantedFunctions.DataSource = null;
grdGrantedFunctions.DataSource = ds.Tables[0];
grdGrantedFunctions.DataBind();
errorHandle(false, "This User Haven't Granted Any Function");
return;
}
}
protected void grdAllFunctions_RowCommand(object sender, GridViewCommandEventArgs e)
{
int roleid = Convert.ToInt32(ddlUser.SelectedValue);
int rowIndex = Convert.ToInt32(e.CommandArgument);
GridViewRow row = grdAllFunctions.Rows[rowIndex];
int funcid = Convert.ToInt32(row.Cells[0].Text);
UserClass obj = new UserClass();
try
{
if (ddlUser.SelectedValue == "0")
{
errorHandle(false, "Please Select the Role Name");
return;
}
else
{
DataSet ds = new DataSet();
ds.Merge(obj.checkgrantedfunctions(roleid, funcid));
if (ds.Tables[0].Rows.Count > 0)
{
errorHandle(false, "This Function is Already Assigned");
return;
}
else
{
obj.grant(roleid, funcid);
errorHandle(true, "Successfully Granted");
DataSet dg = new DataSet();
dg.Merge(obj.ungrantedfunctions(roleid));
if (dg.Tables[0].Rows.Count > 0)
{
grdAllFunctions.DataSource = null;
grdAllFunctions.DataSource = dg.Tables[0];
grdAllFunctions.DataBind();
}
else
{
grdAllFunctions.DataSource = dg.Tables[0];
grdAllFunctions.DataBind();
}
DataSet ds1 = new DataSet();
ds1.Merge(obj.grantedfunctions(roleid));
if (ds1.Tables[0].Rows.Count > 0)
{
grdGrantedFunctions.Visible = true;
grdGrantedFunctions.DataSource = ds1.Tables[0];
grdGrantedFunctions.DataBind();
}
return;
}
}
}
catch (Exception ex)
{
Response.Write("<script>alert('" + Server.HtmlEncode(ex.Message) + "')</script>");
return;
}
}
protected void grdGrantedFunctions_RowCommand1(object sender, GridViewCommandEventArgs e)
{
int rowIndex = Convert.ToInt32(e.CommandArgument);
GridViewRow row = grdGrantedFunctions.Rows[rowIndex];
int functionid = Convert.ToInt32(row.Cells[0].Text);
int roleid = Convert.ToInt32(ddlUser.SelectedValue);
UserClass obj = new UserClass();
try
{
obj.revokefunctions(roleid, functionid);
errorHandle(true, "Function Revoked");
DataSet dg = new DataSet();
dg.Merge(obj.ungrantedfunctions(roleid));
if (dg.Tables[0].Rows.Count > 0)
{
grdAllFunctions.DataSource = null;
grdAllFunctions.DataSource = dg.Tables[0];
grdAllFunctions.DataBind();
}
DataSet ds1 = new DataSet();
ds1.Merge(obj.grantedfunctions(roleid));
if (ds1.Tables[0].Rows.Count > 0)
{
grdGrantedFunctions.DataSource = ds1.Tables[0];
grdGrantedFunctions.DataBind();
}
else
{
grdGrantedFunctions.DataSource = ds1.Tables[0];
grdGrantedFunctions.DataBind();
}
return;
}
catch (Exception ex)
{
Response.Write("<script>alert('" + Server.HtmlEncode(ex.Message) + "')</script>");
return;
}
}
}
}
html
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="frmGrantFunction.aspx.cs" Inherits="McsComplain.GrantFunction" MaintainScrollPositionOnPostback="true" %>
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<title></title>
<link rel="stylesheet" href="cssArunaGrantedFuntions.css" />
<script src="D:UsersMcsComplainscriptsjquery-1.4.2.min.js" type="text/javascript"></script>
<script type="text/javascript" language="JavaScript">
function ddlcheck() {
var value = document.getElementById('<%=ddlUser.ClientID%>').value;
if (value == 0) {
alert("Please Select Role ID");
return false;
}
}
$("#dvMessage").show("slow").delay(5000).hide("slow");
</script>
</head>
<body>
<div class="container">
<div class="title">Grant Functions</div>
<form id="form2" runat="server">
<div class="select-box">
<asp:Label ID="lblSelectHeader" class="details" runat="server">Select Role</asp:Label>
<asp:DropDownList ID="ddlUser" runat="server" OnSelectedIndexChanged="ddlUser_SelectedIndexChanged" AutoPostBack="True">
</asp:DropDownList>
</div>
<div class="function-details">
<div class="input-box">
<asp:Label ID="lblAllFunction" class="details" runat="server" Text="">All Function</asp:Label>
<div class="scroll">
<asp:GridView ID="grdAllFunctions" runat="server" AutoGenerateColumns="False" CellPadding="4" ForeColor="#333333" GridLines="None" OnRowCommand="grdAllFunctions_RowCommand"
Width="100%">
<AlternatingRowStyle BackColor="White" />
<Columns>
<asp:BoundField DataField="FUNCTION_ID" HeaderText="Function ID" />
<asp:BoundField DataField="FUNCTION_NAME" HeaderText="Function Name" />
<asp:ButtonField Text="Grant" ButtonType="Button" />
</Columns>
<EditRowStyle BackColor="#7C6F57" />
<FooterStyle BackColor="#1C5E55" Font-Bold="True" ForeColor="White" />
<HeaderStyle BackColor="#1C5E55" Font-Bold="True" ForeColor="White" />
<PagerStyle BackColor="#666666" ForeColor="White" HorizontalAlign="Center" />
<RowStyle BackColor="#E3EAEB" />
<SelectedRowStyle BackColor="#C5BBAF" Font-Bold="True" ForeColor="#333333" />
<SortedAscendingCellStyle BackColor="#F8FAFA" />
<SortedAscendingHeaderStyle BackColor="#246B61" />
<SortedDescendingCellStyle BackColor="#D4DFE1" />
<SortedDescendingHeaderStyle BackColor="#15524A" />
</asp:GridView>
</div>
</div>
<div class="input-box">
<asp:Label ID="lblGrantedFunction" class="details" runat="server" Text="">Granted Function</asp:Label>
<%-- Allocated function tabel --%>
<div style="max-height: 280px; overflow-y: scroll;">
<asp:GridView ID="grdGrantedFunctions" runat="server" AutoGenerateColumns="False" CellPadding="4" ForeColor="#333333" GridLines="None" OnRowCommand="grdGrantedFunctions_RowCommand1"
Width="100%">
<AlternatingRowStyle BackColor="White" />
<Columns>
<asp:BoundField DataField="FUNCTION_ID" HeaderText="Function ID " />
<asp:BoundField DataField="FUNCTION_NAME" HeaderText="Function Name" />
<asp:ButtonField Text="Revoke" ButtonType="Button" />
</Columns>
<EditRowStyle BackColor="#7C6F57" />
<FooterStyle BackColor="#1C5E55" Font-Bold="True" ForeColor="White" />
<HeaderStyle BackColor="#1C5E55" Font-Bold="True" ForeColor="White" />
<PagerStyle BackColor="#666666" ForeColor="White" HorizontalAlign="Center" />
<RowStyle BackColor="#E3EAEB" />
<SelectedRowStyle BackColor="#C5BBAF" Font-Bold="True" ForeColor="#333333" />
<SortedAscendingCellStyle BackColor="#F8FAFA" />
<SortedAscendingHeaderStyle BackColor="#246B61" />
<SortedDescendingCellStyle BackColor="#D4DFE1" />
<SortedDescendingHeaderStyle BackColor="#15524A" />
</asp:GridView>
</div>
</div>
</div>
<div id="dvMessage" runat="server" visible="false" class="alert-success">
<strong>
<asp:Label ID="lblErrorMsg" runat="server" Text=""></asp:Label></strong>
<asp:Label ID="lblMessage" runat="server" Text=""></asp:Label>
</div>
</form>
</div>
</body>
</html>
2
Answers
The smoothest way to solve this would be to utilize AJAX so that the entire page doesn’t reload on postback. Depending on your exact scenario, the easiest way to accomplish this would be to throw the grid in an UpdatePanel.
https://learn.microsoft.com/en-us/dotnet/api/system.web.ui.updatepanel?view=netframework-4.8
Never was aware that the MaintainScrollPositionOnPostback tag existed!!
but, what you can do is as noted is wrap the gv in a update panel.
So, assuming this markup:
And code behind to fill is this:
So we now have this:
But if I scroll down, and then use the delete button in above, it does cause a post-back, and thus the grid scrolls back to top.
However, as suggesed, we can wrap the GV in a update paneal.
So, right after form tag, drag + drop in a script manager.
Then collapse the gv, and then drag + drop in a update panel.
Then wrap the update panel around the GV like this:
Now, when you click a button on the grid, it will not post back the whole page – your position should remain.