c# - 带有动态下拉列表列的 GridView 中的动态 ItemTemplate

标签 c# asp.net gridview drop-down-menu

我正在尝试在 asp.net gridview 中创建动态列,并且在这些动态列中我需要插入一个动态下拉列表。最终结果应如下所示:

enter image description here

请注意此网格的右上角,其中有 HSE1、HSE2 等。在上面的示例中,这些列的含义会发生变化,我可能还有一个额外的 HSE8、HSE9 等。基本上,这些列是动态的。为了做到这一点,我做了以下工作,这是我的 gridview 的 asp.net 标记:

 <asp:GridView ID="gvMain" runat="server"
    AutoGenerateColumns="False"
    Width="100%" DataKeyNames="AreaLevelCostCenterFunctionID" OnPreRender="gvMain_PreRender" >
    <Columns>
        <asp:TemplateField HeaderText="JobTitle" >
            <ItemTemplate>
                <asp:HyperLink CssClass="loaderLink" ID="hlAreaLevel" runat="server" NavigateUrl='<%# "/Views/Training/AreaLevel/Details.aspx?AreaLevelID=" + 
                    Eval("AreaLevelCostCenter.AreaLevelID") %>' Text='<%# Eval( "AreaLevelCostCenter.AreaLevel.AreaLevel1" )%>' ToolTip="Area Level">
                </asp:HyperLink>
            </ItemTemplate>
            <ItemStyle HorizontalAlign="Left"></ItemStyle>
            <HeaderStyle HorizontalAlign="Left"></HeaderStyle>
        </asp:TemplateField>

        <!--HERE'S WHERE I ADD MY DYNAMIC COLUMNS -->
    </Columns>
    <PagerSettings Position="TopAndBottom" />
</asp:GridView>

为了填充这个 gridview(绑定(bind)它),我使用以下内容:

private void SetGvMainGridData(IEnumerable<AreaLevel> newNameList)
{
    if (newNameList != null)
    {
        BuildGridAdditionalColumns();
        gvMain.DataSource = newNameList;
        gvMain.DataBind();
        upData.Update();
    }
}

我的问题是每次我对数据进行分页或回发以过滤数据时,列数都会重复。它每次都一遍又一遍地重新创建相同的列。所以我写了一些代码来删除它,但我认为它看起来不太好。参数 newNameList 是 HSE 1、HSE 2 等类(class)的列表。以下是 BuildGridAdditionalColumns 的作用:

private void BuildGridAdditionalColumns()
{

   using (var db = DataCenterAccess.NewConnection())
    {
        var tManager = new TrainingManager(db, CurrentUser);
         //get the courses, THE HSE 1, HSE 2, etc...
        var preDefinedCourses = tManager.GetTrainingPredefinedCourses();
        if (preDefinedCourses != null && preDefinedCourses.Any())
        {
            foreach (var course in preDefinedCourses)
            {
                // Declare the template field
                TemplateField bfield = new TemplateField();
                //Initalize the DataField value.
                bfield.ItemTemplate = new GridViewTemplate(ListItemType.Item, course.TrainingPredefinedCourse1);
                //Initialize the HeaderText field value.
                bfield.HeaderText = course.TrainingPredefinedCourse1;

                //Add the newly created bound field to the GridView.
                gvMain.Columns.Add(bfield);
            }
        }
    }
}

请注意我是如何做的 bfield.ItemTemplate = new GridViewTemplate(ListItemType.Item, course.TrainingPredefinedCourse1); 我必须创建一个界面来支持此功能,请参阅此 stackoverflow 帖子以获取更多信息:How to add TemplateField to a gridview in the code behind?

基本上那个界面是这样的:

 public class GridViewTemplate : ITemplate
    {
        //A variable to hold the type of ListItemType.
        readonly ListItemType _templateType;
        //A variable to hold the column name.
        readonly string _columnName;
        //Constructor where we define the template type and column name.

        public GridViewTemplate(ListItemType type, string colname)
        {
            //Stores the template type.
            _templateType = type;

            //Stores the column name.
            _columnName = colname;

        }

        void ITemplate.InstantiateIn(Control container)
        {
            if (_templateType == ListItemType.Item)
            {
                //Creates a new drop down list control.
                DropDownList ddl = new DropDownList {ID = _columnName}; 
                ddl.Attributes.Add("class","chosen-select");
                ddl.Width = 70;
                //get the data to populate ddl
                var tList = Utilities.GetCourseKeys().ToList();
                var selectedValues = (from t in tList select new ListItem( t.KeyValue, t.TrainingPredefinedCourseKeyID.ToString())).ToList();
                //add empty option to items and bind
                selectedValues.Insert(0, new ListItem());
                ddl.DataSource = selectedValues;
                ddl.DataBind();
                // ddl.DataBinding += new EventHandler(tb1_DataBinding);   //Attaches the data binding event.
                container.Controls.Add(ddl); //Adds the newly created ddl to the container.
            }
        }
    }

当我回发或刷新此数据时,我基本上遇到了两个问题。一个问题是这些列最终会重复出现。另一个问题是数据绑定(bind)停止工作(即 x,y 值变为空)。

最佳答案

我认为你应该动态创建整个网格看下面的代码

                    string tempnum = "txtbox";
                    TemplateField temp1 = new TemplateField();
                    temp1.HeaderStyle.Width = Unit.Pixel(101);
                    temp1.HeaderStyle.CssClass = "headerwidth";
                    temp1.HeaderText = "txt";
                    temp1.ItemTemplate = new CreateTextBox(tempnum);
                    GridView1.Columns.Add(temp1);

关于c# - 带有动态下拉列表列的 GridView 中的动态 ItemTemplate,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41771846/

相关文章:

c# - 无法在 CRM 中创建记录

c# - 在 asp.net 中克服发送电子邮件延迟的方法

javascript - 下载在 GridView 中选中的文件的更好方法

javascript - 一个很好的 vue 网格替代方案,而不是使用 vue infinite loader

c# - "SqlDbType"和 "size"在添加SqlCommand参数时应该什么时候使用?

c# - 如何在 Entity Framework 数据上下文中的属性名称中使用 sql 保留关键字?

c# - Automapper:从自动映射对象解析源属性名称

asp.net - 将网站移至新主机导致 "forbidden"

asp.net - 如何在 ASP.NET vNext 中处理调试/发布配置转换

c# - DataKeyNames 在 ASP.NET GridView 中作为不需要的更新参数出现