Wie kann ich aus einem Pfad (z. B. bei GetOpenFileName) den Dateinamen (bzw. Ordner) filtern?
Natürlich kann man den gesamten Pfad am Backslash splitten oder andere Stringoperationen anwenden. Am einfachsten ist es aber sicher, wenn man sich mit Dir() den Dateinamen zurückgeben lässt - das geht auch mit allen Dateien, nicht nur mit Exceldateien.
Dir()
Rein für den Dateinamen wäre dies eine einfache Möglichkeit:
Sub DateinamenExtrahieren()
Dim varDName
varDName = Application.GetOpenFilename
If varDName = False Then
MsgBox "Nichts gewählt."
Else
varDName = Dir(varDName)
MsgBox varDName
End If
End Sub
Für alle Angaben aus dem Pfad, also Ordner und Datei, könnte folgende Variante genutzt werden:
Sub DateiPfad()
Dim strGesamt As String, strDatei As String, strOrdner As String
strGesamt = Application.GetOpenFilename
strDatei = Dir(strGesamt)
strOrdner = Left(strGesamt, Len(strGesamt) - Len(Dir(strGesamt)))
MsgBox strDatei & vbNewLine & strOrdner & vbNewLine & strGesamt
End Sub
Wenn davon ausgegangen werden kann, dass die Zeichenfolge des Dateinamens einmalig im Pfad ist, kann auch einfach ersetzt werden:
Sub DateiAusPfad2()
Dim varPfad, strOrdner As String, strDatei As String
varPfad = Application.GetOpenFilename
If varPfad <> False Then
strDatei = Dir(varPfad)
strOrdner = Replace(varPfad, strDatei, "")
MsgBox strDatei & vbNewLine & strOrdner
End If
End Sub
Regulärer Ausdruck
Noch eine Variante für die Freunde regulärer Ausdrücke:
Sub DateiAusPfad3()
Dim varDName, Regex As Object, regMatches, regMatch
varDName = Application.GetOpenFilename
If varDName = False Then
MsgBox "Nichts gewählt."
Else
If Regex Is Nothing Then Set Regex = CreateObject("VBScript.RegExp")
Regex.Pattern = "^(.+[\\\/])(.*)$"
Set regMatches = Regex.Execute(varDName)
MsgBox regMatches(0).SubMatches(1)
Set Regex = Nothing
End If
End Sub
Der Schrägstrich wurde aufgenommen, weil Pfade in Onedrive gespeicherter Dateien mit Schrägstrich geliefert werden.
Sollen Ordner und Dateiname zurückgegeben werden, wäre dies möglich:
Sub DateiAusPfad4()
Dim varPfad, strOrdner As String, strDatei As String
Dim Regex As Object, regMatches, regMatch
varPfad = Application.GetOpenFilename
If varPfad <> False Then
If Regex Is Nothing Then Set Regex = CreateObject("VBScript.RegExp")
Regex.Pattern = "^(.+[\\\/])(.*)$"
Set regMatches = Regex.Execute(varPfad)
strOrdner = regMatches(0).SubMatches(0)
strDatei = regMatches(0).SubMatches(1)
Set Regex = Nothing
MsgBox strDatei & vbNewLine & vbNewLine & strOrdner
End If
End Sub
Die integrierte Funktion =ZELLE("Dateiname";A1) liefert den kompletten Pfad bis zum Tabellenblatt. Der Dateiname ist dabei in eckige Klammern eingeschlossen: Pfad[Dateiname]Blattname. Mit einem regulären Ausdruck können die einzelnen Bestandteile ausgegeben werden (ggf. noch Fehlerbehandlung einbauen):
Sub DateiAusZellFunktion()
Dim strPfad, strOrdner As String, strDatei As String, strBlatt As String
Dim Regex As Object, regMatches, regMatch
strPfad = Evaluate("=cell(""filename"",A1)")
If Regex Is Nothing Then Set Regex = CreateObject("VBScript.RegExp")
Regex.Pattern = "^(.*)\[(.*)\](.*)$"
Set regMatches = Regex.Execute(strPfad)
strOrdner = regMatches(0).SubMatches(0)
strDatei = regMatches(0).SubMatches(1)
strBlatt = regMatches(0).SubMatches(2)
Set Regex = Nothing
MsgBox strBlatt & vbNewLine & strDatei & vbNewLine & strOrdner
End Sub
Dynamische Matrixformel (Arrayformel) und verschütteter Array
Per benutzerdefinierter Funktion können seit Excel 365 auch die einzelnen Ordner bzw. Bestandteile eines Pfades in Zellen ausgegeben werden. Dazu diese Funktion als Beispiel:
Function PfadDetails(ByVal strPfad As String)
PfadDetails = ""
If strPfad <> "" Then
Select Case True
Case InStr(1, strPfad, "\") > 0: PfadDetails = Split(Replace(strPfad, "\\", "\"), "\")
Case InStr(1, strPfad, "/") > 0: PfadDetails = Split(Replace(strPfad, "//", "/"), "/")
End Select
End If
End Function
In die Zelle kommt dann diese Formel:
=PfadDetails(A5)
Wenn wie hier im Beispiel in A5 ein Pfad steht, werden an der Zelle mit der Formel die einzelnen Elemente des Pfades ausgegeben. Das letzte Element sollte bei einem kompletten Pfad zu einer Datei der Dateiname sein.
Das Beispiel mit der Funktion =ZELLE("Dateiname";A1) kann auch als Arrayformel verwendet werden:
Function DateiAusZellFunktion(strFktPfad)
Dim arrTemp(1 To 3)
Dim Regex As Object, regMatches, regMatch
DateiAusZellFunktion = ""
If strFktPfad <> "" Then
If Regex Is Nothing Then Set Regex = CreateObject("VBScript.RegExp")
Regex.Pattern = "^(.*)\[(.*)\](.*)$"
Set regMatches = Regex.Execute(strFktPfad)
If regMatches.Count = 1 Then
arrTemp(1) = regMatches(0).SubMatches(2)
arrTemp(2) = regMatches(0).SubMatches(1)
arrTemp(3) = regMatches(0).SubMatches(0)
DateiAusZellFunktion = arrTemp
End If
Set Regex = Nothing
End If
End Function
In die Zelle kommt dann =DateiAusZellFunktion(ZELLE("Dateiname";A1)) und in ihr sowie den Nachbarzellen werden Blattname, Dateiname und Ordnerpfad erscheinen.
Formeln/integrierte Funktionen
Den aktuellen Ordner gibt diese Funktion zurück:
=INFO("Verzeichnis")
In anderen Sprachen geht übrigens auch einfach Basename(Pfad).