如何委托telerik网格视图常用方法从每个子页面的父页面调用?

Posted

技术标签:

【中文标题】如何委托telerik网格视图常用方法从每个子页面的父页面调用?【英文标题】:How to delegate telerik grid view common methods to be call from parent page from every child page? 【发布时间】:2016-03-27 09:19:15 【问题描述】:

我正在使用Telerik Gridview 来显示记录列表,并且我有超过 10 页 我正在使用此 gridview 并粘贴以下常见事件代码副本(有一些小的更改)所有这些页面:

protected void Page_Load(object sender, EventArgs e)

    DisplayRecords()


public void DisplayRecords()

    //Grid view names are different on different pages.
    GridView1.DataSource=Fetching records from database.
    GridView1.DataBind();


protected void GridView1_SortCommand(object sender, GridSortCommandEventArgs e)

    DisplayRecords()


protected void GridView1_PageIndexChanged(object sender, GridPageChangedEventArgs e)

    var index = e.NewPageIndex;
    DisplayRecords()


protected void GridView1_PageSizeChanged(object sender, GridPageSizeChangedEventArgs e)

    var size = e.NewPageSize;
    DisplayRecords()

这是我继承自以下页面的一页:

public partial class LoadSettings : ParentPage

    //Load events and other events


[Serializable]
public class ParentPage: RadAjaxPage




Page 1:**ttt.aspx**
public void DisplayRecords()
    
        //Grid view names are different on different pages.
        GridView1.DataSource=this.GetAlltttData()
        GridView1.DataBind();
    

    public DataTable GetAlltttData()
            
                using (var context = new MyDataContext())
                
                    var data = from c in context.ttt select c;
                    return MyDataContext.LINQToDataTable(data);
                
            


Page 2:**bbb.aspx**
public void DisplayRecords()
    
        //Grid view names are different on different pages.
        GridView1.DataSource=this.GetAllbbbData()
        GridView1.DataBind();
    

    public DataTable GetAllbbbData()
            
                using (var context = new MyDataContext())
                
                    var data = from c in context.bbb select c;
                    return MyDataContext.LINQToDataTable(data);
                
            

protected void rgbbb_SortCommand(object sender, GridSortCommandEventArgs e)
        
           DisplayRecords()
        
protected void rgbbb_PageIndexChanged(object sender, GridPageChangedEventArgs e)
        
            var index = e.NewPageIndex;
            DisplayRecords()
        

 protected void rgbbb_PageSizeChanged(object sender, GridPageSizeChangedEventArgs e)
        
           var size = e.NewPageSize;
           DisplayRecords()
        

那么有没有可能我可以将所有这些事件放在这个 ParentPage 页面中,然后从每个子页面调用而不是用这些事件污染我的每个页面??

注意:在我的某些页面中,此 DisplayRecords 方法可以包含一些参数,但其余所有事件都是常见的。

【问题讨论】:

您不能创建一个已经包含此控件的母版页吗?您也可以使用父 Page 类来执行此操作,但您需要在 Init 事件上将控件动态添加到其父控件,以便其生命周期仍然有效 @Luizgrs:我无法将其保留在我的母版页上,因为每个页面上的网格定义都不同,所以我将如何维护它,所以我认为母版页解决方案不好。 母版页可以“链接”,我的意思是你可以有另一个母版页使用主页,只有这 10 个页面会使用第二个母版页 @Luizgrs: 你能发布任何描述这个的解决方案吗?请这样对我和其他人也有帮助 @Luizgrs: 你能看看这个问题上的答案 【参考方案1】:

也许您可以将通用逻辑放在抽象类中,方法(或属性)返回具体GridView 的引用并从此类继承。然后在每个页面上,您只需要实现该方法。

类似这样的:

public abstract class ParentPage

    public virtual void DisplayRecords()
    
        var gridView = this.GetGridView();
        gridView.DataSource = this.GetAllData();
        gridView.DataBind();
    

    protected abstract  DataTable GetAllData();

    protected string GetSortOrder()
    
        if (this.sortOrder != GridSortOrder.Assending)
            return string.Format("0 DESC", this.sortExpression)
        return this.sortExpression;
    

    protected void Page_Load(object sender, EventArgs e)
    
        DisplayRecords();
    

    protected void GridView1_SortCommand(object sender, GridSortCommandEventArgs e)
    
        if (!e.Item.OwnerTableView.SortExpressions.ContainsExpression(e.SortExpression))
        
            GridSortExpression sortExpr = new GridSortExpression();
            sortExpr.FieldName = e.SortExpression;
            sortExpr.SortOrder = GridSortOrder.Ascending;
            e.Item.OwnerTableView.SortExpressions.AddSortExpression(sortExpr);
        
    

    protected void GridView1_PageIndexChanged(object sender, GridPageChangedEventArgs e)
    
        e.Item.OwnerTableView.PageIndex = e.NewPageIndex;
        DisplayRecords();
    

    protected void GridView1_PageSizeChanged(object sender, GridPageSizeChangedEventArgs e)
    
        e.Item.OwnerTableView.PageSize = e.NewPageSize;
        DisplayRecords();
    


