Hallo,
ich abe eventuell nur ein Verständnispröblem ...
Ich nutze eine DataTable um die Daten für das DataGridView zu halten.
Die Definition:
m_ServerDataTable = new DataTable();
m_ServerDataTable.Columns.Add("Quelle");
DataColumn columnInvalid = new DataColumn();
columnInvalid.ColumnName = "Invalid";
columnInvalid.DataType = typeof(MSP_MF); // <- Enum
m_ServerDataTable.Columns.Add(columnInvalid);
DataColumn columnInverter = new DataColumn();
columnInverter.ColumnName = "Inverter";
columnInverter.DataType = typeof(bool);
m_ServerDataTable.Columns.Add(columnInverter);
m_ServerDataTable.Columns.Add("Senke");
Angebunden an das View:
dataGridViewServerData.DataSource = m_ServerDataTable;
Die Spalte "Inverter" wird als Checkbox angezeigt.
In der Spalte "Invalid" wird leider nur der übergebene Text eingetragen, ich hätte eine Combobox mit der Auswahl aus dem Enum erwartet.
Kann ich nach der Bindung an die DataTable den Typ der Spalte auf "ComboBox" ändern?
Ich habe bisher nur Beispiele gefunden in welchen die Spalte im Vorfeld als Combobox formatiert wird und dann dem Grid zugefügt wurde.
Nun sind meine Daten aber dynamisch und die Spalte die ich als Auswahl haben möchte ändert sich.
Ist der Ansatz falsch oder wo liegt mein Fehler?
Gruß RioFuTa.
Du erstellst ja irgendwo das DGV, und da musst du dann eben die entsprechenden DataGridViewComboBoxColumn erzeugen
Das DGV ist leer und ohne Datenquelle in Designer erstellt.
Die Spalten erstellen sich automatisch durch die Bindung an die DataTable.
Kann ich die Spalten im DGV vorher erstellen obwohl ich an ein DataTable binde?
Natürlich, einfach AutoGenerateColumns auf false und los
Der Tipp ist gut.
Wusste ich noch nicht.
Ich habe die Spalten jetzt vorher angelegt:
dataGridViewServerData.Columns.Clear();
dataGridViewServerData.AutoGenerateColumns = false;
DataGridViewColumn dgvc_source = new DataGridViewColumn();
dgvc_source.HeaderText = "Quelle";
dataGridViewServerData.Columns.Add(dgvc_source);
DataGridViewComboBoxColumn dgvc_invalid = CreateComboBoxColumn("Invalid");
dgvc_invalid.Items.AddRange("Keine", "Sig_1", "Sig_2", "Sig_3", "Sig_4", "Sig_5", "Sig_6");
dgvc_invalid.HeaderText = "Invalid";
dataGridViewServerData.Columns.Add(dgvc_invalid);
DataGridViewCheckBoxColumn dgvc_inv2 = new DataGridViewCheckBoxColumn();
dgvc_inv2.HeaderText = "Inverter";
dataGridViewServerData.Columns.Add(dgvc_inv2);
DataGridViewColumn dgvc_drain = new DataGridViewColumn();
dgvc_drain.HeaderText = "Senke";
dataGridViewServerData.Columns.Add(dgvc_drain);
Die Tablelle ist wie bisher nur ohne Spaltenbezeichner
m_ServerDataTable = new DataTable();
m_ServerDataTable.Columns.Add("");
m_ServerDataTable.Columns.Add("");
m_ServerDataTable.Columns.Add("");
m_ServerDataTable.Columns.Add("");
m_ServerDataTable.Rows.Add(new object[] { "xyz", "Keine", true, "abc" });
m_ServerDataTable.Rows.Add(new object[] { "123", "Keine", true, "456" });
Bei der Bindung des DGV an die Tabelle
dataGridViewServerData.DataSource = m_ServerDataTable;
erhalte ich eine Exception > Fehlermeldung:
System.InvalidOperationException: "Mindestens eine Spalte des DataGridView-Steuerelements hat keine Zellenvorlage."
Muss ich hier eventuell das DGV selber füllen und nicht den Weg über die DataTable nehmen?
Klappt.
Für die Textfelder
DataGridViewTextBoxColumn dgvc_source = new DataGridViewTextBoxColumn();
dgvc_source.HeaderText = "Quelle";
dgvc_source.ValueType = typeof(string);
dataGridViewServerData.Columns.Add(dgvc_source);
Für die Auswahlen
DataGridViewComboBoxColumn dgvc_invalid = CreateComboBoxColumn("Invalid");
dgvc_invalid.Items.AddRange(MSP_MF.Keine, MSP_MF.Sig_1, MSP_MF.Sig_2, MSP_MF.Sig_3, MSP_MF.Sig_4, MSP_MF.Sig_5, MSP_MF.Sig_6);
dgvc_invalid.HeaderText = "Invalid";
dgvc_invalid.ValueType = typeof(MSP_MF);
dataGridViewServerData.Columns.Add(dgvc_invalid);
Die Daten kommen ohne Tabelle direkt
object[] row0 = { "xyz", MSP_MF.Keine, true, "abc" };
dataGridViewServerData.Rows.Add(row0);
Vielen Dank für die Tipps.
👍
Bitte nicht so machen.
Die Daten gehören nicht in das DGV sondern in eine Liste/DataTable.
Damit die jeweilige Column auch weis welche Spalte der DataTable gemeint ist, musst du nur MappingName setzen und dafür muss die Spalte natürlich auch einen namen haben
Die Datenhaltung per DataTable ist mir auch viel lieber.
Ich halte eh begleitend eine DataTable und synchronisiere die Daten über "CellValueChanged".
Ich habe die Styles angelegt.
Zwar kann ich keine "DataGrid<COMBOBOX>Column" auswählen, aber ich habe mal ersatzweise Text zugewiesen.
DataGridTableStyle myGridStyle = new DataGridTableStyle();
myGridStyle.MappingName = "Data";
DataGridColumnStyle gsd_source = new DataGridTextBoxColumn();
gsd_source.HeaderText = "Quelle";
myGridStyle.GridColumnStyles.Add(gsd_source);
DataGridColumnStyle gsd_invalid = new DataGridTextBoxColumn();
gsd_invalid.MappingName = "Invalid";
myGridStyle.GridColumnStyles.Add(gsd_invalid);
DataGridColumnStyle gsd_inv2 = new DataGridBoolColumn();
gsd_inv2.MappingName = "Inverter";
myGridStyle.GridColumnStyles.Add(gsd_inv2);
DataGridColumnStyle gsd_drain = new DataGridTextBoxColumn();
gsd_drain.MappingName = "Senke";
myGridStyle.GridColumnStyles.Add(gsd_drain);
Meine Tabelle hat wieder Spaltenbezeichner
m_ServerDataTable.Columns.Add("Quelle");
m_ServerDataTable.Columns.Add("Invalid");
m_ServerDataTable.Columns.Add("Invert");
m_ServerDataTable.Columns.Add("Senke");
Aber die Bindung an das DGV will nicht gelingen. Das Property "TableStyles" bleibt leider rot unterstrichen.
dataGridViewServerData.TableStyles.Add(myGridStyle);
DataGridColumnStyle
gehört zum (veralteten) DataGrid, nicht zur DataGridView
.
Du mußt nur für jede Spalte die Eigenschaft DataPropertyName auf die zugehörige DataTable-Spalte mappen.
Schau dir mal das Code-Beispiel der Antwort in Create DataGridView column that maps value from datasource (SetGridColumns
) an.
Klappt. -> Klasse.
Mit dem Mapping auf die Tabellenspalten klappt es hervoragend und ich muss keine Datan im DGV halten
DataGridViewTextBoxColumn dgvc_source = new DataGridViewTextBoxColumn();
dgvc_source.HeaderText = "Signalquelle";
dgvc_source.DataPropertyName = "Quelle";
dgvc_source.ValueType = typeof(string);
dataGridViewServerData.Columns.Add(dgvc_source);
Danke für die Hilfe.