ListView SortOrder

  • VB.NET

Es gibt 30 Antworten in diesem Thema. Der letzte Beitrag () ist von RodFromGermany.

    ListView SortOrder

    Hallo,

    folgendes Problem; ich lade mein ListView mittels:

    VB.NET-Quellcode

    1. Dim li As New ListViewItem
    2. Dim Filename As String
    3. Dim TFile As System.IO.StreamReader
    4. Dim sRGB As String()
    5. Dim S As String
    6. Dim X, Y As Integer
    7. Dim S1, S2, S3, S4, S5, S6, S7, S8, S9, S10 As String
    8. Try
    9. Filename = "F:\Mechaniker\MechanikerDB2017.lst"
    10. ListView1.Items.Clear()
    11. TFile = My.Computer.FileSystem.OpenTextFileReader(Filename)
    12. Do While (TFile.Peek() > -1)
    13. X = ListView1.Items.Count
    14. S = Trim(TFile.ReadLine)
    15. sRGB = S.Split(",")
    16. S1 = sRGB(0)
    17. S2 = sRGB(1)
    18. S3 = sRGB(2)
    19. S4 = sRGB(3)
    20. S5 = sRGB(4)
    21. S6 = sRGB(5)
    22. S7 = sRGB(6)
    23. S8 = sRGB(7)
    24. S9 = sRGB(8)
    25. S10 = sRGB(9)
    26. Dim item As ListViewItem = ListView1.Items.Add(S1)
    27. item.SubItems.Add(S2)
    28. item.SubItems.Add(S3)
    29. item.SubItems.Add(S4)
    30. item.SubItems.Add(S5)
    31. item.SubItems.Add(S6)
    32. item.SubItems.Add(S7)
    33. item.SubItems.Add(S8)
    34. item.SubItems.Add(S9)
    35. item.SubItems.Add(S10)
    36. item.ImageIndex = 1
    37. Loop
    38. Catch ex As Exception
    39. End Try
    40. li.Checked = True
    41. ToolStripStatusLabel2.Text = "Aufträge: " & ListView1.Items.Count.ToString
    42. TFile.Close()
    43. ListView1.Sort()


    VB.NET-Quellcode

    1. [b][/b]ListView1.Sort()[b][/b]
    verwende ich damit die Items in Colum 4 Absteigend Sortiert werden.

    Meine Klasse zum Sortieren;

    VB.NET-Quellcode

    1. Public Class ListViewComparer
    2. Implements IComparer
    3. Private intColumn As Integer
    4. Private soSortOrder As SortOrder
    5. Private cicComparer As CaseInsensitiveComparer
    6. Public Sub New(ByVal ParentListView As ListView)
    7. intColumn = 4
    8. soSortOrder = SortOrder.Descending
    9. cicComparer = New CaseInsensitiveComparer()
    10. ParentListView.ListViewItemSorter = Me
    11. End Sub
    12. Public Property SortOrder() As SortOrder
    13. Get
    14. Return soSortOrder
    15. End Get
    16. Set(ByVal value As SortOrder)
    17. soSortOrder = value
    18. End Set
    19. End Property
    20. Public Property SortColumn() As Integer
    21. Get
    22. Return intColumn
    23. End Get
    24. Set(ByVal value As Integer)
    25. intColumn = value
    26. End Set
    27. End Property
    28. Public Function Compare(ByVal x As Object, ByVal y As Object) As Integer Implements IComparer.Compare
    29. Dim compareResult As Integer
    30. Dim listviewX As ListViewItem, listviewY As ListViewItem
    31. listviewX = CType(x, ListViewItem)
    32. listviewY = CType(y, ListViewItem)
    33. compareResult = cicComparer.Compare(listviewX.SubItems(intColumn).Text, listviewY.SubItems(intColumn).Text)
    34. If soSortOrder = SortOrder.Ascending Then
    35. Return compareResult
    36. ElseIf soSortOrder = SortOrder.Descending Then
    37. Return compareResult * -1
    38. Else
    39. Return 0
    40. End If
    41. End Function
    42. End Class


    Aber beim Starten kommt immer der Fehler: InvalidArgument=Value mit dem Wert 4 ist für index ungültig. Parametername: index

    Ich hab keine Ahnung woran das liegt :(
    @VB1963 bei

    VB.NET-Quellcode

    1. compareResult = cicComparer.Compare(listviewX.SubItems(intColumn).Text, listviewY.SubItems(intColumn).Text)


    Hab das hier gefunden, aber wie wende ich das bei mir an? :/

    Fehler beim sortieren von listview

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

    @Pixxxas Setz in die Funktion Function Compare() einen Haltepunkt rein und kläre auf, was da mit den Parametern x und y ühaupt reinkommt.
    Und:

    Pixxxas schrieb:

    VB.NET-Quellcode

    1. Return compareResult * -1
    machst Du

    VB.NET-Quellcode

    1. Return -compareResult
    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!
    @RodFromGermany
    @VB1963

    So beim laden scheint alles zu klappen, aber wenn ich mit einem Button die Liste neu laden möchte (anderer User hat ein neues Item Hinzugefügt) kommt der selbe Fehler.
    Müssen irgendwelche Einstellungen zurück gesetzt werden?
    So sieht jetzt mein Load Event aus und das habe ich im Button so ein zu ein übernommen.

    VB.NET-Quellcode

    1. 'ListView1.OwnerDraw = True
    2. ProgressBar1.Maximum = 1000
    3. 'Me.Show()
    4. 'Control.CheckForIllegalCrossThreadCalls = False
    5. 'Me.ListView1.ListViewItemSorter = lvwColumnSorter
    6. Dim li As New ListViewItem
    7. Dim Filename As String
    8. Dim TFile As System.IO.StreamReader
    9. Dim sRGB As String()
    10. Dim S As String
    11. Dim X, Y As Integer
    12. Dim S1, S2, S3, S4, S5, S6, S7, S8, S9, S10 As String
    13. 'Filename = "F:\Mechaniker\MechanikerDB2017.lst"
    14. Filename = "\\internal.novero.com\dab\Data\PostkastenNOVERO\Sarra\Mechaniker\MechanikerDB2017.lst"
    15. ListView1.Items.Clear()
    16. TFile = My.Computer.FileSystem.OpenTextFileReader(Filename)
    17. Do While (TFile.Peek() > -1)
    18. X = ListView1.Items.Count
    19. S = Trim(TFile.ReadLine)
    20. sRGB = S.Split(",")
    21. S1 = sRGB(0)
    22. S2 = sRGB(1)
    23. S3 = sRGB(2)
    24. S4 = sRGB(3)
    25. S5 = sRGB(4)
    26. S6 = sRGB(5)
    27. S7 = sRGB(6)
    28. S8 = sRGB(7)
    29. S9 = sRGB(8)
    30. S10 = sRGB(9)
    31. Dim item As ListViewItem = ListView1.Items.Add(S1)
    32. item.SubItems.Add(S2)
    33. item.SubItems.Add(S3)
    34. item.SubItems.Add(S4)
    35. item.SubItems.Add(S5)
    36. item.SubItems.Add(S6)
    37. item.SubItems.Add(S7)
    38. item.SubItems.Add(S8)
    39. item.SubItems.Add(S9)
    40. item.SubItems.Add(S10)
    41. item.ImageIndex = 1
    42. Loop
    43. li.Checked = True
    44. ToolStripStatusLabel2.Text = "Aufträge: " & ListView1.Items.Count.ToString
    45. TFile.Close()
    46. 'lvwColumnSorter.SortColumn = 4
    47. 'lvwColumnSorter.Order = SortOrder.Descending
    48. 'Me.ListView1.Sort()
    49. 'ListView1.Sort()
    50. cmpFileListViewComparer.SortOrder = SortOrder.Descending
    51. cmpFileListViewComparer.SortColumn = 4
    52. ListView1.Sort()



    Du hast recht, die Liste muss erst Fertig geladen werden.
    Wenn ich die Liste fertig laden lasse und dann per Button, die liste Sortieren lasse, klappt alles.

    VB.NET-Quellcode

    1. cmpFileListViewComparer.SortOrder = SortOrder.Descending
    2. cmpFileListViewComparer.SortColumn = 4
    3. ListView1.Sort()



    Dieser Beitrag wurde bereits 3 mal editiert, zuletzt von „Pixxxas“ ()

    @Pixxxas Poste mal ein Testprojekt als ZIP (vorher ausprobieren und bereinigen), das den Effekt reproduziert.
    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!
    @Pixxxas Wenn Du Fehler beseitigen willst, musst Du zunächst das Try/Catch rausnehmen.
    Ich hab mal Deine Comparer-Klasse etwas gestylt:
    Spoiler anzeigen

    VB.NET-Quellcode

    1. Public Class ListViewComparer
    2. Implements IComparer
    3. Private cicComparer As CaseInsensitiveComparer
    4. Public Sub New(ByVal ParentListView As ListView)
    5. SortColumn = 0
    6. SortOrder = SortOrder.None
    7. cicComparer = New CaseInsensitiveComparer()
    8. ParentListView.ListViewItemSorter = Me
    9. End Sub
    10. Public Property SortOrder() As SortOrder
    11. Public Property SortColumn() As Integer
    12. Public Function Compare(ByVal x As Object, ByVal y As Object) As Integer Implements IComparer.Compare
    13. Dim listviewX = CType(x, ListViewItem)
    14. Dim listviewY = CType(y, ListViewItem)
    15. Console.WriteLine("Anzahl: {0}, {1}", listviewX.SubItems.Count, listviewY.SubItems.Count)
    16. 'Console.WriteLine("1: {0}, {1}, {2}", listviewX.SubItems(0).Text, listviewX.SubItems(1).Text, listviewX.SubItems(2).Text)
    17. 'Console.WriteLine("2: {0}, {1}, {2}", listviewY.SubItems(0).Text, listviewY.SubItems(1).Text, listviewY.SubItems(2).Text)
    18. Dim compareResult = cicComparer.Compare(listviewX.SubItems(SortColumn).Text, listviewY.SubItems(SortColumn).Text)
    19. If SortOrder = SortOrder.Ascending Then
    20. Return compareResult
    21. ElseIf SortOrder = SortOrder.Descending Then
    22. Return -compareResult
    23. Else
    24. Return 0
    25. End If
    26. End Function
    27. End Class
    Es zeigt sich, dass bereits sortiert wird, obwohl die Zeile noch nicht fertig hinzugefügt ist.
    Anzahl: 3, 1

    Das passiert bei Dir in diesem Code:

    VB.NET-Quellcode

    1. ListView1.Items.Add(S1)
    2. ListView1.Items(X).SubItems.Add(S2)
    3. ListView1.Items(X).SubItems.Add(S3)
    Wenn Du diese Zeilen durch diesen Code ersetzt, spricht die Nachbarin wieder mit Dir: ;)

    VB.NET-Quellcode

    1. Dim lvi = New ListViewItem(S1)
    2. lvi.SubItems.Add(S2)
    3. lvi.SubItems.Add(S3)
    4. ListView1.Items.Add(lvi)
    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!
    Neues Problem :(

    Ich sortiere meine Liste Absteigend;

    9
    8
    7 usw....

    Trage ich aber 10 oder 11 ein setzt er die Zahl zwischen 1 und 2

    also er sortiert nur von 1-9 nicht von 1-10 oder 11 usw...

    VB.NET-Quellcode

    1. Public Class ListViewComparer
    2. Implements IComparer
    3. Private intColumn As Integer
    4. Private soSortOrder As SortOrder
    5. Private cicComparer As CaseInsensitiveComparer
    6. Public Sub New(ByVal ParentListView As ListView)
    7. intColumn = 0
    8. soSortOrder = SortOrder.None
    9. cicComparer = New CaseInsensitiveComparer()
    10. ParentListView.ListViewItemSorter = Me
    11. End Sub
    12. Public Property SortOrder() As SortOrder
    13. Get
    14. Return soSortOrder
    15. End Get
    16. Set(ByVal value As SortOrder)
    17. soSortOrder = value
    18. End Set
    19. End Property
    20. Public Property SortColumn() As Integer
    21. Get
    22. Return intColumn
    23. End Get
    24. Set(ByVal value As Integer)
    25. intColumn = value
    26. End Set
    27. End Property
    28. Public Function Compare(ByVal x As Object, ByVal y As Object) As Integer Implements IComparer.Compare
    29. Dim compareResult As Integer
    30. Dim listviewX As ListViewItem, listviewY As ListViewItem
    31. listviewX = CType(x, ListViewItem)
    32. listviewY = CType(y, ListViewItem)
    33. compareResult = cicComparer.Compare(listviewX.SubItems(intColumn).Text, listviewY.SubItems(intColumn).Text)
    34. If soSortOrder = SortOrder.Ascending Then
    35. Return compareResult
    36. ElseIf soSortOrder = SortOrder.Descending Then
    37. 'Return compareResult * -1
    38. Return -compareResult
    39. Else
    40. Return 0
    41. End If
    42. End Function
    43. End Class


    Im Load event

    VB.NET-Quellcode

    1. cmpFileListViewComparer.SortOrder = SortOrder.Descending
    2. cmpFileListViewComparer.SortColumn = 4
    3. ListView1.Sort()

    Pixxxas schrieb:

    compareResult = cicComparer.Compare(listviewX.SubItems(intColumn).Text, listviewY.SubItems(intColumn).Text)


    Ein Textvergleich. Was erwartest Du? Die einzelnen Zeichen der jeweiligen Zeichenfolge werden natürlich verglichen. Woher soll das Programm auch wissen, dass die Werte anders interpretiert werden sollen, also in diesem Fall als Zahlen?
    Entweder Du gibst Deiner Klasse einen zusätzlichen Parameter, der dann angibt, wie eine Sortierung erfolgen soll/als welcher Variablentyp die ListViewItem-Texte interpretiert werden sollen oder Du machst Deinen ListViewComparer generisch, indem Du schreibst

    VB.NET-Quellcode

    1. Public Class ListViewComparer (Of T As IComparable)
    , später in Compare Deine ListViewItemTexte in T konvertierst und dann den Vergleich zwischen den zu T gewordenen Werten durchfühst.
    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.
    @Pixxxas Hast Du reine numerische Werte oder Strings, in denen auch Zahlen vorkommen?
    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!
    Ich werf mal ein paar Stichworte in den Raum:
    - DataGrid
    - DataTable (Datentypen vergeben)
    - DataSource

    Ich wunder mich eh immer, warum hier viele mit dem ListView rum werkeln um das Grid zu umgehen... Gibts da entscheidende Vorteile oder warum ist das so?
    "Gib einem Mann einen Fisch und du ernährst ihn für einen Tag. Lehre einen Mann zu fischen und du ernährst ihn für sein Leben."

    Wie debugge ich richtig? => Debuggen, Fehler finden und beseitigen
    Wie man VisualStudio nutzt? => VisualStudio richtig nutzen
    Ich bekomme es einfach nicht hin :(

    Ich speicher alles in eine Access DB, er soll die Spalte ID (9) Absteigend Sortieren.

    Felddatentyp ist Zahl

    So schreibe ich in die DB:

    VB.NET-Quellcode

    1. OleDa.InsertCommand.Parameters.Add("@ID", OleDbType.VarWChar, 50, "ID").Value = (CStr(CInt(comp.ListView1.Items.Count.ToString) + 1))


    So lade ich die ID wieder:

    VB.NET-Quellcode

    1. Item.SubItems.Add(Oledr("ID").ToString())
    2. cmpFileListViewComparer.SortOrder = SortOrder.Descending
    3. cmpFileListViewComparer.SortColumn = 9
    4. ListView1.Sort()

    VB.NET-Quellcode



    Beim Starten, alles wunderbar, wenn ich die Liste neu Lade kommt der Fehler;
    Zusätzliche Informationen: InvalidArgument=Value mit dem Wert 9 ist für index ungültig.

    Sorter

    VB.NET-Quellcode

    1. Public Class ListViewComparer
    2. Implements IComparer
    3. Private intColumn As Integer
    4. Private soSortOrder As SortOrder
    5. Private cicComparer As CaseInsensitiveComparer
    6. Public Sub New(ByVal ParentListView As ListView)
    7. intColumn = 0
    8. soSortOrder = SortOrder.None
    9. cicComparer = New CaseInsensitiveComparer()
    10. ParentListView.ListViewItemSorter = Me
    11. End Sub
    12. Public Property SortOrder() As SortOrder
    13. Get
    14. Return soSortOrder
    15. End Get
    16. Set(ByVal value As SortOrder)
    17. soSortOrder = value
    18. End Set
    19. End Property
    20. Public Property SortColumn() As Integer
    21. Get
    22. Return intColumn
    23. End Get
    24. Set(ByVal value As Integer)
    25. intColumn = value
    26. End Set
    27. End Property
    28. Public Function Compare(ByVal x As Object, ByVal y As Object) As Integer Implements IComparer.Compare
    29. Dim compareResult As Integer
    30. Dim listviewX As ListViewItem, listviewY As ListViewItem
    31. Dim bListviewX As Boolean, bListviewY As Boolean
    32. listviewX = CType(x, ListViewItem)
    33. listviewY = CType(y, ListViewItem)
    34. Try
    35. bListviewX = IsNumeric(listviewX.SubItems(intColumn).Text)
    36. bListviewY = IsNumeric(listviewY.SubItems(intColumn).Text)
    37. Catch ex As Exception
    38. End Try
    39. compareResult = 0
    40. If (bListviewX And bListviewY) Then
    41. compareResult = cicComparer.Compare(CInt(listviewX.SubItems(intColumn).Text), CInt(listviewY.SubItems(intColumn).Text))
    42. Else
    43. compareResult = cicComparer.Compare(listviewX.SubItems(intColumn).Text, listviewY.SubItems(intColumn).Text)
    44. End If
    45. If soSortOrder = SortOrder.Ascending Then
    46. Return compareResult
    47. ElseIf soSortOrder = SortOrder.Descending Then
    48. 'Return compareResult * -1
    49. Return -compareResult
    50. Else
    51. Return 0
    52. End If
    53. End Function
    54. End Class

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

    Ich kann zwar grad nix mit dem Laden-Befehl anfangen, aber bevor Du sortierst, schau doch erstmal per MessageBox.Show oder per If ListView1.Columns.Count() < 10 Then Stop, ob da wirklich 10 Spalten (nämlich 0-9) in dem ListView drin sind. Denn bei meinem Test-ListView funktioniert Dein Sorter.
    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.
    Ja es sind wirklich 9 ^^

    Hier mal ein Test Projekt, wenn man das erste mal Startet geht alles, trage ich alles ein oder möchte ein Item Löschen kommt der Fehler.
    Irgend was ist mit der ID, er kann dann nicht mehr Sortieren.
    Dateien
    • Datenbank.rar

      (177,32 kB, 87 mal heruntergeladen, zuletzt: )
    Wenn es 9 Spalten sind, geht der index von 0-8, nicht aber von 0-9(!).

    Spalte 1 = index 0
    ...
    Spalte 9 = index 8
    "Gib einem Mann einen Fisch und du ernährst ihn für einen Tag. Lehre einen Mann zu fischen und du ernährst ihn für sein Leben."

    Wie debugge ich richtig? => Debuggen, Fehler finden und beseitigen
    Wie man VisualStudio nutzt? => VisualStudio richtig nutzen