Autor Beitrag
bamba
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Di 25.03.14 21:27 
Hallo zusammen :)

ich versuche von meinem Datagridview die Eigenschaft "IsCurrentRowDirty" auf false zu setzen.
Soweit ich das verstehe, ist es true, solange der Stift im RowHeader bei diese Zeile navigiert ist.

Ich habe es schon versucht mit
ausblenden C#-Quelltext
1:
dgv.CancelEdit();					

oder
ausblenden C#-Quelltext
1:
dgv.EndEdit();					


Hintergrund:

1. Ich schreibe was in eine Zelle rein
Dann nach bestimmten Eingaben:
2. Ich möchte meinen vorhandenen Grid löschen und neu erstellen:

ausblenden C#-Quelltext
1:
this.gp.Controls.RemoveAt(0); //Hier wirft er mir die Exception:					

Zitat:
InvalidOperationException
{"Der Vorgang kann in diesem Ereignishandler nicht durchgeführt werden."}


Weiss jemand einen Rat???
Danke

Moderiert von user profile iconTh69: C#-Tags hinzugefügt
Moderiert von user profile iconTh69: B- durch C#-Tags ersetzt
Moderiert von user profile iconTh69: U- durch Quote-Tags ersetzt
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Di 25.03.14 23:43 
Zitat:
ich versuche von meinem Datagridview die Eigenschaft "IsCurrentRowDirty" auf false zu setzen.


Das ist eine reine Leseproperty die du von außen nicht ändern kannst. Warum würde man das auch tun wollen?

Zitat:
Soweit ich das verstehe, ist es true, solange der Stift im RowHeader bei diese Zeile navigiert ist.


Klingt grauenhaft. Du solltest lieber die englisch Hilfe lesen und nicht die maschinell ins deutsche übersetzte ;)

Zitat:
this.gp.Controls.RemoveAt(0); //Hier wirft er mir die Exception:
InvalidOperationException


Von wo rufst du den Code auf? Aus einem Event des Grids? Das ist ist vermutlich keine Gute Idee und erinnert mich an die Münchhausen Geschichte vom am eigene Schopf aus dem Sumpf ziehen.
Prinzipiell ist das löschen und neuerstellen von Controls kritisch und sollte man nicht ohne wirklich guten Grund machen. Was wäre dein Grund?
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Mi 02.04.14 00:06 
Ralf Jansen hat folgendes geschrieben:
Von wo rufst du den Code auf? Aus einem Event des Grids? Das ist ist vermutlich keine Gute Idee und erinnert mich an die Münchhausen Geschichte vom am eigene Schopf aus dem Sumpf ziehen.

Also der Aufrufstack ist:

3. PrivateMethode
wo der Fehler passiert
2.weitere PrivateMethode
1.RowLeave-Ereignis vom Grid

Wenn ich in der 3 sage, lösche mir das vorhandene Grid von der Oberfläche und generiere das neu, weil sich die Daten zwischenzeitlich geändert haben:
ausblenden C#-Quelltext
1:
this.gpContentLicence.Controls.RemoveAt(0);					


dann geht er anschließend wieder ins RowLeave und sieht, dass "IsCurrentRowDirty" true ist und ruft wieder die 3 auf^^ also eine undliche Schleife....
Deswegen meine ich....ich muss IsCurrentRowDirty irgendwie auf "false" bekommen....

oder welche Ansätze gibts da noch???

Vielen Dank.

Moderiert von user profile iconTh69: Quote-Tag hinzugefügt.
Moderiert von user profile iconTh69: C#-Tags hinzugefügt
Th69
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Moderator
Beiträge: 4798
Erhaltene Danke: 1059

Win10
C#, C++ (VS 2017/19/22)
BeitragVerfasst: Mi 02.04.14 09:50 
Hallo bamba,

du solltest nicht das Grid neu erstellen, sondern nur die Daten aktualisieren (d.h. am besten gleich per DataBinding).
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Mi 02.04.14 10:11 
Ich mache Databinding über nen DataTable, ist das ok??
Soll ich dann einfach dem vorhandenen Grid neue Datensource zuweisen?
Th69
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Moderator
Beiträge: 4798
Erhaltene Danke: 1059

Win10
C#, C++ (VS 2017/19/22)
BeitragVerfasst: Mi 02.04.14 10:28 
Hallo,

