简体   繁体   中英

How to program Combox in dataGridView?

How to program Combox in dataGridView?
The following code does not lead to the result.

Data tables parsitsya in Datatable.
I want to make the "combox" displayed for the "Type" field

在此处输入图片说明 Code

  DataTable dt;        

OleDbConnection connection;
OleDbDataAdapter adapter;
OleDbCommandBuilder commandBuilder;


        static string catBD = @"z:\vs\csharp\prb\db_GridVAccess.accdb";
        string connectionString = string.Format("Provider=Microsoft.ACE.OLEDB.12.0;Data Source={0}", catBD);

        string sql = "SELECT * FROM tbl_01_Combox";

        public Form5()
        {
            InitializeComponent();


            using (OleDbConnection cn = new OleDbConnection())
            {
                connection = new OleDbConnection(connectionString);
                connection.Open();

                adapter = new OleDbDataAdapter(sql, connection);

                commandBuilder = new OleDbCommandBuilder(adapter);

                // На соновании DataTable
                dt = new DataTable();
                adapter.Fill(dt);
                dataGridView1.DataSource = dt;
            }
        }

        private void Form5_Load(object sender, EventArgs e)
        {
            // Ширина поля            
            dataGridView1.Columns[0].Width = 50;

            // Комбокс
            string[] countrys = new string[] { "США", "ОАЭ", "ЮАР" };
            (dataGridView1.Columns[1] as DataGridViewComboBoxColumn).DataSource = countrys;

        }

I believe the problem is your "countrys" isn't observable, plus it has to be a property. Consider the following code:

private ObservableCollection<string> _Countries;    
public ObservableCollection<string> Countries
{
    get { return _Countries; }
    set { _Countries = value; }
}

Initialize and set its contents in your Form5_Load and see if it works.

EDIT 1:

I was curious, so I actually created a project and tried to recreate the problem, and I believe the real problem here is that your DataGridView is populated according to the info you get from DB. I looked into it a bit further, and found this post on SO:

C# Replace default textbox in DataGridView with a Combobox

According to it, you can't change the type of the column to DataGridView ComboBox Column, after it's already been created as DataGridView TextBox Column according to the data you got from DB. It also suggests two different approaches to the case, which do sound realistic. I hope you can figure it out, good luck.

EDIT 2:

Per your request, I'll try to figure the way to accomplish it with changing the data you get from DB.

In the following piece of code, you have a "dt" object which has data that you want to show in your DataGridView.

dt = new DataTable();    
adapter.Fill(dt);
dataGridView1.DataSource = dt;

I've never done it myself, and I can't really recreate it anyhow fast, but I suggest you try and play with the contents of the object "dt". I suppose the code which happens in "adapter.Fill" creates the DataTable according to the data from db, you can try and add there some code which will add a List instead of a string for the "type" column (It will then help create a ComboBoxColumn instead of TextBoxColumn as far as I follow). I actually checked it our right now, and it looks to be a bit complicated, but I really don't know what's happening there in your program, it might just be as easy as it gets.

Anyway, I did try to do it another way, instead of changing the existing column type, I added a new DataGridViewComboBoxColumn of my own, to the end of the automatically populated DataGridView:

在此处输入图片说明

DataTable dt = new DataTable();
dataGridView2.DataSource = dt;

DataGridViewComboBoxColumn newColumn = new DataGridViewComboBoxColumn();

newColumn.DataSource = new List<string> { "asd", "qwe", "zxc" };

dataGridView2.Columns.Add(newColumn);

You then can just remove/delete the irrelevant "type" column that you got from db. But, then you'll face some other problems along the way, as connecting the selected object in combobox to the other data in the row. It's not complicated, but can get relatively ugly.

Edited:

If you have set the DataGridView.AutoGenerateColumns = true and the columns are generated automatically, the type of column "type" is not ComboBox. in that case you can create a new column, set it up and then replace the old column with it:

DataGridViewComboBoxColumn column = new DataGridViewComboBoxColumn();
int i = 0;
column.DataPropertyName = "type";
column.DataSource = countrys.Select(x => new { Key = i++, Value = x }).ToList();
column.DisplayMember = "Value";
column.ValueMember = "Key";
dataGridView1.Columns.RemoveAt(1);
dataGridView1.Columns.Insert(1, column);

the previous code didn't work because column[1] could not be cast into DataGridViewComboBoxColumn so (dataGridView1.Columns[1] as DataGridViewComboBoxColumn) would return a null and because you have put the code in Form_Load the Exception was omitted.

Original:

try this:

int i = 0;
(dataGridView1.Columns[1] as DataGridViewComboBoxColumn).DataSource = countrys.Select(x=> new {Key = i++, Value = x}).ToList();
(dataGridView1.Columns[1] as DataGridViewComboBoxColumn).DisplayMember = "Value";
(dataGridView1.Columns[1] as DataGridViewComboBoxColumn).ValueMember = "Key";

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM