我正在将GenericTable作为GridView的自定义实现,它将显示插入的任何对象列表的值.

要在aspx页面上使用该控件,它需要是UserControl,因此GridView作为GenericTable中的组件包含在内:

<%@ Control Language="C#" AutoEventWireup="true" CodeBehind="GenericTable.ascx.cs" Inherits="CASH.WebApplication.Controls.GenericTable" %>
<div style="width: 100%; overflow: scroll">
    <asp:GridView ID="grid" runat="server"></asp:GridView>
</div>

这适用于我的控件的第一次使用,它已添加到aspx页面.似乎这样做会增加某种启动控制组件的魔力.
当用户单击具有其自身属性的项时,GenericTable应在当前行下方插入一行并生成将显示所述属性的新GenericTable. table是我用来设置GridView内容的DataTable:

var data = table.NewRow();
var child = new GenericTable();

data[0] = child;

table.Rows.InsertAt(data,row);
grid.DataSource = table;
grid.DataBind(); // The extra row is displayed Now,initialize components in the aspx code?
child.MakeTable(); // Throws exception because it's `grid` property is null.

当我尝试激活新制作的GenericTable时,在此代码之后,它的网格为空.

有没有办法初始化此控件位于aspx代码中时发生的相同魔术?

更新:也许问题在于如何在回发之间存储表,目前我正在使用会话,也许有更好的方法来记住用户输入?
整个GenericTable代码:

using Project.DomainModel.Models;
using System;
using System.Collections.Generic;
using System.Data;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Web.UI;
using System.Web.UI.WebControls;

namespace CASH.WebApplication.Controls
{
    public partial class GenericTable : UserControl
    {
        private PropertyInfo[] properties;
        //private GridView gridView;
        private DataTable table = new DataTable();
        private Dictionary<int,int> ingedrukt = new Dictionary<int,int>();

        protected void Page_Init(object sender,EventArgs e)
        {
            grid.RowCommand += WeergaveDossiers_RowCommand;
        }

        protected void Page_Load(object sender,EventArgs e)
        {
            if (!IsPostBack)
            {
                for (int i = 0; i < grid.Rows.Count; i++)
                {
                    grid.Rows[i].Cells[0].ColumnSpan = 0;
                }
            }
            else
            {
                properties = (PropertyInfo[])Session["properties"];
                table = (DataTable)Session["table"];
                ingedrukt = (Dictionary<int,int>)Session["ingedrukt"];

                foreach (var knop in ingedrukt)
                {
                    DetailRijToevoegen(knop.Key,knop.Value);
                }
            }

            grid.DataBind();
        }

        protected void SaveInSession()
        {
            Session["properties"] = properties;
            Session["table"] = table;
            Session["ingedrukt"] = ingedrukt;
        }

        protected void WeergaveDossiers_RowCommand(object sender,GridViewCommandEventArgs e)
        {
            int row = int.Parse((string)e.CommandArgument) + 1;
            int col = GetKolomIndex(e.CommandName) + 1;

            if (ingedrukt.ContainsKey(row))
            {
                if (ingedrukt[row] != col)
                {
                    //DetailRijVerwijderen(row);
                    //ingedrukt.Remove(row);
                    //ingedrukt[row] = col;
                }
            }
            else
            {
                ingedrukt[row] = col;
            }

            //DetailRijToevoegen(row,col);
            SaveInSession();
        }

        protected void DetailRijToevoegen(int row,int col)
        {
            var data = table.NewRow();
            var child = new GenericTable();
            child.grid = new GridView();

            data[0] = child;

            table.Rows.InsertAt(data,row);
            grid.DataSource = table;
            grid.DataBind();

            var cells = grid.Rows[row].Cells;
            // Only keep the first cell
            while (cells.Count > 1)
            {
                cells.RemoveAt(1);
            }

            child.MaakTable(new List<object>() { table.Rows[row][col] });

            grid.Columns[0].Visible = true;
            grid.Rows[row].Cells[0].ColumnSpan = table.Columns.Count;
        }

        protected void DetailRijVerwijderen(int row)
        {

        }

        protected int GetKolomIndex(string naam)
        {
            for (int i = 0; i < properties.Length; i++)
            {
                if (properties[i].Name == naam)
                {
                    return i;
                }
            }

            throw new InvalidDataException("Kolom naam " + naam + " niet bekend");
        }

        public void MaakTable(IEnumerable<object> data)
        {
            properties = data.First().GetType().GetProperties().Where(p => p.CanRead).ToArray();

            grid.AutoGenerateColumns = false;
            var details = new BoundField();
            details.datafield = "Details";
            grid.Columns.Add(details);

            table.Columns.Add(new DataColumn("Details",typeof(object)));
            foreach (var veld in properties)
            {
                table.Columns.Add(new DataColumn(veld.Name,(veld.Name == "Id" ? typeof(object) : veld.PropertyType)));
                grid.Columns.Add(MaakKolom(veld));
            }

            foreach (var entry in data)
            {
                var row = table.NewRow();
                int col = 0;

                foreach (var veld in properties)
                {
                    row[++col] = veld.GetValue(entry);
                }

                table.Rows.Add(row);
            }

            grid.DataSource = table;

            SaveInSession();
        }