bei DataBinding braucht man eigentlich gar nichts mehr selber tun, da die Controls sich dann automatisch selber aktualisieren, sobald sich die DataSource (in deinem Fall DataTable) ändert.
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Mi 02.04.14 10:32 
Ja. Das ist definitiv besser.

Klingt aber immer nochmerkwürdig aus einem Grid Event insbesondere sowas wie RowLeave gleich die Datenmenge auszutauschen und ich würde immer noch mit Problemen rechnen.
Datenmenge austauschen ist ein eventauslösendes Ereignis und du bist gerade in einem Event. Nebenbei änderst du die Grundlage die dieses Ereignis ausgelöst hat. Nach dem RowLeave will das Grid selbst möglicherweise noch irgendwas an der Row oder der vor dem Event ermittelten neuen ZielRow anstellen die existieren aber nicht mehr.

Wenn du uns erklärst was du tatsächlich erreichen willst fällt uns vermutlich was geeigneteres ein.
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Mo 07.04.14 09:51 
Danke schön :)

Das konkrete Problem ist:
1. Ich klicke in die Zelle
2. Ändere was
3. Programm sagt mir, dass die Daten inkonsistent sind.
4. Ich will dann mir die aktuellsten Daten holen.

Die Speicherroutine wird von dem RowLeave-Ereignis aufgerufen, weil ich jeweils speichere, wenn ich in einer andere Zeile gehe.
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Mo 07.04.14 10:00 
Hole dir die eventuell geänderten Daten in eine weiter DataTable und merge die in die gebundene DataTable.
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Mi 16.04.14 00:24 
also beim Erstellen des Grids benutze ich globales DataTable, welches ich zuerst befülle und dann das dem Grid zuweise.
Nun führe ich einfach die Abfrage erneut aus und speichere es in dem globalen DataTable, in diesem Moment hab ich erwartet, dass
das Grid das sofort mitbekommt, sobald ich das Ergebnis dem DataTable zuweise...leider ändern sich die Daten nicht an der Oberfläche....
muss ich da erneut das geupdatete DataTable dem der Grid.DataSource zuweisen?

Moderiert von user profile iconTh69: Beiträge zusammengefasst

weil das Grid wird temporär erzeugt und ich kann nicht so einfach auf die "DataSource" zugreifen:

ausblenden C#-Quelltext
1:
grupBox1.Controls[0].DataBindings[0].DataSource = updatedTable;					

geht nicht, denn die Eigenschaft "DataSource" ist aufeinmal schreibgeschützt....was muss man da machen??
Danke für jeden Tipp.

Moderiert von user profile iconTh69: Quote- durch C#-Tags ersetzt
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Mi 16.04.14 09:31 
Wenn du dem DataTable etwas hinzufügst bekommt das Grid das sofort mit. Eigentlich muß man da also nix extra machen.

Zitat:
Nun führe ich einfach die Abfrage erneut aus und speichere es in dem globalen DataTable,


Zeig uns das doch mal den speichern in globale DataTable Teil. So wie du das wiedergibst wäre eine Vermutung das du die DataTable nicht weiterverwendest sondern durch eine neue ersetzt und somit das Grid weiterhin auf die vorhergehende schaut.
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Mi 16.04.14 15:15 
klar kann ich machen :)

also das ist die Oberflächenklasse:
ausblenden volle Höhe C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
34:
35:
36:
37:
38:
39:
40:
41:
namespace meinProgramm
{
    public partial class frmForm: Form
    {
         private DataTable meinDataTable;
         
          public DataGridView createGrid(string GridName)
          {

                meinGrid= new System.Windows.Forms.DataGridView();
                
                meinDataTable= controller.retrieve(seriennr);
                meinGrid.DataSource = tableSourceForLicencemenu;
                return meinGrid;
                      
          }

           private void grid_KeyDown(object sender, KeyEventArgs e)
          {

                updateDataTable() //wenn man ne Taste drückt, updated er die globale DataTable und somit mein Gridview
          }

          private void grid_CellClick(object sender, DataGridViewCellEventArgs e)
          {
                 
               meinGroupBox.Controls.Add(createGrid("test")); //rufe obige Funktion auf, hole daten und speichere sie ins   
                                                              //globale Datatable, gib nen Grid zurück und füge es Groupbox  
                                                              //zu.        



          }

          

