Is there an easy way to get the "Target" from a shortcut (*.lnk) file?
Printable View
Is there an easy way to get the "Target" from a shortcut (*.lnk) file?
Probably by either using the Windows Script Host Object Model or the Shell Controls and Automation Library. Link resolution can be a dynamic process though and trying to access the Target can produce dialogs, invoke Windows Installer, etc.
How do I reference the ''Windows Script Host Object'', do you know?
I looked in references, can't see it.
menu Project > References.
Can't see it, wot dais it look like?
From the menu bar click Project then reference. Select microsoft Shell Controls And Automation from the list. If its not there, click browse and select shell32.dll from Windows\System32 folder.
In this example, there is an image at "D:\BG.jpg". The shortcut is at "D:\Shortcut to BG.jpg.lnk".
vb Code:
Option Explicit Private Sub Form_Load() Dim oSH32 As Shell, oItem As Shell32.FolderItem, oFldr As Shell32.Folder Set oSH32 = New Shell Set oFldr = oSH32.NameSpace("D:\") Set oItem = oFldr.ParseName("Shortcut to BG.jpg.lnk") Debug.Print "Shortcut Path: " + oItem.Path Debug.Print "Shortcut Target: " + oItem.GetLink.Path Set oSH32 = Nothing Set oFldr = Nothing Set oItem = Nothing Call Unload(Me) End Sub
This worked for me under XP, no refs needed...
Code:Option Explicit
Private Sub Command1_Click()
Debug.Print GetTarget("C:\Test.Lnk")
End Sub
Function GetTarget(ByVal FileName As String) As String
Dim Obj As Object, Shortcut As Object
Set Obj = CreateObject("WScript.Shell")
Set Shortcut = Obj.CreateShortcut(FileName)
GetTarget = Shortcut.TargetPath
Set Obj = Nothing
Set Shortcut = Nothing
End Function
It says "Windows Script Host Object Model" in the list.
Yes........!!!!!!!!!!
It's easy when you know wot to look for.
Thanks guys!
Have a nice day,
Regards 5ms.
I think I found one caveat recently.
The library "Microsoft Shell Controls and Automation" did not maintain binary compatibility in all newer versions of Windows for some reason (Microsoft goofed?). So if you use early binding your program created on Windows XP probably won't work on Windows 7 and vice versa. I don't recall where Vista fell in this, but it probably also has the issue.
This is a lot like what you run into when automating Office programs of different versions.
I saw the same sort of problem with ADOX. Initially in Vista there was only an ADOX 6.0 type library, which meant that WinXP programs would fail to run under Vista. In Vista SP2 this was corrected and a typelib for ADOX 2.8 was added (msadox28.tlb) along with adding the ADOX 2.8 interfaces to msadox.dll.
I now try to avoid early binding for any of these things in my programs.
Xiphias3 code, got the job dun.
baja_yu, can't see it, Please! post the browse and select name of the .dll for the "Windows Script Host Object Model"
Edgemeal, I'm under XP sp1, your code I got this,
OK, I see it's the wshom.ocx, Thank you baja_yu
baja_yu, I can't Rate your post, so Thank you will have to do.
Have a nice day,
Regards 5ms.
No problem! ;)
You can also late-bind to Shell32.dll as in:
Note the use of ssfDRIVES which avoids the need to parse off the folder name first if you have a full pathname to the shortcut file.Code:Option Explicit
Private Sub Form_Load()
Const ssfDRIVES = 17 'My Computer. Virtual folder containing
'everything on the local computer: storage
'devices, printers, and Control Panel. This
'folder may also contain mapped network drives.
AutoRedraw = True
Show
With CreateObject("Shell.Application").NameSpace(ssfDRIVES). _
ParseName("D:\ZZtestZZ\SomeRandom.lnk")
Print "Shortcut Path: "; .Path
Print "Shortcut Target: "; .GetLink.Path
End With
End Sub
I'll be calling the ''GetTarget2'' about 20 times in a row, there is no references, so the Created Object will be destroyed on ''End Function'', yes/no?
Code:Function GetTarget2(ByVal FileName As String) As String
With CreateObject("Shell.Application").NameSpace(17).ParseName(FileName)
GetTarget2 = .GetLink.Path
End With
End Function
If you need to fetch several of these you can reduce the overhead by not re-creating the objects repeatedly:
In this case MyComputer will release its reference when the Form unloads. If you had a reason to release it early (done with it but lots more to do in the program) just set it to Nothing.Code:Option Explicit
Private Const ssfDRIVES = 17 'My Computer. Virtual folder containing
'everything on the local computer: storage
'devices, printers, and Control Panel. This
'folder may also contain mapped network drives.
Private MyComputer As Object
Private Function GetTarget(ByVal LinkPath As String) As String
GetTarget = MyComputer.ParseName(LinkPath).GetLink.Path
End Function
Private Sub Form_Load()
Set MyComputer = CreateObject("Shell.Application").NameSpace(ssfDRIVES)
AutoRedraw = True
Show
Print GetTarget("D:\SomeShortcuts\Notepad.lnk")
Print GetTarget("D:\SomeShortcuts\WMPlayer.lnk")
End Sub
It would probably be cleaner to bundle all of this in a Class.