RichardL Posted September 23, 2022 Share Posted September 23, 2022 Hi, I wanted a multi-column listview, with coloured cells, and I found @Melba23’s example here. That works, but the listview has a flicker. It redraws all the rows whenever you add one. It’s not so obvious with the few lines in the original example, but becomes worse with more items and wider. It’s the same whether you add the new items at the top, as in the example, or on the end. I tried _GUICtrlListView_BeginUpdate and _GUICtrlListView_EndUpdate but that didn’t seem to make any difference. I tried GUICtrlSetState($iGUI1_LV, $GUI_HIDE) before adding multiple items, and $GUI_SHOW after. With this you only see one redraw for multiple items, but still a full redraw for adding a single item. I tried @jpm’s Lock/ResetLock but that seems the same as hide/show. Not directly connected, I tried _GUICtrlListView_DeleteAllItems, that seemed to work, but when I added another item, all the deleted ones reappeared. The code below adds some items, wait 2 seconds, and adds another, see full redraw. After a few more seconds it deletes all the items, you can see them gone. Then it adds a item, which appears at the top, but all the deleted ones reappear below. AutoIt 3.3.14.5 Any help appreciated. expandcollapse popup#include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include "GUIListViewEx.au3" $hGUI = GUICreate("Coloured ListView Example", 500, 300) ; Create ListView $cLV = GUICtrlCreateListView("Column 0|Colourable|Column 2|Column 3", 10, 10, 480, 260, BitOR($LVS_SINGLESEL, $LVS_SHOWSELALWAYS)) For $i = 0 To 3 _GUICtrlListView_SetColumnWidth($cLV, $i, 100) Next ; Initiate ListView = user colours $iLVIndex = _GUIListViewEx_Init($cLV, "", 0, 0, True, 32) ; Set default colours to use Global $aDefCols[4] = ["0x000000", "0xFEFEFE", "0xFFFFFF", "0x0000FF"] _GUIListViewEx_SetDefColours($iLVIndex, $aDefCols) ; If colours used then this function must be run BEFORE GUISetState _GUIListViewEx_MsgRegister() GUISetState() ; Create array and fill listview Global $aLVArray[6][4] ;_GUICtrlListView_BeginUpdate($cLV) For $i = 0 To 5 $sData = "Item " & $i & "-0" $aLVArray[$i][0] = $sData For $j = 1 To 3 $sData &= "|SubItem " & $i & "-" & $j $aLVArray[$i][$j] = "SubItem " & $i & "-" & $j Next _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) ; Some simple conditions for colour $sColSet = ";0x00FF00" If Mod($i, 2) = 0 Then $sColSet = ";0xFFFF00" ElseIf Mod($i, 3) = 0 Then $sColSet = ";0xFF0000" EndIf ; Set item colour ;_GUIListViewEx_SetColour($iLVIndex, $sColSet, 0, 1) Next Sleep(2000) _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) ;_GUICtrlListView_EndUpdate($cLV) Local $iLoops = 0 While 1 $iMsg = GUIGetMsg() Switch $iMsg Case $GUI_EVENT_CLOSE Exit EndSwitch $vRet = _GUIListViewEx_EventMonitor() If $iLoops = 50 Then _GUICtrlListView_DeleteAllItems($cLV) EndIf If $iLoops = 100 Then _GUIListViewEx_InsertSpec($iLVIndex, 0, "More|Data") EndIf Sleep(100) $iLoops += 1 WEnd Link to comment Share on other sites More sharing options...
Moderators Melba23 Posted September 23, 2022 Moderators Share Posted September 23, 2022 RichardL, There will always be some flicker as using colour means hat the ListView is user-drawn and AutoIt takes a time to run through all of the elements to redraw them when the ListView is altered. But using the UDF function _GUIListViewEx_BlockReDraw helps when adding multiple items as I hope you can see in the example below. As to the "DeleteAll" problem, did you read the the Guide that is part of the UDF download? If not then you missed this bit: Quote Closure and Reloading: <...> If you wish to reload the ListView with new data, you will need to clear the current content using _GUICtrlListView_DeleteAllItems, close it within the UDF using _GUIListViewEx_Close, reload the ListView with the new data and then reinitialise it using _GUIListViewEx_Init. Otherwise the UDF will become confused about the current content and errors will certainly occur. When you follow this procedure, the UDF no longer believes that the original content is there and does not show it at the next redraw. Here is your script with the amendments: expandcollapse popup#include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include "GUIListViewEx.au3" $hGUI = GUICreate("Coloured ListView Example", 500, 300) ; Create ListView $cLV = GUICtrlCreateListView("Column 0|Colourable|Column 2|Column 3", 10, 10, 480, 260, BitOR($LVS_SINGLESEL, $LVS_SHOWSELALWAYS)) For $i = 0 To 3 _GUICtrlListView_SetColumnWidth($cLV, $i, 100) Next ; Initiate ListView = user colours $iLVIndex = _GUIListViewEx_Init($cLV, "", 0, 0, True, 32) ; Set default colours to use Global $aDefCols[4] = ["0x000000", "0xFEFEFE", "0xFFFFFF", "0x0000FF"] _GUIListViewEx_SetDefColours($iLVIndex, $aDefCols) ; If colours used then this function must be run BEFORE GUISetState _GUIListViewEx_MsgRegister() GUISetState() ; Create array and fill listview Global $aLVArray[6][4] _GUIListViewEx_BlockReDraw($iLVIndex, True) For $i = 0 To 5 $sData = "Item " & $i & "-0" $aLVArray[$i][0] = $sData For $j = 1 To 3 $sData &= "|SubItem " & $i & "-" & $j $aLVArray[$i][$j] = "SubItem " & $i & "-" & $j Next _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) ; Some simple conditions for colour $sColSet = ";0x00FF00" If Mod($i, 2) = 0 Then $sColSet = ";0xFFFF00" ElseIf Mod($i, 3) = 0 Then $sColSet = ";0xFF0000" EndIf ; Set item colour _GUIListViewEx_SetColour($iLVIndex, $sColSet, 0, 1) Next _GUIListViewEx_BlockReDraw($iLVIndex, False) Sleep(2000) _GUIListViewEx_BlockReDraw($iLVIndex, True) _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) _GUIListViewEx_BlockReDraw($iLVIndex, False) Local $iLoops = 0 While 1 $iMsg = GUIGetMsg() Switch $iMsg Case $GUI_EVENT_CLOSE Exit EndSwitch $vRet = _GUIListViewEx_EventMonitor() If $iLoops = 50 Then _GUICtrlListView_DeleteAllItems($cLV) _GUIListViewEx_Close($iLVIndex) $iLVIndex = _GUIListViewEx_Init($cLV, "", 0, 0, True, 32) EndIf If $iLoops = 100 Then _GUIListViewEx_InsertSpec($iLVIndex, 0, "More|Data") EndIf Sleep(100) $iLoops += 1 WEnd Does that meet with your expectations? M23 Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind Open spoiler to see my UDFs: Spoiler ArrayMultiColSort ---- Sort arrays on multiple columnsChooseFileFolder ---- Single and multiple selections from specified path treeview listingDate_Time_Convert -- Easily convert date/time formats, including the language usedExtMsgBox --------- A highly customisable replacement for MsgBoxGUIExtender -------- Extend and retract multiple sections within a GUIGUIFrame ---------- Subdivide GUIs into many adjustable framesGUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView itemsGUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeViewMarquee ----------- Scrolling tickertape GUIsNoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxesNotify ------------- Small notifications on the edge of the displayScrollbars ----------Automatically sized scrollbars with a single commandStringSize ---------- Automatically size controls to fit textToast -------------- Small GUIs which pop out of the notification area Link to comment Share on other sites More sharing options...
RichardL Posted September 23, 2022 Author Share Posted September 23, 2022 Hi @Melba23 Thanks. The example program is working fine now. I've copied the changes into the real program. The update is looking smooth, but the DeleteAllItems is causing a crash when new items are added. I'm puzzling what I've done different from the example. Should the _GUIListViewEx_EventMonitor() be done just once? at the start? Link to comment Share on other sites More sharing options...
RichardL Posted September 23, 2022 Author Share Posted September 23, 2022 Fixed, stupid error, it's all fine. Link to comment Share on other sites More sharing options...
Moderators Melba23 Posted September 23, 2022 Moderators Share Posted September 23, 2022 RichardL, Delighted to hear it. M23 Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind Open spoiler to see my UDFs: Spoiler ArrayMultiColSort ---- Sort arrays on multiple columnsChooseFileFolder ---- Single and multiple selections from specified path treeview listingDate_Time_Convert -- Easily convert date/time formats, including the language usedExtMsgBox --------- A highly customisable replacement for MsgBoxGUIExtender -------- Extend and retract multiple sections within a GUIGUIFrame ---------- Subdivide GUIs into many adjustable framesGUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView itemsGUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeViewMarquee ----------- Scrolling tickertape GUIsNoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxesNotify ------------- Small notifications on the edge of the displayScrollbars ----------Automatically sized scrollbars with a single commandStringSize ---------- Automatically size controls to fit textToast -------------- Small GUIs which pop out of the notification area Link to comment Share on other sites More sharing options...
RichardL Posted September 25, 2022 Author Share Posted September 25, 2022 @Melba23, I have another listview with a flicker and I think you might be saying it can't be fixed. "There will always be some flicker as using colour..." With fewer than about 20 rows the flicker is very fast, almost unnoticible. With 40 rows or more it's annoying. The action is: - if the LV is full, delete the top row. - insert a new row at the end - Update the text of one sub-item in the new row (possibly a few times) - change the colour on that sub-item. The delete and insert each make a flicker but combined into one with BlockRedraw. The new row and the change sub-item each make a flicker. The colour change works very nicely, changes the colour without any flicker. Is any improvement possible? expandcollapse popup#include <GUIConstantsEx.au3> #include <Date.au3> #include <WindowsConstants.au3> #include "GUIListViewEx.au3" Opt("MustDeclareVars", 1) Local $iGW = 700 Local $iGH = 600 Local $hGUI Local $cLV Local $iLVIndex Local $vRet Local $sData Local $sColSet Local $iMsg Local $iColWid $hGUI = GUICreate("Coloured ListView Example", $iGW, $iGH) ; Create ListView $cLV = GUICtrlCreateListView("Column 0|Colourable|Column 2|Column 3|C4|C5", 10, 10, $iGW - 20, $iGH - 20, BitOR($LVS_SINGLESEL, $LVS_SHOWSELALWAYS)) For $i = 0 To 5 $iColWid = 100 If $i = 3 Then $iColWid = 160 _GUICtrlListView_SetColumnWidth($cLV, $i, $iColWid) Next ; Initiate ListView = user colours $iLVIndex = _GUIListViewEx_Init($cLV, "", 0, 0, True, 32) ; Set default colours to use ;Global $aDefCols[4] = ["0x000000", "0xFEFEFE", "0xFFFFFF", "0x0000FF"] ;_GUIListViewEx_SetDefColours($iLVIndex, $aDefCols) ; If colours used then this function must be run BEFORE GUISetState _GUIListViewEx_MsgRegister() GUISetState() ; Create array and fill listview Global $aLVArray[6][4] _GUIListViewEx_BlockReDraw($iLVIndex, True) For $i = 0 To 5 $sData = "Item " & $i & "-0" $aLVArray[$i][0] = $sData For $j = 1 To 3 $sData &= "|SubItem " & $i & "-" & $j $aLVArray[$i][$j] = "SubItem " & $i & "-" & $j Next _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) _GUIListViewEx_InsertSpec($iLVIndex, 0, $sData) ; Some simple conditions for colour $sColSet = ";0x00FF00" If Mod($i, 2) = 0 Then $sColSet = ";0xFFFF00" ElseIf Mod($i, 3) = 0 Then $sColSet = ";0xFF0000" EndIf ; Set item colour _GUIListViewEx_SetColour($iLVIndex, $sColSet, 0, 1) Next _GUIListViewEx_BlockReDraw($iLVIndex, False) ConsoleWrite(StringFormat("Count %3d\n", _GUICtrlListView_GetItemCount($cLV))) Sleep(1000) ; Try deleting an item. ;_GUICtrlListView_DeleteItem($cLV, 3) !NO _GUIListViewEx_DeleteSpec($iLVIndex, 3) ConsoleWrite(StringFormat("Count %3d\n", _GUICtrlListView_GetItemCount($cLV))) Sleep(1000) Local $iNofRows Local $iDly ; Insert more lines For $iIx = 1 To 5000 $iDly = 200 _GUIListViewEx_BlockReDraw($iLVIndex, True) If $iIx > 20 Then $iDly = 400 $iNofRows = _GUICtrlListView_GetItemCount($cLV) If $iNofRows > $iGH / 18 + 5 Then _GUIListViewEx_DeleteSpec($iLVIndex, 0) EndIf Sleep($iDly) $sData = StringFormat("Count %3d|Rows %3d|---------|------------|-----------|---------", $iIx, $iNofRows) ;_GUIListViewEx_BlockReDraw($iLVIndex, True) _GUIListViewEx_InsertSpec($iLVIndex, -1, $sData) _GUIListViewEx_BlockReDraw($iLVIndex, False) Local $iLVItmNo $iLVItmNo = _GUICtrlListView_GetItemCount($cLV) - 1 ConsoleWrite(StringFormat("Count %3d\n", $iLVItmNo)) Sleep($iDly) _GUIListViewEx_ChangeItem($iLVIndex, $iLVItmNo, 3, _Now()) Sleep($iDly) _GUIListViewEx_SetColour($iLVIndex, ";0x00FF00", $iLVItmNo, 3) Next Local $iLoops = 0 While 1 $iMsg = GUIGetMsg() Switch $iMsg Case $GUI_EVENT_CLOSE Exit EndSwitch ;$vRet = _GUIListViewEx_EventMonitor() If 0 Then ; Try delet all and add again. If $iLoops = 50 Then _GUICtrlListView_DeleteAllItems($cLV) _GUIListViewEx_Close($iLVIndex) $iLVIndex = _GUIListViewEx_Init($cLV, "", 0, 0, True, 32) EndIf If $iLoops = 100 Then _GUIListViewEx_InsertSpec($iLVIndex, 0, "More|Data") _GUIListViewEx_InsertSpec($iLVIndex, 0, "More|Data") EndIf EndIf Sleep(100) $iLoops += 1 WEnd Link to comment Share on other sites More sharing options...
Moderators Melba23 Posted September 26, 2022 Moderators Share Posted September 26, 2022 RichardL, Alas, I do not think that the flicker can be reduced any further when there are a significant number of rows in the ListView. This thread shows the effort that went into getting the code as "fast" as it is now! Something that does reduce the flicker a bit is setting the value that you subsequently change into the original data that you load into the new line - I realise this is an example script and your full version may not be able to do such a thing, but it might be worth taking a look to see if something along those lines is possible. Taking another route, LarsJ has done a lot of work on "virtual ListViews" which are significantly faster that the "normal" ones when there are large numbers of rows in the control - and as I pinched used his colouring code in my UDF I am sure that he must have a coloured version on the forum somewhere. That might well be a solution. M23 Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind Open spoiler to see my UDFs: Spoiler ArrayMultiColSort ---- Sort arrays on multiple columnsChooseFileFolder ---- Single and multiple selections from specified path treeview listingDate_Time_Convert -- Easily convert date/time formats, including the language usedExtMsgBox --------- A highly customisable replacement for MsgBoxGUIExtender -------- Extend and retract multiple sections within a GUIGUIFrame ---------- Subdivide GUIs into many adjustable framesGUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView itemsGUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeViewMarquee ----------- Scrolling tickertape GUIsNoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxesNotify ------------- Small notifications on the edge of the displayScrollbars ----------Automatically sized scrollbars with a single commandStringSize ---------- Automatically size controls to fit textToast -------------- Small GUIs which pop out of the notification area Link to comment Share on other sites More sharing options...
Solution kurtykurtyboy Posted September 28, 2022 Solution Share Posted September 28, 2022 @RichardL Try adding the $LVS_EX_DOUBLEBUFFER extended style. This eliminated all flickering for me. $cLV = GUICtrlCreateListView("Column 0|Colourable|Column 2|Column 3|C4|C5", 10, 10, $iGW - 20, $iGH - 20, BitOR($LVS_SINGLESEL, $LVS_SHOWSELALWAYS)) _GUICtrlListView_SetExtendedListViewStyle($cLV, BitOR($LVS_EX_FULLROWSELECT, $WS_EX_CLIENTEDGE, $LVS_EX_DOUBLEBUFFER)) CYCho 1 Link to comment Share on other sites More sharing options...
kurtykurtyboy Posted September 28, 2022 Share Posted September 28, 2022 For what it's worth, here is a quick and dirty version of your last example using the LarsJ virtual listview plus colors. It's surprisingly easy to set up, you just need to take care of your data and color arrays. expandcollapse popup#include <GUIConstantsEx.au3> #include <Date.au3> #include <WindowsConstants.au3> #include <Array.au3> #include <GuiListView.au3> #include <ListViewConstants.au3> Opt("MustDeclareVars", 1) Local $iGW = 700 Local $iGH = 600 Local $hGUI Global $cLV, $h_cLV Local $iLVIndex Local $vRet Local $sData Local $sColSet Local $iMsg Local $iColWid Local $iNumberCols = 6 Global $tText = DllStructCreate("wchar[4096]") $hGUI = GUICreate("Coloured ListView Example", $iGW, $iGH) ; Create ListView - set $LVS_OWNERDATA to indicate that we will keep track of our own data $cLV = GUICtrlCreateListView("Column 0|Colourable|Column 2|Column 3|C4|C5", 10, 10, $iGW - 20, $iGH - 20, BitOR($LVS_SINGLESEL, $LVS_SHOWSELALWAYS, $LVS_OWNERDATA)) _GUICtrlListView_SetExtendedListViewStyle($cLV, BitOR($LVS_EX_FULLROWSELECT, $WS_EX_CLIENTEDGE, $LVS_EX_DOUBLEBUFFER)) $h_cLV = GUICtrlGetHandle($cLV) For $i = 0 To $iNumberCols - 1 $iColWid = 100 If $i = 3 Then $iColWid = 160 _GUICtrlListView_SetColumnWidth($cLV, $i, $iColWid) Next GUIRegisterMsg($WM_NOTIFY, "WM_NOTIFY") GUISetState() ; Create array to hold listview data Global $aLVArray[0][$iNumberCols] ; Create array to hold color data Global $aLVColors[0][$iNumberCols] Local $aData[1][$iNumberCols], $aColors[1][$iNumberCols] _GUICtrlListView_BeginUpdate($cLV) For $i = 0 To 5 $sData = "Item " & $i & "-0" $aData[0][0] = $sData For $j = 1 To 3 $aData[0][$j] = "SubItem " & $i & "-" & $j Next If UBound($aLVColors) = 0 Then _ArrayAdd($aLVArray, $aData) Else _ArrayInsert($aLVArray, 0, $aData) EndIf _ArrayInsert($aLVArray, 0, $aData) ; Some simple conditions for colour $aColors[0][0] = 0xFFFFFF $aColors[0][1] = 0xFFFFFF $aColors[0][2] = 0xFFFFFF $aColors[0][3] = 0xFFFFFF $aColors[0][4] = 0xFFFFFF $aColors[0][5] = 0xFFFFFF $sColSet = _WinAPI_SwitchColor(0x00FF00) If Mod($i, 2) = 0 Then $sColSet = _WinAPI_SwitchColor(0xFFFF00) ElseIf Mod($i, 3) = 0 Then $sColSet = _WinAPI_SwitchColor(0xFF0000) EndIf If UBound($aLVColors) = 0 Then _ArrayAdd($aLVColors, $aColors) Else _ArrayInsert($aLVColors, 0, $aColors) EndIf ; Set item colour $aColors[0][1] = $sColSet _ArrayInsert($aLVColors, 0, $aColors) Next _GUICtrlListView_EndUpdate($cLV) ;force the listview to update itself GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) ConsoleWrite(StringFormat("Count %3d\n", _GUICtrlListView_GetItemCount($cLV))) Sleep(1000) ; Try deleting an item. ;~ _GUICtrlListView_DeleteItem($cLV, 3) _ArrayDelete($aLVArray, 3) _ArrayDelete($aLVColors, 3) GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) ConsoleWrite(StringFormat("Count %3d\n", _GUICtrlListView_GetItemCount($cLV))) Sleep(1000) Local $iNofRows Local $iDly ; Insert more lines For $iIx = 1 To 5000 $iDly = 200 If $iIx > 20 Then $iDly = 400 $iNofRows = UBound($aLVArray) If $iNofRows > $iGH / 18 + 5 Then _ArrayDelete($aLVArray, 0) _ArrayDelete($aLVColors, 0) EndIf GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) Sleep($iDly) $sData = StringFormat("Count %3d|Rows %3d|---------|------------|-----------|---------", $iIx, $iNofRows) ;_GUIListViewEx_BlockReDraw($iLVIndex, True) ;~ _GUIListViewEx_InsertSpec($iLVIndex, -1, $sData) ;~ _GUIListViewEx_BlockReDraw($iLVIndex, False) $aData[0][0] = "Count " & $iIx $aData[0][1] = "Rows " & $iNofRows $aData[0][2] = "---------" $aData[0][3] = "---------" $aData[0][4] = "---------" $aData[0][5] = "---------" _ArrayAdd($aLVArray, $aData) $aColors[0][0] = 0xFFFFFF $aColors[0][1] = 0xFFFFFF $aColors[0][2] = 0xFFFFFF $aColors[0][3] = 0xFFFFFF $aColors[0][4] = 0xFFFFFF $aColors[0][5] = 0xFFFFFF _ArrayAdd($aLVColors, $aColors) GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) Local $iLVItmNo $iLVItmNo = UBound($aLVArray) - 1 ConsoleWrite(StringFormat("Count %3d\n", $iLVItmNo)) Sleep($iDly) ;~ _GUIListViewEx_ChangeItem($iLVIndex, $iLVItmNo, 3, _Now()) $aLVArray[$iLVItmNo][3] = _Now() ;~ GUICtrlSendMsg($cLV, $LVM_REDRAWITEMS, $iLVItmNo, $iLVItmNo) GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) Sleep($iDly) ;~ _GUIListViewEx_SetColour($iLVIndex, ";0x00FF00", $iLVItmNo, 3) $aLVColors[$iLVItmNo][3] = 0x00FF00 GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) Next ;~ Local $iLoops = 0 ;~ While 1 ;~ $iMsg = GUIGetMsg() ;~ Switch $iMsg ;~ Case $GUI_EVENT_CLOSE ;~ Exit ;~ EndSwitch ;~ ;$vRet = _GUIListViewEx_EventMonitor() ;~ If 0 Then ; Try delet all and add again. ;~ If $iLoops = 50 Then ;~ _GUICtrlListView_DeleteAllItems($cLV) ;~ _GUIListViewEx_Close($iLVIndex) ;~ $iLVIndex = _GUIListViewEx_Init($cLV, "", 0, 0, True, 32) ;~ EndIf ;~ If $iLoops = 100 Then ;~ _GUIListViewEx_InsertSpec($iLVIndex, 0, "More|Data") ;~ _GUIListViewEx_InsertSpec($iLVIndex, 0, "More|Data") ;~ EndIf ;~ EndIf ;~ Sleep(100) ;~ $iLoops += 1 ;~ WEnd Func WM_NOTIFY($hWnd, $iMsg, $wParam, $lParam) Local $tNMHDR = DllStructCreate($tagNMHDR, $lParam) Local $hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom")) Local $iCode = DllStructGetData($tNMHDR, "Code") Switch $hWndFrom Case $h_cLV Switch $iCode ;virtual listview and color change from larsj ;https://www.autoitscript.com/forum/topic/168707-listview-item-subitem-background-colour/#comment-1234009 Case $LVN_GETDISPINFOW ; Fill virtual listview Local $tNMLVDISPINFO = DllStructCreate($tagNMLVDISPINFO, $lParam) If BitAND(DllStructGetData($tNMLVDISPINFO, "Mask"), $LVIF_TEXT) Then Local $sItem = $aLVArray[DllStructGetData($tNMLVDISPINFO, "Item")][DllStructGetData($tNMLVDISPINFO, "SubItem")] DllStructSetData($tText, 1, $sItem) DllStructSetData($tNMLVDISPINFO, "TextMax", StringLen($sItem)) DllStructSetData($tNMLVDISPINFO, "Text", DllStructGetPtr($tText)) EndIf Case $NM_CUSTOMDRAW Local $tNMLVCUSTOMDRAW = DllStructCreate($tagNMLVCUSTOMDRAW, $lParam) Local $dwDrawStage = DllStructGetData($tNMLVCUSTOMDRAW, "dwDrawStage") Switch $dwDrawStage ; Holds a value that specifies the drawing stage Case $CDDS_PREPAINT ; Before the paint cycle begins Return $CDRF_NOTIFYITEMDRAW ; Notify the parent window of any item-related drawing operations Case $CDDS_ITEMPREPAINT ; Before painting an item Return $CDRF_NOTIFYSUBITEMDRAW ; Notify the parent window of any subitem-related drawing operations Case BitOR($CDDS_ITEMPREPAINT, $CDDS_SUBITEM) ; Before painting a subitem ;Local $iItem = DllStructGetData($tNMLVCUSTOMDRAW, "dwItemSpec") ; Item index ;Local $iSubItem = DllStructGetData($tNMLVCUSTOMDRAW, "iSubItem") ; Subitem index ;DllStructSetData( $tNMLVCUSTOMDRAW, "ClrTextBk", $aColors[$iItem][$iSubItem] ) ; Backcolor of item/subitem DllStructSetData($tNMLVCUSTOMDRAW, "ClrTextBk", $aLVColors[DllStructGetData($tNMLVCUSTOMDRAW, "dwItemSpec")][DllStructGetData($tNMLVCUSTOMDRAW, "iSubItem")]) Return $CDRF_NEWFONT ; $CDRF_NEWFONT must be returned after changing font or colors EndSwitch EndSwitch EndSwitch Return $GUI_RUNDEFMSG #forceref $hWnd, $iMsg, $wParam EndFunc ;==>WM_NOTIFY Link to comment Share on other sites More sharing options...
Moderators Melba23 Posted September 28, 2022 Moderators Share Posted September 28, 2022 kurtykurtyboy, Very nice - thanks for the tip. M23 Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind Open spoiler to see my UDFs: Spoiler ArrayMultiColSort ---- Sort arrays on multiple columnsChooseFileFolder ---- Single and multiple selections from specified path treeview listingDate_Time_Convert -- Easily convert date/time formats, including the language usedExtMsgBox --------- A highly customisable replacement for MsgBoxGUIExtender -------- Extend and retract multiple sections within a GUIGUIFrame ---------- Subdivide GUIs into many adjustable framesGUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView itemsGUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeViewMarquee ----------- Scrolling tickertape GUIsNoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxesNotify ------------- Small notifications on the edge of the displayScrollbars ----------Automatically sized scrollbars with a single commandStringSize ---------- Automatically size controls to fit textToast -------------- Small GUIs which pop out of the notification area Link to comment Share on other sites More sharing options...
RichardL Posted September 29, 2022 Author Share Posted September 29, 2022 @kurtykurtyboy Thanks, wow! I've put your ExtendedViewStyle solution into the test program and the real one and it's perfect. Now we can look at the info without being annoyed by the flicker. I have tried the 2nd one, but can't resist the single line fix. I'll keep it in mind for next time. Link to comment Share on other sites More sharing options...
argumentum Posted September 29, 2022 Share Posted September 29, 2022 ..just in case. Y' know, "make it until you brake it" is my motto. Spoiler expandcollapse popup#include <GUIConstantsEx.au3> #include <Date.au3> #include <WindowsConstants.au3> #include <Array.au3> #include <GuiListView.au3> #include <ListViewConstants.au3> ;;; https://www.autoitscript.com/forum/topic/208868-listview-flicker-and-failing-to-deleteall/ Opt("MustDeclareVars", 1) Opt("TrayAutoPause", 0) Local $iGW = 700 Local $iGH = 600 Local $hGUI Global $cLV, $h_cLV Local $iLVIndex Local $vRet Local $sData Local $sColSet Local $iMsg Local $iColWid Local $iNumberCols = 6 Global $tText = DllStructCreate("wchar[4096]") $hGUI = GUICreate("Coloured ListView Example", $iGW, $iGH) ; Create ListView - set $LVS_OWNERDATA to indicate that we will keep track of our own data $cLV = GUICtrlCreateListView("Column 0|Colourable|Column 2|Column 3|C4|C5", 10, 10, $iGW - 20, $iGH - 20, BitOR($LVS_SINGLESEL, $LVS_SHOWSELALWAYS, $LVS_OWNERDATA)) _GUICtrlListView_SetExtendedListViewStyle($cLV, BitOR($LVS_EX_FULLROWSELECT, $WS_EX_CLIENTEDGE, $LVS_EX_DOUBLEBUFFER)) $h_cLV = GUICtrlGetHandle($cLV) For $i = 0 To $iNumberCols - 1 $iColWid = 100 If $i = 3 Then $iColWid = 160 _GUICtrlListView_SetColumnWidth($cLV, $i, $iColWid) Next GUIRegisterMsg($WM_NOTIFY, "WM_NOTIFY") GUISetState() ; Create array to hold listview data Global $aLVArray[0][$iNumberCols] ; Create array to hold color data Global $aLVColors[0][$iNumberCols] Local $aData[1][$iNumberCols], $aColors[1][$iNumberCols] _GUICtrlListView_BeginUpdate($cLV) For $i = 0 To 5 $sData = "Item " & $i & "-0" $aData[0][0] = $sData For $j = 1 To 3 $aData[0][$j] = "SubItem " & $i & "-" & $j Next If UBound($aLVColors) = 0 Then _ArrayAdd($aLVArray, $aData) Else _ArrayInsert($aLVArray, 0, $aData) EndIf _ArrayInsert($aLVArray, 0, $aData) ; Some simple conditions for colour $aColors[0][0] = 0xFFFFFF $aColors[0][1] = 0xFFFFFF $aColors[0][2] = 0xFFFFFF $aColors[0][3] = 0xFFFFFF $aColors[0][4] = 0xFFFFFF $aColors[0][5] = 0xFFFFFF $aColors[0][0] = 0 $aColors[0][1] = 0 $aColors[0][2] = 0 $aColors[0][3] = 0 $aColors[0][4] = 0 $aColors[0][5] = 0 $sColSet = _WinAPI_SwitchColor(0x009900) If Mod($i, 2) = 0 Then $sColSet = _WinAPI_SwitchColor(0x999900) ElseIf Mod($i, 3) = 0 Then $sColSet = _WinAPI_SwitchColor(0x990000) EndIf If UBound($aLVColors) = 0 Then _ArrayAdd($aLVColors, $aColors) Else _ArrayInsert($aLVColors, 0, $aColors) EndIf ; Set item colour $aColors[0][1] = $sColSet _ArrayInsert($aLVColors, 0, $aColors) Next _GUICtrlListView_EndUpdate($cLV) ;force the listview to update itself GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) ConsoleWrite(StringFormat("Count: %3d\n", _GUICtrlListView_GetItemCount($cLV))) ;~ Sleep(1000) ; Try deleting an item. ;~ _GUICtrlListView_DeleteItem($cLV, 3) _ArrayDelete($aLVArray, 3) _ArrayDelete($aLVColors, 3) GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) ConsoleWrite(StringFormat("Count:: %3d\n", _GUICtrlListView_GetItemCount($cLV))) ;~ Sleep(1000) Local $iNofRows Local $iDly ; Insert more lines For $iIx = 1 To 5000 $iDly = 200 If $iIx > 20 Then $iDly = 400 $iNofRows = UBound($aLVArray) If $iNofRows > $iGH / 18 + 5 Then _ArrayDelete($aLVArray, 0) _ArrayDelete($aLVColors, 0) EndIf GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) ;~ Sleep($iDly) ; Scotty, full speed ahead, warp factor 10 ( https://www.youtube.com/watch?v=AzGVz9cTIpg ) $sData = StringFormat("Count %3d|Rows %3d|---------|------------|-----------|---------", $iIx, $iNofRows) ;_GUIListViewEx_BlockReDraw($iLVIndex, True) ;~ _GUIListViewEx_InsertSpec($iLVIndex, -1, $sData) ;~ _GUIListViewEx_BlockReDraw($iLVIndex, False) $aData[0][0] = "Count " & $iIx $aData[0][1] = "Rows " & $iNofRows $aData[0][2] = "---------" $aData[0][3] = "---------" $aData[0][4] = "---------" $aData[0][5] = "---------" _ArrayAdd($aLVArray, $aData) $aColors[0][0] = 0xFFFFFF $aColors[0][1] = 0xFFFFFF $aColors[0][2] = 0xFFFFFF $aColors[0][3] = 0xFFFFFF $aColors[0][4] = 0xFFFFFF $aColors[0][5] = 0xFFFFFF $aColors[0][0] = 0 $aColors[0][1] = 0 $aColors[0][2] = 0 $aColors[0][3] = 0 $aColors[0][4] = 0 $aColors[0][5] = 0 _ArrayAdd($aLVColors, $aColors) GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) Local $iLVItmNo $iLVItmNo = UBound($aLVArray) - 1 ConsoleWrite(StringFormat("Count::: %3d\n", $iLVItmNo)) ;~ Sleep($iDly) ;~ _GUIListViewEx_ChangeItem($iLVIndex, $iLVItmNo, 3, _Now()) $aLVArray[$iLVItmNo][3] = _Now() ;~ GUICtrlSendMsg($cLV, $LVM_REDRAWITEMS, $iLVItmNo, $iLVItmNo) GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) ;~ Sleep($iDly) ;~ _GUIListViewEx_SetColour($iLVIndex, ";0x00FF00", $iLVItmNo, 3) $aLVColors[$iLVItmNo][3] = 0x009900 GUICtrlSendMsg($cLV, $LVM_SETITEMCOUNT, UBound($aLVArray), 0) Next Func WM_NOTIFY($hWnd, $iMsg, $wParam, $lParam) Local $tNMHDR = DllStructCreate($tagNMHDR, $lParam) Local $hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom")) Local $iCode = DllStructGetData($tNMHDR, "Code") Switch $hWndFrom Case $h_cLV Switch $iCode ;virtual listview and color change from larsj ;https://www.autoitscript.com/forum/topic/168707-listview-item-subitem-background-colour/#comment-1234009 Case $LVN_GETDISPINFOW ; Fill virtual listview Local $tNMLVDISPINFO = DllStructCreate($tagNMLVDISPINFO, $lParam) If BitAND(DllStructGetData($tNMLVDISPINFO, "Mask"), $LVIF_TEXT) Then ; vvvvvvvvv these IF UBound() THEN are needed vvvvvvvvvvvvvvvvvv If DllStructGetData($tNMLVDISPINFO, "Item") < UBound($aLVArray) And DllStructGetData($tNMLVDISPINFO, "SubItem") < UBound($aLVArray, 2) Then Local $sItem = $aLVArray[DllStructGetData($tNMLVDISPINFO, "Item")][DllStructGetData($tNMLVDISPINFO, "SubItem")] DllStructSetData($tText, 1, $sItem) DllStructSetData($tNMLVDISPINFO, "TextMax", StringLen($sItem)) DllStructSetData($tNMLVDISPINFO, "Text", DllStructGetPtr($tText)) Else ConsoleWrite('! GETDISPINFOW ! ' & DllStructGetData($tNMLVDISPINFO, "Item") & ' , ' & DllStructGetData($tNMLVDISPINFO, "SubItem") & @CRLF) EndIf EndIf Case $NM_CUSTOMDRAW Local $tNMLVCUSTOMDRAW = DllStructCreate($tagNMLVCUSTOMDRAW, $lParam) Local $dwDrawStage = DllStructGetData($tNMLVCUSTOMDRAW, "dwDrawStage") Switch $dwDrawStage ; Holds a value that specifies the drawing stage Case $CDDS_PREPAINT ; Before the paint cycle begins Return $CDRF_NOTIFYITEMDRAW ; Notify the parent window of any item-related drawing operations Case $CDDS_ITEMPREPAINT ; Before painting an item Return $CDRF_NOTIFYSUBITEMDRAW ; Notify the parent window of any subitem-related drawing operations Case BitOR($CDDS_ITEMPREPAINT, $CDDS_SUBITEM) ; Before painting a subitem ;Local $iItem = DllStructGetData($tNMLVCUSTOMDRAW, "dwItemSpec") ; Item index ;Local $iSubItem = DllStructGetData($tNMLVCUSTOMDRAW, "iSubItem") ; Subitem index ;DllStructSetData( $tNMLVCUSTOMDRAW, "ClrTextBk", $aColors[$iItem][$iSubItem] ) ; Backcolor of item/subitem If DllStructGetData($tNMLVCUSTOMDRAW, "dwItemSpec") < UBound($aLVColors) And DllStructGetData($tNMLVCUSTOMDRAW, "iSubItem") < UBound($aLVColors) Then DllStructSetData($tNMLVCUSTOMDRAW, "ClrTextBk", $aLVColors[DllStructGetData($tNMLVCUSTOMDRAW, "dwItemSpec")][DllStructGetData($tNMLVCUSTOMDRAW, "iSubItem")]) Else ; vvvvvvvvv these IF UBound() THEN are needed vvvvvvvvvvvvvvvvvv ConsoleWrite('! repaint ! ' & DllStructGetData($tNMLVCUSTOMDRAW, "dwItemSpec") & ' , ' & DllStructGetData($tNMLVCUSTOMDRAW, "iSubItem") & @CRLF) EndIf Return $CDRF_NEWFONT ; $CDRF_NEWFONT must be returned after changing font or colors EndSwitch EndSwitch EndSwitch Return $GUI_RUNDEFMSG #forceref $hWnd, $iMsg, $wParam EndFunc ;==>WM_NOTIFY I have a wheel mouse and I tend to spin it. Is a metal one so it rotates on its own and the momentum brakes the code. So I added If then to save the code from random OMG, wtf moments Follow the link to my code contribution ( and other things too ). FAQ - Please Read Before Posting. Link to comment Share on other sites More sharing options...
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