RSS
StartseiteKnowledge LibraryTop 10Impressum

Besondere Ordner

Pfade zu vordefinierten Systemordnern auflösen

Windows hält ein Vielzahl vordefinierter Standardordner bereit, wie "Eigene Dateien", "Gemeinsame Dateien", Programme, Startmenü u.s.w., die auf jedem Rechner andere Pfade haben können. Passend dazu gibt es auch eine API Funktion, die die Pfade dieser Standardordner zur Laufzeit auflöst.

Wo findet man Ihr Windows - Verzeichnis? "C:\Windows" oder doch "C:\WinNT"? Wie wäre es mit "G:\WinNT"? Dies ist nur ein Beispiel für einen Systemordner, der auf jedem Rechner woanders zu finden sein kann. Windows hält eine Vielzahl weiterer Systemordner bereit, wie "Eigene Dateien", "Gemeinsame Dateien", Programme, Startmenü u.s.w.

Zum Ermitteln der Pfade dieser Systemordner stellt Windows die API Funktion SHGetSpecialFolderLocation bereit. Diese füllt eine ITEMIDLIST-Struktur mit den entsprechenden Informationen, der mit der Shell Funktion SHGetPathFromIDList der reine Pfad im Dateisystem entlockt werden kann.

Mit Windows 2000, aber auch schon zuvor durch den Internet Explorer, wurde der Pool der Systemordner noch einmal aufgestockt und über die Funktion SHGetSpecialFolderLocation können neben den neuen Ordnern "Anwendungsdaten", "Verwaltung" oder "Eigene Bilder", auch die Pfade des Windows bzw. System(32) Verzeichnisses ermittelt werden, wofür zuvor separate API Funktionen benötigt wurden. Zudem besteht über den Flag CSIDL_FLAG_CREATE, einen Ordner anzulegen, wenn er noch nicht existiert.

Für Windows 9x/ME/Windows NT wird diese erweiterte Funktionalität teilweise über die API Funktion SHGetFolderPath aus der weiterverteilbaren Datei "shfolder.dll" bereitgestellt. Welches System, welche Systemordner unterstützt und wo "SHGetFolderPath" aushilft, ist in folgender Tabelle zusammengefasst.

In der hier vorgestellten Funktion GetSpecialFolder, erfolgt der Aufruf der API Funktion SHGetFolderPath nur, wenn SHGetSpecialFolderLocation fehlgeschlagen ist und die Datei "shfolder.dll" vorhanden ist.

Private Type SHITEMID
  cb   As Long
  abID As Byte
End Type

Private Type ITEMIDLIST
  mkid As SHITEMID
End Type

Private Declare Function SHGetFolderPath Lib "shfolder" Alias "SHGetFolderPathA" _
       (ByVal hwndOwner As Long, ByVal nFolder As Long, _
        ByVal hToken As Long, ByVal dwFlags As Long, _
        ByVal pszPath As String) As Long
Private Declare Function SHGetSpecialFolderLocation Lib "Shell32" _
       (ByVal hwndOwner As Long, ByVal nFolder As Long, _
        ByRef ppidl As ITEMIDLIST) As Long
Private Declare Function SHGetPathFromIDList Lib "Shell32" _
       (ByVal pidList As Long, ByVal lpBuffer As String) As Long

Private Declare Function LoadLibrary Lib "kernel32" Alias "LoadLibraryA" _
       (ByVal lpLibFileName As String) As Long
Private Declare Function FreeLibrary Lib "kernel32" _
       (ByVal hLibModule As Long) As Long

Private Const S_OK = 0
Private Const MAX_PATH = 260

Private Const CSIDL_FLAG_CREATE = &H8000&

Public Enum ShellSpecialFolderConstants
  ssfDESKTOP = &H0
  ssfPROGRAMS = &H2
  ssfPERSONAL = &H5
  ssfFAVORITES = &H6
  ssfSTARTUP = &H7
  ssfRECENT = &H8
  ssfSENDTO = &H9
  ssfSTARTMENU = &HB
  ssfDESKTOPDIRECTORY = &H10
  ssfNETHOOD = &H13
  ssfFONTS = &H14
  ssfTEMPLATES = &H15
  ssfCOMMONSTARTMENU = &H16
  ssfCOMMONPROGRAMS = &H17
  ssfCOMMONSTARTUP = &H18
  ssfCOMMONDESKTOPDIRECTORY = &H19
  ssfAPPDATA = &H1A
  ssfPRINTHOOD = &H1B
  ssfLOCALAPPDATA = &H1C
  ssfALTSTARTUP = &H1D
  ssfCOMMONALTSTARTUP = &H1E
  ssfCOMMONFAVORITES = &H1F
  ssfINTERNET_CACHE = &H20
  ssfCOOKIES = &H21
  ssfHISTORY = &H22
  ssfCOMMONAPPDATA = &H23
  ssfWINDOWS = &H24
  ssfSYSTEM = &H25
  ssfPROGRAMFILES = &H26
  ssfMYPICTURES = &H27
  ssfPROFILE = &H28
  ssfPROGRAMFILESCOMMON = &H2B
  ssfCOMMONTEMPLATES = &H2D
  ssfCOMMONDOCUMENTS = &H2E
  ssfCOMMONADMINTOOLS = &H2F
  ssfADMINTOOLS = &H30
  ssfCOMMONMUSIC = &H35
  ssfCOMMONPICTURES = &H36
  ssfCOMMONVIDEO = &H37
  ssfRESOURCES = &H38
  ssfRESOURCESLOCALIZED = &H39
  ssfCDBURNAREA = &H3B
End Enum

Public Function GetSpecialFolder(ByVal Folder As ShellSpecialFolderConstants, _
                        Optional ByVal ForceCreate As Boolean) As String
  Dim tIIDL   As ITEMIDLIST
  Dim strPath As String
  Dim hMod    As Long

  If (ForceCreate) Then
    Folder = Folder Or CSIDL_FLAG_CREATE
  End If
  
  If SHGetSpecialFolderLocation(0, Folder, tIIDL) = S_OK Then
    strPath = Space$(MAX_PATH)
    If SHGetPathFromIDList(tIIDL.mkid.cb, strPath) <> 0 Then
      GetSpecialFolder = Left$(strPath, InStr(1, strPath, vbNullChar) - 1)
    End If
  Else
    strPath = Space$(MAX_PATH)
    hMod = LoadLibrary("shfolder")
    If (hMod <> 0) Then
      If SHGetFolderPath(0, Folder, 0, 0, strPath) = S_OK Then
        GetSpecialFolder = Left$(strPath, InStr(1, strPath, vbNullChar) - 1)
      End If
      FreeLibrary hMod
    End If
  End If
End Function