          updateDataTable(){
             
              meinDataTable= controller.retrieve(seriennr);
          }
    }


Ist das so korrekt??? also mit der Absicht, dass auf eine Benutzeriteration das Grid sich selbst aktualisiert.
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Mi 16.04.14 16:15 
updateDataTable ändert die Variable meinDataTable mit einer neuen DataTable die er von deiner Controller Klasse geholt hat.
Wenn du zu einem früheren Zeitpunkt dem Grid eine andere DataTable über diese Variable zugeordnet hast zeigt ab dann die Variable und das Grid auf die selbe DataTable.
Wenn du nun denn Verweis der Variablen änderst wieso sollte sich das Grid mit ändern? Grid.DataSource weiß nichts davon das es mal über diese Variable an die DataTable Instanz gebunden wurde und wird weiter auf die DataTable schauen die du im mal früher zugewiesen hast.

Oder in Code vielleicht einfacher zu verstehen. Wenn dt2 ein neue DataTable zugewiesen bekommt bekommt das dt1 natürlich nicht mit. Sie wird weiter auf die auf sie einmal zugewiesene DataTable schauen.
ausblenden C#-Quelltext
1:
2:
3:
DataTable dt2 = new DataTable();
DataTable dt1 = dt2;
DataTable dt2 = new DataTable();



Wenn du eine neue Instanz hast mußt du die auch neu ans Grid binden.
Und wenn du nicht gerade beliebig viele Grids auf deiner Form stapeln willst dann erzeuge nicht das Grid neu!
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Fr 18.04.14 12:00 
Danke für die Antwort.

ich hoffe, ich habe dich verstanden....
Also ich hab mir einfach gedacht, dass ich ein globales DataTable habe.
Und aus verschiedenen Methoden aktuallisiere ich ihn, in dem ich was von der ControllerKlasse hole...

Zitat:
Wenn du eine neue Instanz hast mußt du die auch neu ans Grid binden.


Ja...und das habe ich versucht zu tun:
ausblenden C#-Quelltext
1:
GroupBox.Controls[0].DataBindings[0].DataSource = meinDataTable					


Aber die "DataSource" ist nun aufeinmal schreibgeschützt..... :(


ausblenden C#-Quelltext
1:
2:
3:
4:
 private void updateDataTable(){
             
              meinDataTable= controller.retrieve(seriennr);
          }


die "meinDataTable" ist ja eine globale Variable...
Am Anfang setze ich sie in der Methode A.
Dann später möchte ich sie aus der Methode B eben erneuern, und das Grid sollte das ja eigentlich sofort mitbekommen.
Oder verstehe ich da was falsch.....
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Fr 18.04.14 14:52 
Zitat:
die "meinDataTable" ist ja eine globale Variable...


Es ist eine private Klassenvariable. Der Begriff global macht in einem objektorientierten System wenig Sinn.

Zitat:
GroupBox.Controls[0].DataBindings[0].DataSource = meinDataTable


Du willst scheinbar das Binding ändern und die DataSource eines Binding war und ist immer einer reine Leseproperty. Binding ändern hieße üblicherweise ein neues Binding erzeugen.
Aber das macht man eigentlich nicht. Genauso wenig wie Controls neu erzeugen.

Zitat:
Dann später möchte ich sie aus der Methode B eben erneuern, und das Grid sollte das ja eigentlich sofort mitbekommen.


Mitbekommen kann das Grid nur Dinge die an dem Object passieren auf das Grid.DataSource schaut. Wenn zu irgendeinem Zeitpunkt meinDataTable und Grid.DataSource auf die gleich DataTable schauen kannst du den Inhalt der DataTable über meinDataTable ändern und das Grid wird diese Änderungen anzeigen. Das hier

ausblenden C#-Quelltext
1:
meinDataTable= controller.retrieve(seriennr);					


ändert aber nicht den Inhalt des Objects das an meinDataTable hängt sondern läßt meinDataTable auf eine andere DataTable schauen. Wenn du jetzt was an der DataTable in meinDataTable änderst wird das keine Auswirkungen auf das Grid haben denn das Grid arbeitet ja mit einer anderen DataTable eben das von dem du zu einen früherem Zeitpunkt gesagt hast "Bitte liebes Grid arbeite mit dieser DataTable".
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Fr 18.04.14 16:32 
Zitat:

Das hier

ausblenden C#-Quelltext
1:
meinDataTable= controller.retrieve(seriennr);					


ändert aber nicht den Inhalt des Objects das an meinDataTable hängt sondern läßt meinDataTable auf eine andere DataTable schauen. Wenn du jetzt was an der DataTable in meinDataTable änderst wird das keine Auswirkungen auf das Grid haben denn das Grid arbeitet ja mit einer anderen DataTable eben das von dem du zu einen früherem Zeitpunkt gesagt hast "Bitte liebes Grid arbeite mit dieser DataTable".


Und das ist eben das Problem, dass ich einfach ein anderes DataTable erzeuge mit der obigen Zeile code und überschreibe somit nicht das ursprüngliche DataTable.
Aber wie kann ich den das ursprüngliche DataTable mit dem neuen Inhalt aus der Datenbank überschreiben bzw. füllen bzw. aktuallisieren?
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Fr 18.04.14 17:45 
user profile iconRalf Jansen hat folgendes geschrieben Zum zitierten Posting springen:
Hole dir die eventuell geänderten Daten in eine weiter DataTable und merge die in die gebundene DataTable.


Folge dem Link. Ich sehe aber auch kein Problem darin wenn du eine neue DataTable holst die neu ans Grid zu binden. Warum willst du das nicht?
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: Fr 18.04.14 17:58 
Zitat:
Ich sehe aber auch kein Problem darin wenn du eine neue DataTable holst die neu ans Grid zu binden. Warum willst du das nicht?


hehe^^

Das Grid ich ja nicht hin....
ich habe ein anonymes DataGridview, welches ich am Anfang beim Laden auf ein Groupbox binde.....
Nun versuche ich über die Index von "Controls" der Groupbox das angefügte Grid irgendwie anzusprechen:

ausblenden C#-Quelltext
1:
2:
meinDataTable = controller.retrive(seriennr); //neue Daten holen, neues DataTable erzeugen
GroupBox.Controls[0].DataBindings[0].DataSource = meinDataTable; //neues DataTable an das vorhandene Grid anfügen, bzw. das alte DataTable somit ersetzen.


und das geht eben nicht, weil "DataSource" schreibgeschützt ist.
Wie kann ich das sonst machen??
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Fr 18.04.14 18:10 
Gib dem Grid einen Namen(jedes Control hat eine Name Property) und suche dann das Grid über den Namen.

ausblenden C#-Quelltext
1:
2:
3:
var controls = GroupBox.Controls.Find(meinLieberGridName, true);
if ((controls.count > 0) && (controls[0is DataGridview))
  (controls[0as DataGridview).DataSource = meinDataTable;


Aber da sind wir dann am nächsten Punkt wovon wir hier die ganze Zeit abraten. Erstell das Grid nicht neu bzw. dynamisch. Wirf es im Designer einfach auf die Form. Dann hast du etwas das du passend einstellen kannst und eine Variable für das Grid über das du einfach die DataSource zuweisen kannst.
bamba Threadstarter
Hält's aus hier
Beiträge: 13



BeitragVerfasst: So 20.04.14 18:30 
heey, vielen Dank.

Ich hab das implementiert und es auch an anderen Stellen verwendet, was super funtioniert, wofür ich mich herzlich bedanken möchte, nur an dieser Stelle funktioniert es nicht.

Und zwar tritt ein RowLeave-Event auf, worin ich die Speichermethode aufrufe, die mir dann später nen Fehler verursacht.
Diese Speichermethode rufe ich nur auf wenn die Eigenschaft grid.IsCurrentRowDirty mir true zurück gibt.
Ich möchte sie aber vor dem "RowLeave" auf false setzen.
Dafür hab ich schon "CancelEdit" ausprobiert usw....das bringt alles nichts.
Irgendwie muss der "Stift" auf der linken Seite des Grids verschwinden, sodass diese Zeile nicht im Editiermodus ist...
Wie kriege ich es hin diese Eigenschaft dgvCurrentDongel.IsCurrentRowDirty wieder auf false zu setzen`????
Danke

Moderiert von user profile iconTh69: C#-Tags hinzugefügt