#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <FontConstants.au3>
#Include <ScrollBarConstants.au3>
#Include <GUIScrollBars.au3>
#include <GUIListView.au3>
#include <GUITreeView.au3>
#include <WinAPI.au3>
Global $i_TLV_CHANGING = False
Global $i_TLV_SEL_CHANGED = False
Global $a_TLV_DATA[1][1]
;Global $h_TLV_FONT = _WinAPI_CreateFont(14, 6, 0, 0, 0, False, False, False, $DEFAULT_CHARSET, $OUT_DEFAULT_PRECIS, $CLIP_DEFAULT_PRECIS, $DEFAULT_QUALITY, 0, 'Arial')
$hGUI = GUICreate("TreeListView Test", 700, 500)
$anTLV = _GUICtrlTreeListView_Create($hGUI, 10, 10, 680, 480)
For $i = 1 To 5
$anTLV_Item = _GUICtrlTreeListView_AddItem($anTLV, "My Folder " & $i & "|Folder|" & Round(Random(1, 5), 1) & " mb")
$anTLV_SubItem1 = _GUICtrlTreeListView_AddItem($anTLV, "My Script " & $i & ".au3|File|" & Round(Random(1, 5), 1) & " kb", $anTLV_Item[0])
$anTLV_SubItem2 = _GUICtrlTreeListView_AddItem($anTLV, "My File " & $i & ".txt|File|" & Round(Random(1, 5), 1) & " kb", $anTLV_Item[0])
_GUICtrlTreeListView_ExpandItem($anTLV, $anTLV_Item, True)
Next
GUISetState(@SW_SHOW, $hGUI)
While 1
$nMsg = GUIGetMsg()
Switch $nMsg
Case $GUI_EVENT_CLOSE
Exit
EndSwitch
WEnd
Func _GUICtrlTreeListView_Create($hWnd, $iLeft, $iTop, $iWidth, $iHeight)
Local $anTLV[2], $hTV, $aTVPos, $aLVPos, $iColsCount, $iLVWidth, $iColWidth
$anTLV[0] = GUICtrlCreateTreeView($iLeft + 5, $iTop + 25, ($iWidth / 2) + 10, $iHeight - 35, BitOr($GUI_SS_DEFAULT_TREEVIEW, $TVS_HASLINES, $TVS_LINESATROOT, $TVS_NOSCROLL, $TVS_NONEVENHEIGHT))
$anTLV[1] = GUICtrlCreateListView("Name|Type|Size", $iLeft, $iTop, $iWidth, $iHeight, BitOr($LVS_SHOWSELALWAYS, $LVS_SINGLESEL, $WS_CLIPSIBLINGS, $LVS_NOSORTHEADER))
$hTV = GUICtrlGetHandle($anTLV[0])
__GUICtrlTreeListView_SetFont($anTLV[1], _SendMessage($hTV, $WM_GETFONT))
;_GUICtrlListView_SetExtendedListViewStyle($anTLV[1], $LVS_EX_GRIDLINES, $LVS_EX_GRIDLINES)
_GUICtrlTreeView_SetHeight($hTV, 21)
_GUIScrollBars_EnableScrollBar($hTV, $SB_BOTH, $ESB_DISABLE_BOTH)
_GUIScrollBars_ShowScrollBar($hTV, $SB_VERT, False)
$aTVPos = ControlGetPos($hWnd, "", $anTLV[0])
$aLVPos = ControlGetPos($hWnd, "", $anTLV[1])
If UBound($aTVPos) > 2 And UBound($aLVPos) > 2 Then
$iColsCount = _GUICtrlListView_GetColumnCount($anTLV[1])
$iLVWidth = $aLVPos[2] - ($aTVPos[2] + 10) - 15
$iColWidth = Floor($iLVWidth / ($iColsCount - 1))
For $i = 1 To $iColsCount - 1
_GUICtrlListView_SetColumnWidth($anTLV[1], $i, $iColWidth)
Next
_GUICtrlListView_SetColumnWidth($anTLV[1], 0, $aTVPos[2])
EndIf
GUIRegisterMsg($WM_NOTIFY, "__GUICtrlTreeListView_WM_NOTIFY")
Return $anTLV
EndFunc
Func _GUICtrlTreeListView_AddItem($anTLV, $sItemText, $nTVCtrl = -1)
Local $anTLV_Item[2], $iItem, $aTVPos
$i_TLV_CHANGING = True
If $nTVCtrl = -1 Then
$nTVCtrl = $anTLV[0]
EndIf
$anTLV_Item[0] = GUICtrlCreateTreeViewItem(StringRegExpReplace($sItemText, '^([^|]*)\|.*', '\1'), $nTVCtrl)
$anTLV_Item[1] = GUICtrlCreateListViewItem(StringRegExpReplace($sItemText, '^[^|]*', ''), $anTLV[1])
$a_TLV_DATA[0][0] += 1
ReDim $a_TLV_DATA[$a_TLV_DATA[0][0] + 1][6]
$a_TLV_DATA[$a_TLV_DATA[0][0]][0] = $anTLV[0] ;TreeView ID
$a_TLV_DATA[$a_TLV_DATA[0][0]][1] = $anTLV[1] ;ListView ID
$a_TLV_DATA[$a_TLV_DATA[0][0]][2] = $anTLV_Item[0] ;Added TV Item ID
$a_TLV_DATA[$a_TLV_DATA[0][0]][3] = $anTLV_Item[1] ;Added LV Item ID
$a_TLV_DATA[$a_TLV_DATA[0][0]][4] = $sItemText ;LV Item Text (including SubItems delimited with |)
$a_TLV_DATA[$a_TLV_DATA[0][0]][5] = $nTVCtrl ;TV Item Parent ID
$i_TLV_CHANGING = False
Return $anTLV_Item
EndFunc
Func _GUICtrlTreeListView_ExpandItem($anTLV, $nTVCtrl, $bExpand)
$i_TLV_CHANGING = True
_GUICtrlTreeView_Expand($anTLV[0], $nTVCtrl[0], $bExpand)
$i_TLV_CHANGING = False
EndFunc
Func __GUICtrlTreeListView_WM_NOTIFY($hWnd, $iMsg, $wParam, $lParam)
Local $hWndFrom, $iIDFrom, $iCode, $tNMHDR, $hTreeView, $hListView, $hLVHeader
Global $iLastScrollPos
If $i_TLV_CHANGING Then
Return $GUI_RUNDEFMSG
EndIf
$tNMHDR = DllStructCreate($tagNMHDR, $lParam)
$hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom"))
$iIDFrom = DllStructGetData($tNMHDR, "IDFrom")
$iCode = DllStructGetData($tNMHDR, "Code")
For $i = 1 To $a_TLV_DATA[0][0]
$hTreeView = GUICtrlGetHandle($a_TLV_DATA[$i][0])
$hListView = GUICtrlGetHandle($a_TLV_DATA[$i][1])
$hLVHeader = _GUICtrlListView_GetHeader($hListView)
Switch $hWndFrom
Case $hLVHeader
Switch $iCode
Case $HDN_ITEMCHANGING, $HDN_ITEMCHANGINGW
Return 1
EndSwitch
ExitLoop
Case $hListView
Switch $iCode
Case $LVN_ITEMCHANGING, $LVN_BEGINDRAG, $LVN_MARQUEEBEGIN
Return 1
Case $LVN_BEGINSCROLL
$tSCROLLINFO = DllStructCreate($tagSCROLLINFO)
DllStructSetData($tSCROLLINFO, "cbSize", DllStructGetSize($tSCROLLINFO))
DllStructSetData($tSCROLLINFO, "fMask", $_SCROLLBARCONSTANTS_SIF_ALL) ;如果在这行报错就改成 $SIF_ALL 试试
_GUIScrollBars_GetScrollInfo($hListView, $SB_VERT, $tSCROLLINFO)
$nPage = DllStructGetData($tSCROLLINFO, "nPage")
$nPos = DllStructGetData($tSCROLLINFO, "nPos")
$nMin = DllStructGetData($tSCROLLINFO, "nMin")
$nMax = DllStructGetData($tSCROLLINFO, "nMax")
$nTrackPos = DllStructGetData($tSCROLLINFO, "nTrackPos")
GUICtrlSetStyle($a_TLV_DATA[$i][0], BitOr($GUI_SS_DEFAULT_TREEVIEW, $TVS_HASLINES, $TVS_LINESATROOT))
_GUIScrollBars_SetScrollInfo($hTreeView, $SB_VERT, $tSCROLLINFO)
For $j = 1 To $nPos
GUICtrlSendMsg($a_TLV_DATA[$i][0], $WM_VSCROLL, $SB_LINEDOWN, 0)
Next
_GUIScrollBars_ShowScrollBar($hTreeView, $SB_BOTH, False)
Case $LVN_ENDSCROLL
_GUIScrollBars_ShowScrollBar($hTreeView, $SB_BOTH, False)
EndSwitch
ExitLoop
Case $hTreeView
Switch $iCode
Case $TVN_SELCHANGEDA, $TVN_SELCHANGEDW
Local $hTVItem = _GUICtrlTreeView_GetSelection($a_TLV_DATA[$i][0])
Local $iTVItemIndx = 0
While 1
$hTVItem = _GUICtrlTreeView_GetPrevVisible($a_TLV_DATA[$i][0], $hTVItem)
If $hTVItem = 0 Then ExitLoop
$iTVItemIndx += 1
WEnd
$i_TLV_CHANGING = True
;ControlListView($hWnd, '', $a_TLV_DATA[$i][0], 'SelectClear')
_GUICtrlListView_SetItemSelected($hListView, $iTVItemIndx)
$i_TLV_CHANGING = False
Case $TVN_ITEMEXPANDINGA, $TVN_ITEMEXPANDINGW
$i_TLV_CHANGING = True
Local $tPOINT = DllStructCreate("int X;int Y")
DllStructSetData($tPOINT, "X", MouseGetPos(0))
DllStructSetData($tPOINT, "Y", MouseGetPos(1))
_WinAPI_ScreenToClient($hTreeView, $tPOINT)
Local $iX = DllStructGetData($tPOINT, "X")
Local $iY = DllStructGetData($tPOINT, "Y")
Local $hTVItem = _GUICtrlTreeView_HitTestItem($hTreeView, $iX, $iY)
If $hTVItem = 0 Then
$hTVItem = _GUICtrlTreeView_GetSelection($hTreeView)
EndIf
If $hTVItem <> 0 Then
Local $iTVItemIndx = _GUICtrlTreeView_Index($hTreeView, $hTVItem) ;$aLVItem[0]
Local $iTVItemID = _GUICtrlTreeView_GetItemParam($hTreeView, $hTVItem) ;$aLVItem[0]
For $j = 1 To $a_TLV_DATA[0][0]
If $iTVItemID = $a_TLV_DATA[$j][2] Then
Local $iChilds = _GUICtrlTreeView_GetChildCount($hTreeView, $hTVItem)
If _GUICtrlTreeView_GetExpanded($hTreeView, $hTVItem) Then
For $x = $j + $iChilds To $j + 1 Step -1
GUICtrlDelete($a_TLV_DATA[$x][3])
$a_TLV_DATA[$x][3] = 0
Next
Else
Local $iLVSelItem = _GUICtrlListView_GetSelectedIndices($hListView)
_GUICtrlListView_DeleteAllItems($hListView)
For $x = 1 To $a_TLV_DATA[0][0]
$hParent = _GUICtrlTreeView_GetParentHandle($a_TLV_DATA[$i][0], $a_TLV_DATA[$x][2])
;It's a child item, it's not hitted parent item (expanded), and the parent of this item is expanded
If $hParent And $hParent <> $hTVItem And Not _GUICtrlTreeView_GetExpanded($a_TLV_DATA[$i][0], $hParent) Then
ContinueLoop
EndIf
;Otherwise we create the item (it's visible) and reset the LV Item ID
$a_TLV_DATA[$x][3] = GUICtrlCreateListViewItem($a_TLV_DATA[$x][4], $a_TLV_DATA[$i][1])
Next
_GUICtrlListView_SetItemSelected($hListView, Int($iLVSelItem))
_GUICtrlTreeView_ClickItem($hTreeView, $hTVItem)
EndIf
ExitLoop
EndIf
Next
EndIf
$i_TLV_CHANGING = False
EndSwitch
ExitLoop
EndSwitch
Next
Return $GUI_RUNDEFMSG
EndFunc
; =========================================================================================
; Name...........: _GUICtrlListView_SetFont
; Description ...: Set font for a list-view controls items and header text
; Syntax.........: _GUICtrlListView_SetFont($hWnd, $hFontLV, $hFontHD = 0)
; Parameters ....: $hWnd - Handle to the control
; $hFontLV - Handle to font
; $hFontHD - Handle to header font (Optional)
; Return values .: Success - True
; Failure - False
; Author ........: rover
; Remarks .......: Use optional header font parameter for a different font/size of header
; =========================================================================================
Func __GUICtrlTreeListView_SetFont($hWnd, $hFontLV, $hFontHD = 0)
;If $Debug_LV Then __UDF_ValidateClassName($hWnd, $__LISTVIEWCONSTANT_ClassName)
If Not IsHWnd($hWnd) Then $hWnd = GUICtrlGetHandle($hWnd)
Local $aReturn, $hHeader, $hDLL
$hHeader = HWnd(_GUICtrlListView_GetHeader($hWnd)) ; get handle to header control
If Not IsHWnd($hWnd) Or Not IsPtr($hFontLV) Or Not IsHWnd($hHeader) Then Return SetError(1, 0, False)
_SendMessage($hWnd, $__LISTVIEWCONSTANT_WM_SETREDRAW, 0) ; disable repainting
$hDLL = DllOpen("UxTheme.dll")
; turn off theme for header control to enable header autosizing
$aReturn = DllCall($hDLL, "int", "SetWindowTheme", "hwnd", $hHeader, "wstr", "", "wstr", "")
If @error Or $aReturn[0] Then
DllClose($hDLL)
Return SetError(2, 0, False)
EndIf
If IsPtr($hFontHD) Then ; set font for items and if available separate font for header
_SendMessage($hWnd, $__LISTVIEWCONSTANT_WM_SETFONT, $hFontLV, True, 0, "hwnd")
_SendMessage($hHeader, $__LISTVIEWCONSTANT_WM_SETFONT, $hFontHD, True, 0, "hwnd")
Else ; set same font for header and items
; resizing header down to a smaller font size causes listview repaint problems, so repainting is enabled
_SendMessage($hWnd, $__LISTVIEWCONSTANT_WM_SETREDRAW, 1) ; enable repainting
_SendMessage($hWnd, $__LISTVIEWCONSTANT_WM_SETFONT, $hFontLV, True, 0, "hwnd")
EndIf
; restore control theme painting
$aReturn = DllCall($hDLL, "int", "SetWindowTheme", "hwnd", $hHeader, "ptr", 0, "ptr", 0)
If @error Or $aReturn[0] Then
DllClose($hDLL)
Return SetError(3, 0, False)
EndIf
DllClose($hDLL)
_SendMessage($hWnd, $__LISTVIEWCONSTANT_WM_SETREDRAW, 1) ; enable repainting
_WinAPI_RedrawWindow($hWnd, 0, 0, $RDW_INVALIDATE)
Return SetError(0, 0, $aReturn[0] <> 1)
EndFunc