- Offizieller Beitrag
Diese Funktion liest ein Verzeichnis rekursiv ein und stellt den Inhalt in einem TreeView dar.
Man kann angeben, ob auch Dateien in das TreeView aufgenommen werden sollen (Achtung! Das dauert u.U. sehr lange).
Die Funktion gibt (wenn erfolgreich) ein Array mit 2 Werten zurück ( [0] = Anzahl der Verzeichnisse, [1] = Anzahl der Dateien ).
Screenshot:
autoit.de/wcf/attachment/3644/
Ausführliches Beispielscript ist dabei:
Spoiler anzeigen
#include<GuiTreeView.au3> ; erforderlich
; Beispiel Anfang
#include<EditConstants.au3>
#include<GUIConstantsEx.au3>
#include<TreeViewConstants.au3>
#include<WindowsConstants.au3>
Global $sPath = 'c:\programme\autoit3\'
Global $width = 800, $height = 600
Global $hGui = GUICreate('Directory-Treeview-Beispiel', $width, $height, -1, 0)
Global $hInput = GUICtrlCreateInput($sPath, 10, 10, $width - 160, 20, BitOR($ES_AUTOHSCROLL, $ES_READONLY))
Global $hChoose = GUICtrlCreateButton('...', $width - 148, 9, 30, 22)
GUICtrlSetFont(-1, 9, 600, 0, 'Verdana')
Global $hFiles = GUICtrlCreateCheckbox('inkl. Dateien', $width - 100, 10, 80, 16)
Global $bFiles = False
Global $hTreeView = GUICtrlCreateTreeView(10, 40, $width - 20, $height - 70, BitOR($GUI_SS_DEFAULT_TREEVIEW, $TVS_CHECKBOXES), $WS_EX_STATICEDGE)
GUICtrlSetFont(-1, 10, 400, 0, 'Arial')
GUICtrlSetBkColor(-1, 0xF8F8F8)
Global $hContextMenu = GUICtrlCreateContextMenu($hTreeView)
Global $hInfo = GUICtrlCreateMenuItem('Informationen', $hContextMenu)
Global $hExpand = GUICtrlCreateMenuItem('alles auseinanderfalten', $hContextMenu)
Global $hCollapse = GUICtrlCreateMenuItem('alles zusammenfalten', $hContextMenu)
Global $hStatus1 = GUICtrlCreateLabel('', 0, $height - 16, $width / 2, 16, -1, $WS_EX_STATICEDGE)
Global $hStatus2 = GUICtrlCreateLabel('', $width / 2 + 1, $height - 16, $width / 2, 16, -1, $WS_EX_STATICEDGE)
GUISetState()
_TreeViewUpdate()
[/autoit] [autoit][/autoit] [autoit]While True
Switch GUIGetMsg()
Case $hChoose
$sTmp = FileSelectFolder('Verzeichnis auswählen', '', 0, $sPath, $hGui)
If Not @error Then
$sPath = $sTmp
GUICtrlSetData($hInput, $sPath)
_TreeViewUpdate()
EndIf
Case $hFiles
$bFiles = BitAND(GUICtrlRead($hFiles), $GUI_CHECKED) = $GUI_CHECKED
_TreeViewUpdate()
Case $GUI_EVENT_PRIMARYDOWN
$aInfo = GUIGetCursorInfo($hGui)
If $aInfo[4] = $hTreeView Then
$oldGUIDataSeparatorChar = Opt('GUIDataSeparatorChar', '\')
GUICtrlSetData($hStatus1, ' ' & StringReplace(_GUICtrlTreeView_GetTree($hTreeView), '\\', '\'))
Opt('GUIDataSeparatorChar', $oldGUIDataSeparatorChar)
If BitAND(_GUICtrlTreeView_HitTest($hTreeView, $aInfo[0] - 11, $aInfo[1] - 41), 64) Then
$checked = _GUICtrlTreeView_GetChecked($hTreeView, _GUICtrlTreeView_GetSelection($hTreeView))
_GUICtrlTreeView_SetBold($hTreeView, _GUICtrlTreeView_GetSelection($hTreeView), $checked)
$hItem = _GUICtrlTreeView_GetFirstChild($hTreeView, _GUICtrlTreeView_GetSelection($hTreeView))
If $hItem Then _MarkChildItems($hTreeView, $hItem, $checked)
EndIf
EndIf
Case $hInfo
$oldGUIDataSeparatorChar = Opt('GUIDataSeparatorChar', '\')
$TempPath = StringReplace(_GUICtrlTreeView_GetTree($hTreeView), '\\', '\')
Opt('GUIDataSeparatorChar', $oldGUIDataSeparatorChar)
MsgBox(0, 'Informationen', $TempPath & @CRLF & 'Dateigröße: ' & FileGetSize($TempPath) & ' Bytes')
Case $hExpand
_ExpandAll($hTreeView)
Case $hCollapse
_CollapseAll($hTreeView)
Case $GUI_EVENT_CLOSE
Exit
EndSwitch
WEnd
Func _MarkChildItems(ByRef $hTreeView, $hItem, $checked)
Do
$hNewItem = _GUICtrlTreeView_GetFirstChild($hTreeView, $hItem)
If $hNewItem Then _MarkChildItems($hTreeView, $hNewItem, $checked)
_GUICtrlTreeView_SetChecked($hTreeView, $hItem, $checked)
_GUICtrlTreeView_SetBold($hTreeView, $hItem, $checked)
$hItem = _GUICtrlTreeView_GetNextChild($hTreeView, $hItem)
Until $hItem = 0
EndFunc ;==>_MarkChildItems
Func _ExpandAll($hTreeView)
_GUICtrlTreeView_Expand($hTreeView)
EndFunc ;==>_ExpandAll
Func _CollapseAll($hTreeView)
_GUICtrlTreeView_Expand($hTreeView, 0, False)
EndFunc ;==>_CollapseAll
Func _TreeViewUpdate()
GUICtrlSetData($hStatus1, ' Bitte warten! Verzeichnis wird eingelesen...')
GUICtrlSetData($hStatus2, '')
$Timer = TimerInit()
Local $aCount = _GUICtrlTreeView_CreateDirectory($hTreeView, $sPath, $bFiles)
If Not @error Then
$msg = ' Benötigte Zeit: ' & Round(TimerDiff($Timer) / 1000, 3) & ' sek.'
$msg &= ' | ' & $aCount[1] & ' Datei(en) und ' & $aCount[0] & ' Verzeichniss(e)'
GUICtrlSetData($hStatus1, ' Fertig.')
GUICtrlSetData($hStatus2, $msg)
EndIf
EndFunc ;==>_TreeViewUpdate
; Beispiel Ende
;===============================================================================
; Function Name: _GUICtrlTreeView_CreateDirectory($hTreeView, $sPath, $bFiles)
; Description:: erstellt ein TreeView mit Verzeichnissen (+Dateien)
; Parameter(s): $hTreeView = ControlID/Handle des TreeViews
; $sPath = Verzeichnispfad, der dargestellt werden soll
; $bFiles = True = auch Dateien anzeigen, False = nur Verzeichnisse
; Requirement(s): #include<GuiTreeView.au3>
; Return Value(s): Array mit Anzahl der Verzeichnisse=[0] und Dateien=[1]
; 0 und @error = 1, wenn der Pfad nicht existiert bzw. kein Verzeichnis ist
; 0 und @error = 2, wenn das FileSystemObject nicht erstellt werden konnte
; Author(s): Oscar (http://www.autoit.de)
;===============================================================================
Func _GUICtrlTreeView_CreateDirectory($hTreeView, $sPath, $bFiles = False)
Local $hFileItem, $FolderColor = 0x0000FF, $Folder, $aCount[2] = [0, 0]
If Not StringInStr(FileGetAttrib($sPath), 'D') Then Return SetError(1, 0, 0)
$sPath = FileGetLongName($sPath)
Local $oFSO = ObjCreate('Scripting.FileSystemObject')
If @error Then Return SetError(2, 0, 0)
_GUICtrlTreeView_BeginUpdate($hTreeView)
_GUICtrlTreeView_DeleteAll(GUICtrlGetHandle($hTreeView))
Local $hTreeViewItem = GUICtrlCreateTreeViewItem($sPath, $hTreeView)
GUICtrlSetColor(-1, $FolderColor)
_GUICtrlTreeView_SetIcon($hTreeView, $hTreeViewItem, 'shell32.dll', 0)
$Folder = $oFSO.GetFolder($sPath)
_CreateDirectoryRecursive($hTreeView, $Folder, $hTreeViewItem, $bFiles, $aCount)
If $bFiles Then
For $Files In $Folder.Files
$hFileItem = GUICtrlCreateTreeViewItem($Files.Name, $hTreeViewItem)
$aCount[1] += 1
Next
EndIf
_GUICtrlTreeView_SetIcon($hTreeView, $hTreeViewItem, 'shell32.dll', 3, 2)
_GUICtrlTreeView_SetIcon($hTreeView, $hTreeViewItem, 'shell32.dll', 110, 4)
_GUICtrlTreeView_EndUpdate($hTreeView)
GUICtrlSetState($hTreeViewItem, $GUI_EXPAND)
$oFSO = ''
Return $aCount
EndFunc ;==>_GUICtrlTreeView_CreateDirectory
Func _CreateDirectoryRecursive($hTreeView, $Folder, $ItemOld, $bFiles, ByRef $aCount)
Local $hFolderItem, $hFileItem, $FolderColor = 0x0000FF
For $Subfolder In $Folder.SubFolders
$hFolderItem = GUICtrlCreateTreeViewItem($Subfolder.Name, $ItemOld)
GUICtrlSetColor(-1, $FolderColor)
_GUICtrlTreeView_SetIcon($hTreeView, $hFolderItem, 'shell32.dll', 3, 2)
_GUICtrlTreeView_SetIcon($hTreeView, $hFolderItem, 'shell32.dll', 110, 4)
$aCount[0] += 1
_CreateDirectoryRecursive($hTreeView, $Subfolder, $hFolderItem, $bFiles, $aCount)
If $bFiles Then
For $Files In $Subfolder.Files
$hFileItem = GUICtrlCreateTreeViewItem($Files.Name, $hFolderItem)
$aCount[1] += 1
Next
EndIf
Next
EndFunc ;==>_CreateDirectoryRecursive
Edit ( 06.01.09 Ich habe jetzt herausgefunden, dass die Icons an die Child-Items "vererbt" werden, wenn man nicht explizit ein Icon angibt. Das habe ich mir zunutze gemacht und weise dem ersten Verzeichnis zuerst das Datei-Icon zu, was dann an alle Childs vererbt wird. Den Unterverzeichnissen weise ich dann jeweils das Verzeichnis-Icon zu (dauert nicht so lange) und am Schluß ändere ich das Icon vom ersten Verzeichnis auf das Verzeichnis-Icon. So spare ich mir die Zuweisung bei den Dateien, was ja sonst sehr lange gedauert hat.
Jetzt dauert das Beispielscript (mit Dateien anhaken) bei mir nur noch 1,3 Sek. statt vorher 9,5 Sek.