Jump to content

Filepath with correct uppercase/lowercase


Recommended Posts

Hello,

what is the best way to update a given path to the actual case-sensitive form of that path? I tried to achieve it with, but that is giving mixed results.

Func _Main()
    _Demo("tesT")
    _Demo("t_X_y_esT")
EndFunc   ;==>_Main

Func _Demo($sPath)
    DirCreate(@ScriptDir & "\" & $sPath)
    ConsoleWrite("Path created:    " & @ScriptDir & "\" & $sPath & @CRLF)
    ConsoleWrite("Path lower case: " & StringLower(@ScriptDir & "\" & $sPath) & @CRLF)
    ConsoleWrite("Path retrieved : " & FileGetLongName(StringLower(@ScriptDir & "\" & $sPath)) & @CRLF)
    ConsoleWrite("-----" & @CRLF)
    DirRemove(@ScriptDir & "\" & $sPath)
EndFunc   ;==>_Demo

//Edit:

this is doing the job, but is there something "easier"?

Func _Main()
    Local $sPath = StringLower(@ScriptDir)
    ConsoleWrite(FileGetLongName($sPath) & @CRLF)
    ConsoleWrite(_Test($sPath, "tesT") & @CRLF)
    ConsoleWrite(_Test($sPath, "t_X_y_esT") & @CRLF)
EndFunc   ;==>_Main

Func _FilePath_CaseSensitive($sPath, $sFilter)
    ; Append backslash
    If StringRight($sPath, 1) <> "\" Then $sPath &= "\"

    ; Check if the path exists
    If Not FileExists($sPath) Then Return SetError(0x01, 0, $sPath & $sFilter)
    $sPath = Execute('"' & StringRegExpReplace(FileGetLongName($sPath), "^([a-z])(:)", '" & StringUpper("$1:") & "') & '"')

    ; Check if folder/file from filter exists
    If Not FileExists($sPath & $sFilter) Then Return SetError(0x02, 0, $sPath & $sFilter)

    ; Search for filepath
    Local $hSearch = FileFindFirstFile($sPath & $sFilter)
    If @error Then Return SetError(0x03, 0, $sPath & $sFilter)
    While 1
        ; Execute search
        $sSearch = FileFindNextFile($hSearch)
        If @error Then
            ; Upon error return function parameter
            $sSearch = $sFilter
            ExitLoop
        EndIf
        ; Continue search if result does not match search exactly
        If Not StringRegExp($sSearch, "(?i)^\Q" & $sFilter & "\E") Then ContinueLoop
    WEnd
    FileClose($hSearch)

    ; Return function parameter
    If $sSearch == $sFilter Then Return SetError(0x04, 0, $sPath & $sFilter)

    ; Return result
    Return $sPath & $sSearch
EndFunc   ;==>_FilePath_CaseSensitive

 

Edited by HurleyShanabarger
Link to comment
Share on other sites

This one seems better:

Func _PathCaseSensitive($sPath)
    If Not FileExists($sPath) Then Return SetError(0x01, 0, $sPath)
    ; Get shortname, convert lower case and then get long name
    $sPath = FileGetLongName(StringLower(FileGetShortName($sPath)))

    ; Replace drive letter with uppercase version
    $sPath = Execute('"' & StringRegExpReplace($sPath, "^(\w):", '" & StringUpper("$1:") & "') & '"')
    Return $sPath
EndFunc   ;==>_PathCaseSensitive

 

Link to comment
Share on other sites

Maybe I am misinterpreting you and what you are trying to accomplish

  1. I took your example an have run it
    1. Then I looked at windows explorer and paths are there with case and without
  2. Then run it without the stringlower
    1. All looks fine

If you want the path lowercase you should put stringlower around the filegetlongname instead of within it

In other words I do not get mixed results with your example and removing stringlower within filegetlongname

Link to comment
Share on other sites

Its interesting to see the inconsistent behavior if I run below 2 times (to make sure folders are there)

The underscores seems to be treated in an incorrect way (Fileshortname has same behavior)

Func _Main()
    _Demo("tesT")
    _Demo("t_X_y_esT")
    _Demo("tXyesT")
EndFunc   ;==>_Main

Func _Demo($sPath)
    DirCreate(@ScriptDir & "\" & $sPath)
 ;   ConsoleWrite("Path created:    " & @ScriptDir & "\" & $sPath & @CRLF)
  ;  ConsoleWrite("Path lower case: " & StringLower(@ScriptDir & "\" & $sPath) & @CRLF)
  $fullFileName=@ScriptDir & "\" & $sPath
    ConsoleWrite("Path retrieved : " & FileGetlongName($fullFileName) & @CRLF)
    ConsoleWrite("-----" & @CRLF)
  ;  DirRemove(@ScriptDir & "\" & $sPath)
 EndFunc   ;==>_Demo

    $f=filegetlongname
    ;$f=filegetshortname
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "tesT") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "test") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "TEST") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "t_X_y_esT") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "t_x_y_est") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "T_X_Y_EST") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "tXyesT") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "txyest") & @CRLF)
    ConsoleWrite("Path retrieved : " & $F(@ScriptDir & "\" & "TXYEST") & @CRLF)

    consolewrite("-------" & @CRLF)
 _main()
Path retrieved : C:\projects\csvread_au3\tesT
Path retrieved : C:\projects\csvread_au3\tesT
Path retrieved : C:\projects\csvread_au3\tesT
Path retrieved : C:\projects\csvread_au3\t_X_y_esT
Path retrieved : C:\projects\csvread_au3\t_x_y_est
Path retrieved : C:\projects\csvread_au3\T_X_Y_EST
Path retrieved : C:\projects\csvread_au3\tXyesT
Path retrieved : C:\projects\csvread_au3\tXyesT
Path retrieved : C:\projects\csvread_au3\tXyesT
-------
Path retrieved : C:\projects\csvread_au3\tesT
-----
Path retrieved : C:\projects\csvread_au3\t_X_y_esT
-----
Path retrieved : C:\projects\csvread_au3\tXyesT
-----

 

Link to comment
Share on other sites

I looked around but not much easier then you are already doing

_WinAPI_ShellGetLocalizedName or NtQueryObject but they are all not easier then you are already doing.

Maybe you can identify which characters in filename will cause the weird behavior and from there on you can investigate further.

I feel its more a windows thing then AutoIt manipulating the results so maybe if you google on non AutoIt forums you will find the cause

 

 

Link to comment
Share on other sites

I does not matter to windows. I don't want to change it in the registry.

 

The path in the registry is stored by an external application, mostly in lower case. The path points to projects that the external application is handling. My tool lists the stored projects and displays it in a GUI. For the purpose of the selected it is way easier to have it the proper casing.

c:\users\username\projects\thisistheprojectnameofanexampleproject

just doesn't read as nice as

C:\Users\Username\Projects\ThisIsTheProjectNameOfAnExampleProject

 

Link to comment
Share on other sites

 @Subz has suggested the _FileListToArray, and here is the example for it:
#include <File.au3>

_Main()

Func _Main()
    _Demo("tesT")
    _Demo("t_X_y_esT")
EndFunc   ;==>_Main

Func _Demo($sPath)
    DirCreate(@ScriptDir & "\" & $sPath)
    ConsoleWrite("Path created:    " & @ScriptDir & "\" & $sPath & @CRLF)
    ConsoleWrite("Path lower case: " & StringLower(@ScriptDir & "\" & $sPath) & @CRLF)
    ConsoleWrite("Path retrieved : " & FileGetLongName(StringLower(@ScriptDir & "\" & $sPath)) & @CRLF)
    
    $a_Path=_FileListToArray(@ScriptDir,"*",$FLTA_FOLDERS)
    if @error=0 Then
        For $x=1 to $a_Path[0]
            If $a_Path[$x]=$sPath then ConsoleWrite("Path from FileListToArray: " & $a_Path[$x] & @CRLF)
        Next
    EndIf

    ConsoleWrite("-----" & @CRLF)
    ;DirRemove(@ScriptDir & "\" & $sPath)
EndFunc   ;==>_Demo

I think that should do it. 

Edited by Dan_555

Some of my script sourcecode

Link to comment
Share on other sites

This seems to work. First get the shortname and from the shortname get the long name.
I left the lowercase in there but you could strip that to

Func _Main()
    _Demo("tesT")
    _Demo("T_X_y_esT")
    _Demo("tXyesT")
EndFunc   ;==>_Main

Func _Demo($sPath)
    DirCreate(@ScriptDir & "\" & $sPath)
    ConsoleWrite("Path created:    " & @ScriptDir & "\" & $sPath & @CRLF)
    ConsoleWrite("Path lower case: " & StringLower(@ScriptDir & "\" & $sPath) & @CRLF)
    $fullFileName=@ScriptDir & "\" & $sPath
    $fullFileName=stringlower($fullFileName)
    $fullFileName=FileGetShortName($fullFileName)
    $fullFileName=FileGetlongName($fullFileName)

    ConsoleWrite("Path retrieved : " &  $fullFileName & @CRLF)
    DirRemove(@ScriptDir & "\" & $sPath)
EndFunc   ;==>_Demo

 _main()

 

Link to comment
Share on other sites

4 hours ago, junkew said:

This seems to work. First get the shortname and from the shortname get the long name.
I left the lowercase in there but you could strip that to

Func _Main()
    _Demo("tesT")
    _Demo("T_X_y_esT")
    _Demo("tXyesT")
EndFunc   ;==>_Main

Func _Demo($sPath)
    DirCreate(@ScriptDir & "\" & $sPath)
    ConsoleWrite("Path created:    " & @ScriptDir & "\" & $sPath & @CRLF)
    ConsoleWrite("Path lower case: " & StringLower(@ScriptDir & "\" & $sPath) & @CRLF)
    $fullFileName=@ScriptDir & "\" & $sPath
    $fullFileName=stringlower($fullFileName)
    $fullFileName=FileGetShortName($fullFileName)
    $fullFileName=FileGetlongName($fullFileName)

    ConsoleWrite("Path retrieved : " &  $fullFileName & @CRLF)
    DirRemove(@ScriptDir & "\" & $sPath)
EndFunc   ;==>_Demo

 _main()

 

Isn't that the same as my solution from here:

On 2/8/2021 at 12:34 PM, HurleyShanabarger said:

This one seems better:

Func _PathCaseSensitive($sPath)
    If Not FileExists($sPath) Then Return SetError(0x01, 0, $sPath)
    ; Get shortname, convert lower case and then get long name
    $sPath = FileGetLongName(StringLower(FileGetShortName($sPath)))

    ; Replace drive letter with uppercase version
    $sPath = Execute('"' & StringRegExpReplace($sPath, "^(\w):", '" & StringUpper("$1:") & "') & '"')
    Return $sPath
EndFunc   ;==>_PathCaseSensitive

 

 

Link to comment
Share on other sites

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 account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...