Page 1:**ttt.aspx**
public class **tttPage : BasePage 

    protected override GridView GetGridView()
    
        //return GridView of this page 
        return GridView1;
    

    protected override  DataTable GetAllData()
    
        using (var context = new MyDataContext())
        
            var data = c in context.ttt select c;
            return MyDataContext.LINQToDataTable(data);
        
    


Page 1:**bbb.aspx**
public class **bbbPage : BasePage

    protected override GridView GetGridView()
    
        //return GridView of this page 
        return GridView1;
    

    protected override  DataTable GetAllData()
    
        using (var context = new MyDataContext())
        
            var data = c in context.bbb select c;
            return MyDataContext.LINQToDataTable(data);
        
    

或者您可以将通用逻辑放在基类中,使用虚拟方法使用事件参数来获取GridView,例如e.Item.OwnerTableView

通过将其设为虚拟,您将能够在任何页面类中覆盖此逻辑

类似这样的:

public abstract class ParentPage<TEntity>

    public virtual void DisplayRecords(GridView gridView)
    
        gridView.DataSource = this.GetAllData();
        gridView.DataBind();
    

    protected abstract  DataTable GetAllData();

    protected void Page_Load(object sender, EventArgs e)
    
        DisplayRecords(e.Item.OwnerTableView);
    

    protected void GridView_SortCommand(object sender, GridSortCommandEventArgs e)
    
        DisplayRecords(e.Item.OwnerTableView);
    

    protected void GridView_PageIndexChanged(object sender, GridPageChangedEventArgs e)
    
        DisplayRecords(e.Item.OwnerTableView);
    

    protected void GridView_PageSizeChanged(object sender, GridPageSizeChangedEventArgs e)
    
        DisplayRecords(e.Item.OwnerTableView);
    


public class **tttPage : ParentPage 

    protected override  DataTable GetAllData()
    
        using (var context = new MyDataContext())
        
            var data = c in context.ttt select c;
            return MyDataContext.LINQToDataTable(data);
        
    


public class **bbbPage : ParentPage 

    protected override  DataTable GetAllData()
    
        using (var context = new MyDataContext())
        
            var data = c in context.bbb select c;
            return MyDataContext.LINQToDataTable(data);
        
    

您还可以使用泛型参数从 db 中获取值。

【讨论】:

因为我有多个页面,所以在所有这些页面上显示记录会有不同的表格来显示记录,所以我将如何在您的 DisplayRecords 方法中处理多个表格? @Learning 使用方法GetGridView 覆盖每个页面,您始终可以获取当前页面的表格并使用它。因此,您可以将每个页面的通用逻辑放在抽象类的DisplayRecords 方法中,并使用页面类中的“DisplayRecords”的覆盖版本添加自定义逻辑。也许您可以提供一些您的“DisplayRecords”方法的代码,我会尝试在示例中展示它? 查看我更新的问题,我添加了一些带有代码的页面 @Learning 我已经更新了我的答案,现在所有逻辑都与在单独的抽象方法中获取数据有关,您可以在每个页面上根据需要实现它。 @Learning 我在示例变量中添加了 event 可以设置所需状态(页面大小、索引、排序表达式),这个变量应该在 BaseClass 里面使用 DisplayRecords 方法来创建结果项目集。如果您可以添加代码如何为您的任何页面完成,我将展示一般如何执行此操作,或者如果您没有代码,我可以根据从 db 上下文中选择的内容编写我的变体。【参考方案2】:

在尝试重构代码时,您通常会应用许多原则。目前,您正在尝试重构代码以不违反DRY 原则(DRY = 不要重复自己)。 但是,您可能要考虑其他一些校长可能会参与其中。 single responsibility principle 表示每种方法只做一件明确的事情。 根据您的场景,您需要使用自定义列和自定义GridView 配置逻辑动态或运行时生成整个GridView,这将比在每个页面中编写这些事件更昂贵。 此外,所有事件都必须绑定到“GridView”才能正确触发。您不能将这些事件与其他文件分开,否则事件将不会触发。 您还有另一个使用 ASP.Net 用户控件的选项,但您需要再次编写逻辑来操作 GridView 自定义列和自定义 GridView 配置逻辑。所以再次让它变得更贵。所以我不建议这样做。最好为每个页面单独保留方法。

【讨论】:

以上是关于如何委托telerik网格视图常用方法从每个子页面的父页面调用?的主要内容,如果未能解决你的问题,请参考以下文章

当我们将 Telerik 网格与 LinqDataSource 一起使用时,如何在页面的各种按钮单击事件上重新生成网格数据

Telerik/ Kendo MVC Grid,按需加载网格,而不是页面加载

用于刷新页面和/或 Telerik 网格的 JavaScript 代码

如何将 webmethod 与 Telerik 批量编辑网格一起使用

无法识别 Telerik 网格中的选定页面。我需要在所选页面上加下划线。在这方面帮助我

如何将列表视图点击事件中的数据传递到另一个页面中的 Telerik 数据表单