Dateipfad im FormDrag Event auslesen

  • VB.NET
  • .NET (FX) 3.0–3.5

Es gibt 38 Antworten in diesem Thema. Der letzte Beitrag () ist von ErfinderDesRades.

    Ich würde Dir dazu raten, anstatt Me.Close() aufzurufen, mit DialogResult zu arbeiten. So kannst Du unterscheiden, ob überhaupt ein Button gedrückt wurde oder die Form einfach so geschlossen wurde...

    VB.NET-Quellcode

    1. Private Sub ButtonClick(sender As Object, e As EventArgs)
    2. Select Case True
    3. Case sender Is BtnRechnung
    4. Me.DocumentType = DocumentTypes.Rechnung
    5. Case sender Is BtnBestellung
    6. Me.DocumentType = DocumentTypes.Bestellung
    7. Case sender Is BtnPreisliste
    8. Me.DocumentType = DocumentTypes.Preisliste
    9. End Select
    10. Me.DialogResult = DialogResult.OK
    11. End Sub


    Das setzten der Property DialogResult schliesst die Form. Der Aufruf dann in Etwa so....

    VB.NET-Quellcode

    1. Protected Overrides Sub OnDragDrop(drgevent As DragEventArgs)
    2. Dim file = DirectCast(drgevent.Data.GetData(DataFormats.FileDrop), String())(0)
    3. Using f2 As New Form2
    4. If f2.ShowDialog = DialogResult.OK Then
    5. Me.Text = $"{New FileInfo(file).Name} is {f2.DocumentType}"
    6. End If
    7. End Using
    8. MyBase.OnDragDrop(drgevent)
    9. End Sub


    Ein einfaches schliessen der Form über das X gibt als DialogResult Cancel zurück. Die Betätigung eines Buttons jedoch OK.....
    Die Unendlichkeit ist weit. Vor allem gegen Ende. ?(
    Manche Menschen sind gar nicht dumm. Sie haben nur Pech beim Denken. 8o

    SpaceyX schrieb:

    Die Betätigung eines Buttons jedoch OK.....
    wenn das so implementiert ist:
    Dialoge: Instanziierung von Forms und Aufruf von Dialogen
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Alles klar Spacey, werde ich mir anschauen. Ohne Dialog Result, wäre ja mein FileType im Falle eines schließens der Form übers "x" immer der erste des ENums. Was ja doof ist.

    Aber noch eine Frage.
    Nach dem Drop einer Datei, kommt eine Auswahlform um welche Firma es sich handelt. Hierzu habe ich eine bereits existierende "SupplierSelect" Form verwendet.
    Diese ändert den SupplierBindingsource.current und castet dann auf die entsprechende Row.
    Auf die gleiche Art und Weise wollte ich nun eine Rechnung auswählen. Jedoch werden mir in meiner erstellten Form alle Rechnungen (und nicht nur wie erwartet, die Rechnungen der ausgewählten Firma) angezeigt.
    Auf meine neu erstellte Form habe ich nur aus den Datenquellen das in Supplier eingeschachtelte OrderDGV gezogen und einen Dialog.OK Button erzeugt.
    Deswegen hätte ich erwartet, dass mir eben nur die Daten des ausgewählten "Supplier" angezeigt werden - aber warum seh ich alle?
    Die Auswahl der "OrderDaten" klappt, mir wird in der Messagebox die richtige Rechnungsnummer angezeigt.
    Hier der Code:

    VB.NET-Quellcode

    1. Private Sub frmMainForm_DragDrop(sender As System.Object, e As System.Windows.Forms.DragEventArgs) Handles Me.DragDrop
    2. 'auf die Form gedroppte Dateien in Array speichern
    3. Dim files() As String = CType(e.Data.GetData(DataFormats.FileDrop), String())
    4. 'Schleife durch jeden Arrayeintrag und Verarbeitung der Dateien
    5. For Each Filepath In files
    6. Dim FileInfo As FileInfo = New FileInfo(Filepath)
    7. 'Lieferantenauswahl
    8. Using SupplierSelect As New frmSupplierSelect()
    9. SupplierSelect.DtsSettings = Me.DtsSettings
    10. SupplierSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    11. SupplierSelect.ShowDialog(Me)
    12. If SupplierSelect.DialogResult = DialogResult.OK Then SupplierBindingSource.Position = SupplierSelect.SupplierBindingSource.Position
    13. End Using
    14. If SupplierBindingSource.Current Is Nothing Then Exit Sub
    15. Dim SelectedSupplier = DirectCast(DirectCast(SupplierBindingSource.Current, DataRowView).Row, DtsSettings.SupplierRow)
    16. 'Auswahl um welche Art Datei es sich handelt
    17. Using ChooseFileType As New frmChooseFileType
    18. ChooseFileType.LBLFilename.Text = FileInfo.Name
    19. ChooseFileType.ShowDialog(Me)
    20. If ChooseFileType._FileType = frmChooseFileType.FileType.Invoice Then InvoiceDropped(FileInfo, SelectedSupplier.Name)
    21. If ChooseFileType._FileType = frmChooseFileType.FileType.Order Then Orderdropped()
    22. End Using
    23. Next
    24. End Sub
    25. 'Sub zum verarbeiten einer gedroppten Rechnung
    26. Private Sub InvoiceDropped(Fileinfo As FileInfo, Supplier As String)
    27. Dim TargetPath = My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier & "\"
    28. 'Prüfen ob Ordner existieren
    29. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen")
    30. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier)
    31. 'Auswahl um welche Rechnung es sich handelt
    32. Using InvoiceSelect As New frmInvoiceSelect()
    33. InvoiceSelect.DtsSettings = Me.DtsSettings
    34. InvoiceSelect.OrderBindingSource.DataSource = Me.DtsSettings
    35. InvoiceSelect.ShowDialog(Me)
    36. If InvoiceSelect.DialogResult = DialogResult.OK Then OrderBindingSource.Position = InvoiceSelect.OrderBindingSource.Position
    37. End Using
    38. If OrderBindingSource.Current Is Nothing Then Exit Sub
    39. Dim SelectedOrder = DirectCast(DirectCast(OrderBindingSource.Current, DataRowView).Row, DtsSettings.OrderRow)
    40. MessageBox.Show(SelectedOrder.InvoiceNumber)
    41. Exit Sub
    42. 'Datei kopieren
    43. Fileinfo.CopyTo(TargetPath & Fileinfo.Name)
    44. End Sub


    Ein Bild des DateSets, sowie die Stelle in den Datenquellen aus denen ich das DGV auf die Form gezogen habe, habe ich angehängt.
    Bilder
    • DataSet.jpg

      401,13 kB, 1.920×1.080, 66 mal angesehen
    Naja. Aus programmatorischer (ich hoffe das heißt so) Sicht, wähle ich eine OrderRow aus.
    Diese beinhaltet aber Columns wie InvoiceDate und InvoiceNumber, welche ich dem User präsentiere, damit dieser letzlich eine Rechnung auswählt.

    Also nochmal (in korrekt)
    Da ich die in Supplier eingeschachtelte OrderTable als DGV auf meine Form gezogen habe (im Screenshot rot umkreist), gehe ich davon aus, dass mir nur die OrderRows für den entsprechenden (vorher ausgewählten) Supplier angezeigt werden. Ich sehe aber alle OrderRows. Warum?
    ich glaub, du hast nur die OrderTable aufs Form gezogen, und die SupplierTable nicht? Dann generiert das wohl keine untergeordnete BindingSource.
    Also die Untergeordnet-Funktionalität wird dadurch bewirkt, dass bei der OrderBindingSource als DataSource nicht das Dataset eingestellt ist, sondern eine SupplierBindingSource.
    Und DataMember der OrderBindingSource muss sein: "FK_Supplier_Order".
    Prüf das mal nach.

    Das "Ziehen der eingeschachtelten Tabelle" ist nur ein bequemer Weg, eine so konfigurierte BindingSource zu erhalten, wo ausserdem das DGV noch dran angebunden ist.
    Man kann diese Dinge aber auch selbst so einrichten, indem man bei einer BindingSource diese beiden Properties setzt: 1) DataSource=dasDataset, 2) DataMember=dieRelationZurUebergeordnetenTable
    Sind beides Auswahlfelder im Designer.
    Ahja. Gleich zwei Fehler habe ich gemacht.
    Ich hab glaube ich erst die eingeschachtelte OrderTable und dann die Supplier auf die Form gezogen. Dadurch war der DataMember in meiner Orderbindingsource falsch.
    Außerdem habe ich ja auch beim Aufruf der SubForm InvoiceSelect.OrderBindingSource.DataSource = Me.DtsSettings aufgerufen.
    Hier muss ich ja aber NUR die Supplierbindingsource bespeisen, nicht die OrderBindingSource.
    Nu klappts :o)

    Edit: @ErfinderDesRades
    Nein klappt doch nicht (immer). Mir werden die korrekten OrderRows angezeigt, aber folgende Zeile scheint Problem zu machen.
    If InvoiceSelect.DialogResult = DialogResult.OK Then OrderBindingSource.Position = InvoiceSelect.OrderBindingSource.Position
    Wenn ich nämlich über die in der Hauptform im entsprechenden OrderDatagridview (ebenfalls gebunden an die eingeschachtelte OrderTable in Suppler), die OrderBindingsource.Position ändere (also da was anklicke), wird mir immer diese Row ausgegeben, egal was ich in meiner Unterform ändere. Warum passiert das?
    Auch ändert sich in meiner Hauptform die ausgewählte OrderRow nicht. Hier müsste im DGV ja dann eigentlich die gleiche Row ausgewählt sein, wie in meiner Unterform. Da ändert sich aber nix.

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „DerSmurf“ ()

    DerSmurf schrieb:

    If InvoiceSelect.DialogResult = DialogResult.OK Then
    Mach das mal anders rum:

    VB.NET-Quellcode

    1. If InvoiceSelect.DialogResult <> DialogResult.OK Then
    2. Return
    3. End If
    falls nach Deiner Zeile noch Anweisungen vorkommen, die eigentlich ein OK voraussetzen.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!

    DerSmurf schrieb:

    VB.NET-Quellcode

    1. OrderBindingSource.Position = InvoiceSelect.OrderBindingSource.Position
    Dassis natürlich höchst anfällig.
    Wer sagt denn, dass die gemeinte OrderRow in deiner MainForm-BindingSource an genau derselben Position liegt, wie sie auf deim Subform inne BindingSource lag?
    Gib dir den Positions-Wert mal einfach aus, und guck im MainForm, ob an der Position da wirklich der von dir gemeinte Datensatz liegt.
    Ansonsten gib lieber den gemeinten Datensatz zurück, und suche den dann eigenständig im MainForm.

    Ich setze mal voraus, du arbeitest mit Formübergreifendem Databinding - sonst liegt noch viel mehr im Argen.

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „ErfinderDesRades“ ()

    @RodFromGermany Nein, das können wir ausschließen. Ich bin schrittweise durchgegangen, DialogResult ist immer OK und es kommt auch nur die eine gepostete Zeile, die "OK" erwartet.

    @ErfinderDesRades

    ErfinderDesRades schrieb:

    Ich setze mal voraus, du arbeitest mit Formübergreifendem Databinding - sonst liegt noch viel mehr im Argen.

    Ich glaube schon :o)

    Aber ich habe den Fehler gefunden. Glaube ich habe die Funktionsweise von .Position falsch verstanden.
    In meiner Mainform sind die Rows nach Bestelldatum aufsteigend, in der SubForm waren sie absteigend sortiert. Ich habe testweise zwei OrderRows erstellt.
    Hierdurch waren dann die Positionen eben anders und manchmal habe ich dann auf die falsche Row gecastet (weil Position einen anderen Wert als erwartet hatte).
    Aber eigentlich benötige ich nur die Rechnungsnummer (Order.Invoicenumber) und das Rechnungsdatum (Order.InvoiceDate).
    Da ist es ja wahrscheinlich sowieso eleganter in der SubForm diese Daten auszulesen und an die Aufrufsub zu übergeben, statt auf die BindingSource.Position zu ändern und dann in der Aufrufsub die Daten zu sammeln.

    Edit: also so in der SubForm: (Button1, wird natürlich noch umbenannt) - sonst gibts hier nur ein an die OrderTable gebundenes DGV.

    VB.NET-Quellcode

    1. Public Class frmInvoiceSelect
    2. Public Property _Invoicenumber As String
    3. Public Property _InvoiceDate As Date
    4. Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
    5. If OrderBindingSource.Current Is Nothing Then Exit Sub
    6. Dim SelectedOrder = DirectCast(DirectCast(OrderBindingSource.Current, DataRowView).Row, DtsSettings.OrderRow)
    7. _Invoicenumber = SelectedOrder.InvoiceNumber
    8. _InvoiceDate = SelectedOrder.InvoiceDate
    9. Me.DialogResult = DialogResult.OK
    10. End Sub
    11. End Class

    und die Mainform

    VB.NET-Quellcode

    1. Private Sub InvoiceDropped(Fileinfo As FileInfo, Supplier As String)
    2. Dim InvoiceNumber As String
    3. Dim InvoiceDate As Date
    4. Dim TargetPath = My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier & "\"
    5. 'Prüfen ob Ordner existieren
    6. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen") 'Funktion zum prüfen ob Ordner existiert. Wenn nicht, wird er erstellt.
    7. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier)
    8. 'Auswahl um welche Rechnung es sich handelt
    9. Using InvoiceSelect As New frmInvoiceSelect()
    10. InvoiceSelect.DtsSettings = Me.DtsSettings
    11. InvoiceSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    12. InvoiceSelect.ShowDialog(Me)
    13. If InvoiceSelect.DialogResult = DialogResult.OK Then
    14. InvoiceNumber = InvoiceSelect._Invoicenumber
    15. InvoiceDate = InvoiceSelect._InvoiceDate
    16. Fileinfo.CopyTo(TargetPath & InvoiceNumber & "_vom_" & InvoiceDate.ToShortDateString & Fileinfo.Extension, True)
    17. End If
    18. End Using
    19. End Sub


    Das müsste ja ohnehin besser sein, als die BindingSource.Position zu ändern.
    Aber ist das mit den Propertys so korrekt?
    also einfach nur:
    Public Property _Invoicenumber As String
    Public Property _InvoiceDate As Date
    Oder brauche ich hier dann lieber eine "Get Property" ? Wenn nicht, wann brauche ich die?

    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „DerSmurf“ ()

    Warum haben Deine Public Properties einen Unterstrich? Sowas wird eigentlich mit Private Members gemacht, die durch ne Property manipuliert werden:

    VB.NET-Quellcode

    1. Private _MyValue As Integer
    2. Public Property MyValue As Integer
    3. Get
    4. Return _MyValue
    5. End Get
    6. Set(NewValue As Integer)
    7. If _MyValue > 100 Then Return 'nur als Zusatz, damit der Volleinsatz der Property gerechtfertigt ist
    8. _MyValue = NewValue
    9. End Get
    10. End Property

    Was meinst Du mit "Get Property"? Ne ReadOnly Property?
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Wie gesagt: Gib die OrderRow zurück.
    Nicht iwelche Werte der OrderRow, sondern einfach die OrderRow selbst - da sind die Werte ja drinne.
    Oder hol sie dir aus dem SubForm. Beispiel HauptForm-Code:

    VB.NET-Quellcode

    1. Private Sub InvoiceDropped(Fileinfo As FileInfo, Supplier As String)
    2. Dim TargetPath = My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier & "\"
    3. 'Prüfen ob Ordner existieren
    4. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen") 'Funktion zum prüfen ob Ordner existiert. Wenn nicht, wird er erstellt.
    5. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier)
    6. 'Auswahl um welche Rechnung es sich handelt
    7. Using InvoiceSelect As New frmInvoiceSelect()
    8. InvoiceSelect.DtsSettings = Me.DtsSettings
    9. InvoiceSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    10. InvoiceSelect.ShowDialog(Me)
    11. If InvoiceSelect.DialogResult = DialogResult.OK Then
    12. Dim rwSelected = DirectCast(DirectCast(InvoiceSelect.OrderBindingSource.Current, DataRowView).Row, OrderRow)
    13. Fileinfo.CopyTo(TargetPath & rwSelected.InvoiceNumber & "_vom_" & rwSelected.InvoiceDate.ToShortDateString & Fileinfo.Extension, True)
    14. End If
    15. End Using
    16. End Sub
    Die generierten Datenklassen sind ziemlich gut designed - die kann man benutzen wie sie sind.
    So brauchst du keinerlei Extra-Brimborium im Subform zu implementieren.

    Zeile 15 wäre übrigens schöner mit String-Interpolation:

    VB.NET-Quellcode

    1. Fileinfo.CopyTo($"{TargetPath}{rwSelected.InvoiceNumber}_vom_{rwSelected.InvoiceDate.ToShortDateString}{Fileinfo.Extension}", True)


    Geht noch hübscher:

    VB.NET-Quellcode

    1. Private Sub InvoiceDropped(Fileinfo As FileInfo, Supplier As String)
    2. Dim TargetPath = My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier & "\"
    3. 'Prüfen ob Ordner existieren
    4. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen") 'Funktion zum prüfen ob Ordner existiert. Wenn nicht, wird er erstellt.
    5. CheckAndCreateFolders(My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier)
    6. 'Auswahl um welche Rechnung es sich handelt
    7. Using InvoiceSelect As New frmInvoiceSelect()
    8. InvoiceSelect.DtsSettings = Me.DtsSettings
    9. InvoiceSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    10. If InvoiceSelect.ShowDialog(Me).DialogResult <> DialogResult.OK Then Return
    11. Dim rwSelected = DirectCast(DirectCast(InvoiceSelect.OrderBindingSource, DataRowView).Row, OrderRow)
    12. Fileinfo.CopyTo($"{TargetPath}{rwSelected.InvoiceNumber}_vom_{rwSelected.InvoiceDate.ToShortDateString}{Fileinfo.Extension}", True)
    13. End Using
    14. End Sub


    Und noch ein klein:

    VB.NET-Quellcode

    1. Private Sub InvoiceDropped(Fileinfo As FileInfo, Supplier As String)
    2. Dim diTarget = New directoryInfo(My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier)
    3. If Not diTarget.exists Then diTarget.Create()
    4. 'Auswahl um welche Rechnung es sich handelt
    5. Using InvoiceSelect As New frmInvoiceSelect()
    6. InvoiceSelect.DtsSettings = Me.DtsSettings
    7. InvoiceSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    8. If InvoiceSelect.ShowDialog(Me).DialogResult <> DialogResult.OK Then Return
    9. Dim rwSelected = DirectCast(DirectCast(InvoiceSelect.OrderBindingSource, DataRowView).Row, OrderRow)
    10. Fileinfo.CopyTo($"{diTarget.Fullname}\{rwSelected.InvoiceNumber}_vom_{rwSelected.InvoiceDate.ToShortDateString}{Fileinfo.Extension}", True)
    11. End Using
    12. End Sub

    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „ErfinderDesRades“ ()

    ErfinderDesRades schrieb:

    Wie gesagt: Gib die OrderRow zurück.

    (und nicht die einzelnen Werte aus der OrderRow) - nach dem zweiten mal ists jetzt angekommen :o)
    Und auch vielen Dank für deine Codeoptimierungen!
    Strininterpolaritation, habe ich in meinem Leben noch nie gehört - hier muss ich erstmal suchen was das ist, und was man genau damit machen kann. Aber es sieht definitiv schöner aus, als mein String gebastel.
    Auch dein directoryInfo gefällt mir natürlich sehr viel besser als meine String basierte Lösung.
    Aber hier muss ich natürlich auch erstmal ein bisschen rumprobieren. Aber gerade bei weiter verzweigten Ordnerstrukturen /Hauptordner/Unterordner/Unterordner1/Unterordner2/Unterordner3 ... liegen die Vorteile ja auf der Hand.

    @VaporiZed
    Ja, wie du merkst, tue ich mich damit noch recht schwer...
    Also ich weiß, ich benötige Properties um Private Members formübergreifend zu lesen, bzw. zu schreiben.
    Dies erspart es mir dann diesen Private Member als Public zu deklarieren was (immer?) ein NoGo ist.
    Bei den Propertys gibt es dann ein Set (zum beschreiben) und ein Get (zum "auslesen")
    Um bei deinem Beispiel zu bleiben würde ich also NeueForm.MyValue = 123 verwenden um _MyValue mit 123 zu beschreiben.
    Get habe ich noch nie verwendet (außer in diesem Beispiel hier), aber da ist die funktion ja eben ähnlich.
    Wenn es nur get, oder nur set gibt, dann ist meine Property Read- oder Writeonly und auch entsprechend zu deklarieren.

    Hier hört jetzt aber mein Verständniss von Propertys auf.
    Mich verwirrt daher obiges Beispiel (mit dem Enum), wo ich nur

    VB.NET-Quellcode

    1. [spoiler]Public Class frmChooseFileType
    2. Enum FileType
    3. Delivery = 0
    4. Invoice = 1
    5. End Enum
    6. Public Property PropFileType() As FileType ' das allein genügt hier
    7. Private Sub btnInvoice_Click(sender As Object, e As EventArgs) Handles btnInvoice.Click
    8. FileType = FileType.Invoice
    9. End Sub
    10. End Class
    11. 'und zum Aufruf in der MainForm dann
    12. If ChooseFileType.PropFileType = frmChooseFileType.FileType.Invoice Then MessageBox.Show("Rechnung")
    13. [/spoiler]

    Public Property PropFileType() As FileType aufrufe.
    Warum muss hier kein Get hin?
    Weil das eine Kurzform von folgendem ist:

    VB.NET-Quellcode

    1. Private _PropFileType As FileType
    2. Public Property PropFileType As FileType
    3. Get
    4. Return _PropFileType
    5. End Get
    6. Set(NewValue As FileType)
    7. _PropFileType = NewValue
    8. End Set
    9. End Property

    Schreibst Du das, wird beim Drüberfahren mit der Maus automatisch vorgeschlagen (weil nix Besonderes im Get- und SetBlock steht):

    Und wenn man den Vorschlag von IntelliSense umsetzen lässt, kommt das hier raus:

    VB.NET-Quellcode

    1. Public Property PropFileType As FileType

    Da geht's nur um Texteinsparung. Die volle Funktionalität steht immer noch dahinter. Deshalb hab ich in Post#31 Zeile#7 noch eingefügt, sonst hätte ich es auch zu nem Einzeiler machen können.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Danke!

    Edit: @ErfinderDesRades
    Sopp, ich habe deinen Code nun weitestgehend (bis auf String Interpolarisation) eingebaut.
    An einer Stelle habe ich jedoch eine Frage, bzw. vermute ich einen Fehler und zwar in deinem zuletzt geposteten Code in Zeile 10:

    VB.NET-Quellcode

    1. Dim rwSelected = DirectCast(DirectCast(InvoiceSelect.OrderBindingSource, DataRowView).Row, OrderRow)

    Muss es hier nicht ​= DirectCast(DirectCast(InvoiceSelect.OrderBindingSource.CURRENT, DataRowView).Row, OrderRow)
    heißen?

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „DerSmurf“ ()

    Hmm. Mir scheint die Auswahl meines Lieferanten macht ebenfalls Probleme.
    Wenn ich aber im Einzelschritt durchlaufe, sieht alles gut aus.
    Mir werden jedoch in der sich öffnenden Form Form frmInvoiceSelect immer die OrderRows der Firma mit Position = 0 angezeigt, egal was ich bei SupplierSelect auswähle.
    Sagen wir Testweise gibt es die Lieferanten LF0 und LF1:

    VB.NET-Quellcode

    1. Private Sub frmMainForm_DragDrop(sender As System.Object, e As System.Windows.Forms.DragEventArgs) Handles Me.DragDrop
    2. 'auf die Form gedroppte Dateien in Array speichern
    3. Dim files() As String = CType(e.Data.GetData(DataFormats.FileDrop), String())
    4. 'Schleife durch jeden Arrayeintrag und Verarbeitung der Dateien
    5. For Each Filepath In files
    6. Dim FileInfo As FileInfo = New FileInfo(Filepath)
    7. 'Lieferantenauswahl
    8. Using SupplierSelect As New frmSupplierSelect()
    9. SupplierSelect.DtsSettings = Me.DtsSettings
    10. SupplierSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    11. SupplierSelect.ShowDialog(Me) 'Form mit gebundenem DGV und Combobox und einem Button (DialogResult.OK) - hier wähle ich nun LF1 aus
    12. If SupplierSelect.DialogResult = DialogResult.OK Then SupplierBindingSource.Position = SupplierSelect.SupplierBindingSource.Position
    13. End Using
    14. If SupplierBindingSource.Current Is Nothing Then Exit Sub
    15. Dim SelectedSupplier = DirectCast(DirectCast(SupplierBindingSource.Current, DataRowView).Row, DtsSettings.SupplierRow) 'hier wird korrekt auf LF1 gecastet
    16. 'Auswahl um welche Art Datei es sich handelt
    17. Using ChooseFileType As New frmChooseFileType
    18. ChooseFileType.LBLFilename.Text = FileInfo.Name
    19. ChooseFileType.ShowDialog(Me)
    20. If ChooseFileType.DialogResult = DialogResult.Cancel Then Exit Sub
    21. If ChooseFileType._FileType = frmChooseFileType.FileType.Invoice Then InvoiceDropped(FileInfo, SelectedSupplier.Name) 'auch hier wird LF1 übergeben
    22. If ChooseFileType._FileType = frmChooseFileType.FileType.Order Then Orderdropped(FileInfo, SelectedSupplier.Name)
    23. End Using
    24. Next
    25. End Sub


    VB.NET-Quellcode

    1. Private Sub InvoiceDropped(Fileinfo As FileInfo, Supplier As String)
    2. 'Prüfen ob Ordner existieren
    3. Dim TargetPath = New DirectoryInfo(My.Application.Info.DirectoryPath & "\Daten\Rechnungen\" & Supplier)
    4. If Not TargetPath.Exists Then TargetPath.Create()
    5. 'Auswahl um welche Rechnung es sich handelt
    6. Using InvoiceSelect As New frmInvoiceSelect()
    7. InvoiceSelect.DtsSettings = Me.DtsSettings
    8. InvoiceSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    9. InvoiceSelect.ShowDialog(Me) 'Form mit einem gebundenen DGV an die in Supplier eingeschachtelten Orders - hier werden mir aber die OrderRows von LF0 angezeigt
    10. If InvoiceSelect.DialogResult <> DialogResult.OK Then Return
    11. Dim SelectedOrderRow = DirectCast(DirectCast(InvoiceSelect.OrderBindingSource.Current, DataRowView).Row, DtsSettings.OrderRow)
    12. 'Datei kopieren
    13. Fileinfo.CopyTo(TargetPath.FullName & "\" & SelectedOrderRow.InvoiceNumber & "_vom_" & SelectedOrderRow.InvoiceDate.ToShortDateString & Fileinfo.Extension, True)
    14. End Using
    15. End Sub


    "Fehler" siehe Kommentare im Code. Mir fällt kein Grund für das Verhalten meines Programmes ein.
    Durch Setzen der BS-DataSource (Post#36, Codeblock#2, Zeile#9) wird deren Position wieder auf 0 gesetzt. Da müsstest Du schon entweder die aktuelle Position übergeben oder besser das Current selbst.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Das beudetet, dass ich an folgender Stelle das Current übergeben muss.

    VB.NET-Quellcode

    1. Using InvoiceSelect As New frmInvoiceSelect()
    2. InvoiceSelect.DtsSettings = Me.DtsSettings
    3. InvoiceSelect.SupplierBindingSource.DataSource = Me.DtsSettings
    4. 'HIER
    5. [...]
    6. End Using

    Ich schaffe es jedoch nur, die Position zu übergeben.
    ​InvoiceSelect.SupplierBindingSource.Position = SupplierBindingSource.Position Das scheint zu funktionieren.
    Wie übergebe ich denn das Current zu übergeben?

    VaporiZed schrieb:

    oder besser das Current selbst.

    Current ist ja readonly?
    sowas ist möglich:

    VB.NET-Quellcode

    1. InvoiceSelect.SupplierBindingSource.DataSource = Me.SupplierBindingSource.Current
    Obs tut wasses soll bleibt auszuprobieren.
    Position setzen ist anfällig. Wenn eine der beiden BindingSources eine andere Sortierung hat, oder einen Filter, entsprechen die Positionen einander nicht mehr.
    Da muss man eine kleine Suche schreiben, dass tatsächlich der gemeinte Datensatz aufgesucht wird.

    Kennst du eigentlich meine Helpers-Klassen?
    Da ist das Zeug alles fixnFertig abgehandelt.