SnowOfIce Posted August 3, 2005 Posted August 3, 2005 (edited) I had the problem, that my ListViewItems are connected to an event, but after sorting the conection was broken. So I implement the possibility to combine the sorted ListViewItems again to an event: expandcollapse popupFunc _GUICtrlListViewSort(ByRef $h_listview, ByRef $v_descending, $i_sortcol, $s_Title = "", $s_text = "", $event = "") Local $X, $Y, $b_desc, $columns, $items, $v_item, $temp_item If _GUICtrlListViewGetItemCount($h_listview) Then If (StringLen($s_Title) == 0) Then $s_Title = WinGetTitle("") EndIf If (IsArray($v_descending)) Then $b_desc = $v_descending[$i_sortcol] Else $b_desc = $v_descending EndIf $columns = _GUICtrlListViewGetSubItemsCount($h_listview, $s_Title, $s_text) $items = _GUICtrlListViewGetItemCount($h_listview) For $X = 1 To $columns $temp_item = $temp_item & " |" Next $temp_item = StringTrimRight($temp_item, 1) If ($columns > 1) Then Local $a_lv[$items][$columns] For $X = 0 To UBound($a_lv) - 1 Step 1 For $Y = 0 To UBound($a_lv, 2) - 1 Step 1 $v_item = _GUICtrlListViewGetItemText($h_listview, $X, $Y, $s_Title, $s_text) If (StringIsFloat($v_item) Or StringIsInt($v_item)) Then $a_lv[$X][$Y] = Number($v_item) Else $a_lv[$X][$Y] = $v_item EndIf Next Next _GUICtrlListViewDeleteAllItems($h_listview) _ArraySort($a_lv, $b_desc, 0, 0, $columns, $i_sortcol) For $X = 0 To UBound($a_lv) - 1 Step 1 Local $items = GUICtrlCreateListViewItem($temp_item, $h_listview) If IsDeclared ( "event" ) Then GuiCtrlSetOnEvent($items, $event) EndIf For $Y = 0 To UBound($a_lv, 2) - 1 Step 1 _GUICtrlListViewSetItemText($h_listview, $X, $Y, $a_lv[$X][$Y]) Next Next Else Local $a_lv[$items] For $X = 0 To UBound($a_lv) - 1 Step 1 $v_item = _GUICtrlListViewGetItemText($h_listview, $X, -1, $s_Title, $s_text) If (StringIsFloat($v_item) Or StringIsInt($v_item)) Then $a_lv[$X] = Number($v_item) Else $a_lv[$X] = $v_item EndIf Next _GUICtrlListViewDeleteAllItems($h_listview) _ArraySort($a_lv, $b_desc) For $X = 0 To UBound($a_lv) - 1 Step 1 GUICtrlCreateListViewItem(" ", $h_listview) Local $items = GUICtrlCreateListViewItem(" ", $h_listview) If IsDeclared ( "event" ) Then GuiCtrlSetOnEvent($items, $event) EndIf _GUICtrlListViewSetItemText($h_listview, $X, 0, $a_lv[$X]) Next EndIf If (IsArray($v_descending)) Then $v_descending[$i_sortcol] = Not $b_desc Else $v_descending = Not $b_desc EndIf EndIf EndFunc;==>_GUICtrlListViewSort I don't check if it's useful for other Functions in this UDF, too. Edited August 3, 2005 by SnowOfIce
SnowOfIce Posted August 3, 2005 Author Posted August 3, 2005 (edited) I already used gafrost newer version, but here are my version, where I originally implented the change. So if I make an error during implemention to gafrost's version, look here:This Version is NOT recommended! Use version above, or at least gafrost's finalexpandcollapse popupFunc _GUICtrlListViewSort(ByRef $h_listview, ByRef $v_descending, $i_sortcol, $s_Title = "", $s_text = "", $event = "") Local $X, $Y, $b_desc, $columns, $items, $v_item, $temp_item If (StringLen($s_Title) == 0) Then $s_Title = WinGetTitle("") EndIf If (IsArray($v_descending)) Then $b_desc = $v_descending[$i_sortcol] Else $b_desc = $v_descending EndIf $columns = _GUICtrlListViewGetSubItemsCount($h_listview, $s_Title, $s_text) $items = _GUICtrlListViewGetItemCount($h_listview) For $X = 1 To $columns $temp_item = $temp_item & " |" Next $temp_item = StringTrimRight($temp_item, 1) If ($columns > 1) And ($items > 1) Then Local $a_lv[$items][$columns] For $X = 0 To UBound($a_lv) - 1 Step 1 For $Y = 0 To UBound($a_lv, 2) - 1 Step 1 $v_item = _GUICtrlListViewGetItemText($h_listview, $X, $Y, $s_Title, $s_text) If (StringIsFloat($v_item) Or StringIsInt($v_item)) Then $a_lv[$X][$Y] = Number($v_item) Else $a_lv[$X][$Y] = $v_item EndIf Next Next _GUICtrlListViewDeleteAllItems($h_listview) _ArraySort($a_lv, $b_desc, 0, 0, $columns, $i_sortcol) For $X = 0 To UBound($a_lv) - 1 Step 1 local $items = GUICtrlCreateListViewItem($temp_item, $h_listview) If IsDeclared ( "event" ) Then GuiCtrlSetOnEvent($items, $event) EndIf For $Y = 0 To UBound($a_lv, 2) - 1 Step 1 _GUICtrlListViewSetItemText($h_listview, $X, $Y, $a_lv[$X][$Y]) Next Next ElseIf ($items > 1) Then Local $a_lv[$items] For $X = 0 To UBound($a_lv) - 1 Step 1 $v_item = _GUICtrlListViewGetItemText($h_listview, $X, -1, $s_Title, $s_text) If (StringIsFloat($v_item) Or StringIsInt($v_item)) Then $a_lv[$X] = Number($v_item) Else $a_lv[$X] = $v_item EndIf Next _GUICtrlListViewDeleteAllItems($h_listview) _ArraySort($a_lv, $b_desc) For $X = 0 To UBound($a_lv) - 1 Step 1 Local $items = GUICtrlCreateListViewItem(" ", $h_listview) If IsDeclared ( "event" ) Then GuiCtrlSetOnEvent($items, $event) EndIf _GUICtrlListViewSetItemText($h_listview, $X, 0, $a_lv[$X]) Next EndIf If (IsArray($v_descending)) Then $v_descending[$i_sortcol] = Not $b_desc Else $v_descending = Not $b_desc EndIf EndFunc ;==>_GUICtrlListViewSort Edited August 3, 2005 by SnowOfIce
GaryFrost Posted August 3, 2005 Posted August 3, 2005 I'd like to see a practicle example of this working, btw try to stay away from negative conditions could/should be if @NumParams == 6 then Gary SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
SnowOfIce Posted August 3, 2005 Author Posted August 3, 2005 (edited) Here's an example.It's the "Process list and window controls tester" from TuMbLeWeEd with the ability to Sort the columns.The original you could find here:TuMbLeWeEd's Process list and window controls testerI changed that stuff with the negative conditions. As I became adepted, the option with IsDeclared is however possible!s_Process_list_and_window_controls_tester.zipGuiListView.au3 Edited August 3, 2005 by SnowOfIce
SnowOfIce Posted August 4, 2005 Author Posted August 4, 2005 (edited) I found a wired behaviour. If you start the macro with Scite, it run. But if I compile it and run an exe-file I require a more specific If-Case: If IsDeclared ( "event" ) Then hast to be changed to If IsDeclared ( "event" ) And Not ( $event = "" ) Then And another problem: Sometimes I have strings there are actually numbers, but I want to hold the beginning zeros (Hex-numbers for example). On other hand, if I just compare strings, a 1111 would be "smaller" than a 4. A possible solution is to change the following If-cases: If (StringIsFloat($v_item) Or StringIsInt($v_item)) And Not ( StringLeft($v_item, 1) ="0") Then $a_lv[$X] = Number($v_item) ;numbers like 4 , 3465, 5.34 , 345.5 ElseIf StringIsFloat($v_item) And StringLeft($v_item, 2) ="0." Then $a_lv[$X] = Number($v_item) ;numbers like 0.346 Else $a_lv[$X] = $v_item ;strings like "qwe" , "q23" , "000013" EndIf Edited August 4, 2005 by SnowOfIce
GaryFrost Posted August 4, 2005 Posted August 4, 2005 if use the if @NumParams == 6 then condition shouldn't need to worry about isdeclared being event would be the 6th param. SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
GaryFrost Posted August 4, 2005 Posted August 4, 2005 (edited) I'm thinking this will work better, but I'll have to do more testing If (StringIsFloat($v_item) Or StringIsInt($v_item)) And (Not StringLeft($v_item, 1) ="0") Then $a_lv[$X] = Number($v_item) ElseIf (StringIsFloat($v_item) And Not StringRight($v_item, 1) ="0") Then $a_lv[$X] = Number($v_item) Else $a_lv[$X] = $v_item EndIf Edited August 4, 2005 by gafrost SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
GaryFrost Posted August 4, 2005 Posted August 4, 2005 Didn't like the results keeping the current conditions If (StringIsFloat($v_item) Or StringIsInt($v_item)) Then $a_lv[$X][$Y] = Number($v_item) Else $a_lv[$X][$Y] = $v_item EndIf if the number is 0.3456 it's not changed it's still 0.3456 however if a number is a fraction and ends with 0 the zero is dropped personally i can live with that, for example 4.50 becomes 4.5 or 4.0 becomes 4 I'll look into the event param more, i'll have to make a smaller example to to test with. Gary SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
SnowOfIce Posted August 4, 2005 Author Posted August 4, 2005 No. I mean it like I wrote it. ElseIf StringIsFloat($v_item) And StringLeft($v_item, 2) ="0." Then So I wanted to catch all float numbers with a leading zero followed by a point. If I write a float number like "000.123" then there migth be a reason not to write "0.123". Ending zeros on the rigth - there are you totally correct - are uninteresting and would be caugth by the first If-Case if there are no leading zeros.
GaryFrost Posted August 4, 2005 Posted August 4, 2005 I tried that also, but say for instance you have whole numbers and floats in the column, try out your conditions, you'll see what I mean. SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
GaryFrost Posted August 4, 2005 Posted August 4, 2005 No. I mean it like I wrote it.ElseIf StringIsFloat($v_item) And StringLeft($v_item, 2) ="0." ThenSo I wanted to catch all float numbers with a leading zero followed by a point. If I write a float number like "000.123" then there migth be a reason not to write "0.123".Ending zeros on the rigth - there are you totally correct - are uninteresting and would be caugth by the first If-Case if there are no leading zeros.<{POST_SNAPBACK}>What your suggesting would break the sort for all other users that might put whole numbers and floats in same column, thus making the column contain strings and whole numbers, or strings, whole, and floats, and strings are sorted differently than numbers, character by character, where number is < or >Gary SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
GaryFrost Posted August 4, 2005 Posted August 4, 2005 suggest if the generic sort doesn't fit your needs, couple things you could do 1: if all the numbers in the column have the same # of digits on each side of the decimal than put a space at the end of the number, should be treated as string then. 2: or create a custom sort to fit your needs. SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
GaryFrost Posted August 4, 2005 Posted August 4, 2005 Here's an example.It's the "Process list and window controls tester" from TuMbLeWeEd with the ability to Sort the columns.The original you could find here:TuMbLeWeEd's Process list and window controls testerI changed that stuff with the negative conditions. As I became adepted, the option with IsDeclared is however possible!<{POST_SNAPBACK}>Currently there are no click events for ListView items in autoit, so the event param is useless at this point. SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
SnowOfIce Posted August 4, 2005 Author Posted August 4, 2005 (edited) What your suggesting would break the sort for all other users that might put whole numbers and floats in same column, thus making the column contain strings and whole numbers, or strings, whole, and floats, and strings are sorted differently than numbers, character by character, where number is < or >Gary<{POST_SNAPBACK}>Exactly because of this I suggest to change your code. If I write a number different than normal, so with leading zeros, than there is a particular reason, and this is not an example, that mayby sometimes somehow migth happen. In particular if I sort Hex-formatted numbers than I want to leave them as a string.My code did exactly what it should, I think:1 , 2 , 3 , 4 , 567 ... => Numbers (1)1.0 , 2.40 , 5.456 ... => Numbers ending zero migth be deleted, but it migth be ok (1)0.1 , 0.45 , 0.6 ... => Numbers (2)word , test , qwe ... => String (3)0004F4 , 034d34 ... => String (contains also letter) (3)043404 , 000034 ... => String (It's pretty sure, that the leading zero is reasonable, for example a Hex-Format) (3)00.34 , 000.24 ... => String, there migth be a particular reason, why I add additional zeros at the beginning (but I don,t know any special case, where I could use this) (3)If (StringIsFloat($v_item) Or StringIsInt($v_item)) And Not ( StringLeft($v_item, 1) ="0") Then $a_lv[$X] = Number($v_item) ; (1) ElseIf StringIsFloat($v_item) And StringLeft($v_item, 2) ="0." Then $a_lv[$X] = Number($v_item) ; (2) Else $a_lv[$X] = $v_item ; (3) EndIfOnliest weakness:430023 , 00FF00 ... => Both Hex-Numbers, first will be converted to a number, second to a stringBut mayby there exist a way around: Don't save the converted values in the array, but create an additional array, where you note which kind of values are in the column-array. For example: S => string, I => Int, H => Hex (combine if necessary IH=> Hex and Int), so if there are Ints and Hex-numbers in the array, it's supposable that all values are Hex-Values, if not you could convert them anyway.You could also check if the length of all values are constant, then there is no matter, if you compare strings or numbers. Edited August 4, 2005 by SnowOfIce
GaryFrost Posted August 4, 2005 Posted August 4, 2005 Suggestion turned down, you missed the word "break" in my post If you need to do special sorts, then it will require special sort routines. SciTE for AutoItDirections for Submitting Standard UDFs Don't argue with an idiot; people watching may not be able to tell the difference.
SnowOfIce Posted August 7, 2005 Author Posted August 7, 2005 (edited) Sorry, but I don't see where it could break anything. Floats will still converted to a number just as how Ints. The onliest "Numbers" won't be converted are numbers, they are not formated like numbers. Nobody will write a number with leading zeros except he want it like this. But in this case it's no longer a number, because a number has no leading zeros. So it must be a string and should be handled like one. The same with floats with leading zeros! And all other numbers will still converted into numbers, exactly like in your original! But, Ok! It's your UDF, so I close this discussion from my side, and just change my UDF-Version for myself manualy. If I figured out a precise way to fix the weakness that will be my last post in this discussion. Edited August 7, 2005 by SnowOfIce
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now