        protected DataControlField MaakKolom(PropertyInfo veld)
        {
            DataControlField field;

            if (typeof(Entity).IsAssignableFrom(veld.PropertyType))
            {
                field = new ButtonField();
                ((ButtonField)field).DataTextField = veld.Name;
                ((ButtonField)field).ButtonType = ButtonType.Button;
                ((ButtonField)field).CommandName = veld.Name;
            }
            else if (veld.PropertyType == typeof(bool))
            {
                field = new CheckBoxField();
                ((CheckBoxField)field).datafield = veld.Name;
            }
            else if (veld.PropertyType.IsEnum)
            {
                field = new TemplateField();
                //((TemplateField)field).ItemTemplate = (ITemplate)new Label()
                //{
                //  Text = "#DataBinder.Eval(\"" + veld.Name + "\")",//};
            }
            else if (veld.PropertyType == typeof(DateTime))
            {
                field = new TemplateField();
                //field.DatePicker = true;
            }
            else
            {
                field = new BoundField();
                ((BoundField)field).datafield = veld.Name;
            }

            field.HeaderText = veld.Name;

            return field;
        }

        protected void OnRowDataBound(object sender,GridViewRowEventArgs e)
        {
            if (e.Row.RowType == DataControlRowType.DaTarow)
            {

            }
        }
    }
}

解决方法

我不确定你想要实现什么,我只知道你所做的事情根本就是错误的(好吧,就ASP.NET的世界观而言……).

>您将控件添加到输入数据,而不是将其添加为网格的子控件.
>您没有在控件的consructor中实例化GridView控件.
> Session绝对是存储大量页面相关数据的错误位置.

我将从最后一点开始:如果这是在访问站点之间需要持续存在的数据,那么您必须将其放入数据库中.如果这是仅在某人登录时存在的数据,直到他们注销的时间,那么是,会话可能是适合它的地方.否则,如果它特定于页面并且应该在用户访问另一个页面时被丢弃,那么您应该每次从数据库重新加载它或者可以将它存储在ViewState中.

