在 DataGridView 中过滤外键

Posted

技术标签:

【中文标题】在 DataGridView 中过滤外键【英文标题】:Filter foreign keys in DataGridView 【发布时间】:2018-03-06 16:16:23 【问题描述】:

我正在使用 C# 和 DataGridView WinForms,绑定到 DataTable。我的 DataGridView 包含以下列:

MaterialId(只读外键显示材料标题) PricelistId(带有可选外键的DataGridViewComboBoxCell)

每种材料都有属于它的特定价目表。此信息存在于我的价格表中。

目前,当我单击 PricelistId 组合时,我会获取所有价目表,无论它们属于什么材料。但我想根据 MaterialId 值过滤它。因此,例如,如果第一行的材料是钢材,则价目表字段中应仅显示钢材价目表。如果第二行的材料是塑料,则相应的组合中应仅显示与塑料相关的价目表。

这可能吗?

谢谢!

【问题讨论】:

DataGridView Cascading/Dependent ComboBox Columns @RezaAghaei 非常感谢,这正是我所需要的。我会将其转换为 C#,根据我的需要对其进行一些调整并在此处发布。再次感谢! 【参考方案1】:

根据@RezaAghaei 的评论,这里是为我的需要量身定制的 C# 原型,同时修复了一个问题(当前选定的项目将重置)。

谢谢!

public partial class Form1 : Form

    private DataGridView _dataGridView = new DataGridView();
    private DataSet _dataSet = new DataSet();


    public Form1()
    
        InitializeComponent();

        GenerateDataSet();
        CreateDataGridView();
    


    private void CreateDataGridView()
    
        var MaterialsColumn = new DataGridViewComboBoxColumn
        
            DataPropertyName = "MaterialId",
            HeaderText = "Material",
            DataSource = _dataSet.Tables["Materials"],
            DisplayMember = "Name",
            ValueMember = "Id",
            Name = "MaterialColumn",
            ReadOnly = true
        ;

        var PricelistsColumn = new DataGridViewComboBoxColumn
        
            DataPropertyName = "PricelistId",
            HeaderText = "Pricelist",
            DataSource = _dataSet.Tables["Pricelists"],
            DisplayMember = "Name",
            ValueMember = "Id",
            Name = "PricelistColumn"
        ;

        _dataGridView.AutoGenerateColumns = false;
        _dataGridView.Columns.AddRange(MaterialsColumn, PricelistsColumn);
        _dataGridView.DataSource = _dataSet.Tables["PricelistAssignments"];

        _dataGridView.Dock = DockStyle.Fill;
        _dataGridView.EditingControlShowing += EditingControlShowing;
        _dataGridView.AllowUserToAddRows = false;
        _dataGridView.AllowUserToDeleteRows = false;
        Controls.Add(_dataGridView);
    


    private void GenerateDataSet()
    
        // Create tables
        _dataSet.Tables.Add("Materials");
        _dataSet.Tables["Materials"].Columns.Add("Id", typeof(int));
        _dataSet.Tables["Materials"].Columns.Add("Name", typeof(string));

        _dataSet.Tables.Add("Pricelists");
        _dataSet.Tables["Pricelists"].Columns.Add("Id", typeof(int));
        _dataSet.Tables["Pricelists"].Columns.Add("Name", typeof(string));
        _dataSet.Tables["Pricelists"].Columns.Add("MaterialId", typeof(int));

        _dataSet.Tables.Add("PricelistAssignments");
        _dataSet.Tables["PricelistAssignments"].Columns.Add("MaterialId", typeof(int));
        _dataSet.Tables["PricelistAssignments"].Columns.Add("PricelistId", typeof(int));

        // Populate tables
        _dataSet.Tables["Materials"].Rows.Add(1, "Steel");
        _dataSet.Tables["Materials"].Rows.Add(2, "Plastic");
        _dataSet.Tables["Pricelists"].Rows.Add(1, "PL Steel 1", 1);
        _dataSet.Tables["Pricelists"].Rows.Add(2, "PL Plastic 1", 2);
        _dataSet.Tables["Pricelists"].Rows.Add(3, "PL Steel 2", 1);
        _dataSet.Tables["Pricelists"].Rows.Add(4, "PL Plastic 2", 2);
        _dataSet.Tables["Pricelists"].Rows.Add(5, "PL Plastic 3", 2);
        _dataSet.Tables["PricelistAssignments"].Rows.Add(1, 3);
        _dataSet.Tables["PricelistAssignments"].Rows.Add(1, 1);
        _dataSet.Tables["PricelistAssignments"].Rows.Add(2, 4);
    


    private void EditingControlShowing(object sender, DataGridViewEditingControlShowingEventArgs e)
    
        var grid = (DataGridView)sender;

        if (grid.CurrentCell.ColumnIndex == 1) // Pricelist column
        
            var combo = (DataGridViewComboBoxEditingControl)e.Control;
            var selectedValue = combo.SelectedValue;
            var data = _dataSet.Tables["Pricelists"].AsDataView();
            data.RowFilter = "MaterialId = " + grid.CurrentRow.Cells[0].Value.ToString();
            combo.DataSource = data;
            combo.SelectedValue = selectedValue;
        
    

【讨论】:

以上是关于在 DataGridView 中过滤外键的主要内容,如果未能解决你的问题,请参考以下文章

勾选复选框时如何在DataGridView中执行计算C#

C# datagridviewdatagridGridControl增加行号

DataGridView显示日期格式问题

如何在 c# 中禁用可点击的 datagridview 中的空单元格

问题 Datagridview 和外键和主键列

datagridview DragDrop 实现拖放后 获取所在单元格的位置