接下来,是相同类型的所有对象/它们是否具有相同的字段?如果是这样,那么默认行为(由AutoGenerateColumns显式控制将为您完成工作,无需额外的工作:

<asp:GridView runat="server"
    ID="grid"
    AutoGenerateColumns="true" />

如果没有相同的列,那么它们应该是单独的网格; GridView是一种创建HTTP< table>的方法.元件.表元素应该只包含相关数据;你不会用一张桌子来显示鱼的价格和汽车的颜色.由此得出,如果你有不同的表,有不相关的数据,那么你应该有不同的数据源…一个更简单的解决方案,这意味着你不需要实现你试图实现的控件.

最后,为了完整性,当您定义控件时,您只是创建一个类.如果您希望能够以您尝试的方式实例化控件,那么您需要确保其所有数据成员都在构造函数中实例化,或者任何引用都由空引用检查保护:

if (grid != null)
{
    // Do stuff with grid
}

c# – 为什么我的自定义控件的组件未启动?的更多相关文章

  1. HTML5 Web缓存和运用程序缓存(cookie,session)

    这篇文章主要介绍了HTML5 Web缓存和运用程序缓存(cookie,session),小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧

  2. iOS Swift上弃用后Twitter.sharedInstance().session()?. userName的替代方案

    解决方法如果您仍在寻找解决方案,请参阅以下内容:

  3. 使用Fabric SDK iOS访问Twitter用户时间线

    我试图在这个问题上挣扎两天.我正在使用FabricSDK和Rest工具包,试图为Twitter使用不同的RestAPIWeb服务.我可以使用具有authTokenSecret,authToken和其他值的会话对象的TWTRLogInButton成功登录.当我尝试获取用户时间线时,我总是得到失败的响应,作为:{“errors”:[{“code”:215,“message”:“BadAuthentic

  4. ios – 如何从Apple Watch调用iPhone上定义的方法

    有没有办法从Watchkit扩展中调用iPhone上的类中定义的方法?根据我的理解,目前在Watchkit和iPhone之间进行本地通信的方法之一是使用NSUserDefaults,但还有其他方法吗?

  5. ios – 如何将视频从AVAssetExportSession保存到相机胶卷?

    在此先感谢您的帮助.解决方法只需使用session.outputURL=…

  6. ios – 使用AVCaptureSession sessionPreset = AVCaptureSessionPresetPhoto拉伸捕获的照片

    解决方法所以我解决了我的问题.这是我现在使用的代码,它工作正常:…重要的输出imagaView:一些额外的信息:相机图层必须是全屏,并且outputimageView也必须是.我希望这些对某些人来说也是有用的信息.

  7. 我可以在iOS中自定义Twitter工具包的登录按钮吗?

    我已经下载了Twitter工具包框架并添加了用Twitter登录的代码.但是,我不希望登录按钮看起来像那样.我想要一个用于登录的自定义按钮.我能这样做吗?我只想使用这个框架,因为这也适用于iOS系统帐户.解决方法根据document:在按下按钮中添加代码:Objective-C的迅速

  8. ios – AVCaptureSession条形码扫描

    解决方法以下是我所拥有的项目代码示例,可以帮助您走上正确的轨道

  9. ios – 如何在Watch OS 2中引用不支持的框架

    有没有办法将框架链接到扩展名?

  10. ios7 – 在iOS 7中设置Alamofire中的自定义HTTP标头不工作

    解决方法我得到它的工作这对iOS7没有影响:然而,这将适用于iOS7和8:

随机推荐

  1. c# – (wpf)Application.Current.Resources vs FindResource

    所以,我正在使用C#中的WPF创建一个GUI.它看起来像这样:它现在还没有完成.这两行是我尝试制作一种数据表,它们在XAML中是硬编码的.现在,我正在C#中实现添加新的水果按钮功能.我在XAML中有以下样式来控制行的背景图像应该是什么样子:因此,在代码中,我为每列col0,col1和col2创建一个图像,如果我使用以下代码,它添加了一个如下所示的新行:如你所见,它不太正确……为什么一个似乎忽略了一些属性而另一个没有?

  2. c# – 绑定DataGridTemplateColumn

    似乎我已经打了个墙,试图在DataGrid上使用DataTemplates.我想要做的是使用一个模板来显示每个单元格的两行文本.但是似乎无法以任何方式绑定列.以下代码希望显示我想做的事情.注意每个列的绑定:模板列没有这样的东西,因此,这个xaml不可能工作.我注定要将整个DataTemplate复制到每个列,只是对每个副本都有不同的约束?解决方法我不完全确定你想要做什么,但如果您需要获取整行的DataContext,可以使用RelativeSource绑定来移动视觉树.像这样:

  3. c# – 学习设计模式的资源

    最近我来到了这个设计模式的概念,并对此感到非常热情.你能建议一些帮助我深入设计模式的资源吗?

  4. c# – 是否有支持嵌入HTML页面的跨操作系统GUI框架?

    我想开发一个桌面应用程序来使用跨系统,是否有一个GUI框架,允许我为所有3个平台编写一次代码,并具有完全可脚本化的嵌入式Web组件?我需要它有一个API来在应用程序和网页之间进行交流.我知道C#,JavaScript和一些python.解决方法Qt有这样的事情QWebView.

  5. c# – 通过字符串在对象图中查找属性

    我试图使用任意字符串访问嵌套类结构的各个部分.给出以下(设计的)类:我想要从Person对象的一个实例的“PersonsAddress.HousePhone.Number”获取对象.目前我正在使用反思来做一些简单的递归查找,但是我希望有一些忍者有更好的想法.作为参考,这里是我开发的(crappy)方法:解决方法您可以简单地使用标准的.NETDataBinder.EvalMethod,像这样:

  6. c# – 文件下载后更新页面

    FamilyID=0a391abd-25c1-4fc0-919f-b21f31ab88b7&displaylang=en&pf=true它呈现该页面,然后使用以下元刷新标签来实际向用户提供要下载的文件:你可能需要在你的应用程序中做类似的事情.但是,如果您真的有兴趣在文件完全下载后执行某些操作,那么您的运气不佳,因为没有任何事件可以与浏览器进行通信.执行此操作的唯一方法是上传附件时使用的AJAXupload.

  7. c# – 如何在每个机器应用程序中实现单个实例?

    我必须限制我的.net4WPF应用程序,以便每台机器只能运行一次.请注意,我说每个机器,而不是每个会话.我使用一个简单的互斥体实现单实例应用程序,直到现在,但不幸的是,这样一个互斥是每个会话.有没有办法创建机器互连,还是有其他解决方案来实现每个机器应用程序的单个实例?

  8. c# – WCF和多个主机头

    我的雇主网站有多个主机名,都是同一个服务器,我们只是显示不同的皮肤来进行品牌宣传.不幸的是,在这种情况下,WCF似乎不能很好地工作.我试过overridingthedefaulthostwithacustomhostfactory.这不是一个可以接受的解决方案,因为它需要从所有主机工作,而不仅仅是1.我也看过thisblogpost,但是我无法让它工作,或者不是为了解决我的问题.我得到的错误是“这

  9. c# – ASP.NET MVC模型绑定与表单元素名称中的虚线

    我一直在搜索互联网,试图找到一种方式来容纳我的表单元素的破折号到ASP.NET的控制器在MVC2,3或甚至4中的默认模型绑定行为.作为一名前端开发人员,我更喜欢在我的CSS中使用camelCase或下划线进行破折号.在我的标记中,我想要做的是这样的:在控制器中,我会传入一个C#对象,看起来像这样:有没有办法通过一些正则表达式或其他行为来扩展Controller类来适应这种情况?我讨厌这样的事实,我必须这样做:甚至这个:思考?

  10. c# – 用户界面设计工具

    我正在寻找一个用户界面设计工具来显示文档中可能的GUI.我不能生成代码.我知道MicrosoftVisio提供了一个功能.但有什么办法吗?您使用哪种软件可视化GUI?

返回
顶部