Help Updating Lexikos ShellRun for Latest AutoHotkey 2 Release
Posted: 04 Jul 2020, 18:54
I'm trying to get Lexikos's ShellRun running on AutoHotkey 2, but I'm running into problems.
I'm not good with DllCalls and COM objects, so I'm at a bit of a loss.
I'm running into these errors and I don't know what to do:
Original code that worked in older versions of AutoHotkey 2:
My edit that's generating the errors listed above:
(virtually nothing has changed - I only changed VarSetCapacity into BufferAlloc)
I'm not good with DllCalls and COM objects, so I'm at a bit of a loss.
I'm running into these errors and I don't know what to do:
Code: Select all
Error: No valid COM object!
---> shellObj := ComObject(9, pdisp, 1).Application
Error: This value of type "String" has no method named "ShellExecute".
---> shellObj.ShellExecute(prms*)
Code: Select all
/*
ShellRun by Lexikos
requires: AutoHotkey_L
license: http creativecommons.org /publicdomain/zero/1.0/ Broken Link for safety
Credit for explaining this method goes to BrandonLive:
http brandonlive.com /2008/04/27/getting-the-shell-to-run-an-application-for-you-part-2-how/ Broken Link for safety
Shell.ShellExecute(File [, Arguments, Directory, Operation, Show])
http msdn.microsoft.com /en-us/library/windows/desktop/gg537745 Broken Link for safety
https://docs.microsoft.com/en-us/windows/desktop/shell/shell-shellexecute
ShellExecute takes up to 5 parameters.
ShellExecute(sFile, [ vArguments ], [ vDirectory ], [ vOperation ], [ vShow ])
*/
ShellRun(prms*) {
shellWindows := ComObjCreate("{9BA05972-F6A8-11CF-A442-00A0C90A8F39}")
desktop := shellWindows.Item(ComObject(19, 8)) ; VT_UI4, SCW_DESKTOP
; Retrieve top-level browser object.
if ptlb := ComObjQuery(desktop
, "{4C96BE40-915C-11CF-99D3-00AA004AE837}" ; SID_STopLevelBrowser
, "{000214E2-0000-0000-C000-000000000046}") ; IID_IShellBrowser
{
; IShellBrowser.QueryActiveShellView -> IShellView
if DllCall(NumGet(NumGet(ptlb+0)+15*A_PtrSize), "ptr", ptlb, "ptr*", psv:=0) = 0
{
; Define IID_IDispatch.
VarSetCapacity(IID_IDispatch, 16)
NumPut(0x46000000000000C0, NumPut(0x20400, IID_IDispatch, "int64"), "int64")
; IShellView.GetItemObject -> IDispatch (object which implements IShellFolderViewDual)
DllCall(NumGet(NumGet(psv+0)+15*A_PtrSize), "ptr", psv
, "uint", 0, "ptr", &IID_IDispatch, "ptr*", pdisp:=0)
; Get Shell object.
shellObj := ComObject(9,pdisp,1).Application
; IShellDispatch2.ShellExecute
shellObj.ShellExecute(prms*)
ObjRelease(psv)
}
ObjRelease(ptlb)
}
}
(virtually nothing has changed - I only changed VarSetCapacity into BufferAlloc)
Code: Select all
/*
ShellRun by Lexikos
requires: AutoHotkey_L
license: http creativecommons.org /publicdomain/zero/1.0/ Broken Link for safety
Credit for explaining this method goes to BrandonLive:
http brandonlive.com /2008/04/27/getting-the-shell-to-run-an-application-for-you-part-2-how/ Broken Link for safety
Shell.ShellExecute(File [, Arguments, Directory, Operation, Show])
http msdn.microsoft.com /en-us/library/windows/desktop/gg537745 Broken Link for safety
https://docs.microsoft.com/en-us/windows/desktop/shell/shell-shellexecute
ShellExecute takes up to 5 parameters.
ShellExecute(sFile, [ vArguments ], [ vDirectory ], [ vOperation ], [ vShow ])
*/
ShellRun(prms*) {
shellWindows := ComObjCreate("{9BA05972-F6A8-11CF-A442-00A0C90A8F39}")
desktop := shellWindows.Item(ComObject(19, 8)) ; VT_UI4, SCW_DESKTOP
; Retrieve top-level browser object.
if ptlb := ComObjQuery(desktop
, "{4C96BE40-915C-11CF-99D3-00AA004AE837}" ; SID_STopLevelBrowser
, "{000214E2-0000-0000-C000-000000000046}") ; IID_IShellBrowser
{
; IShellBrowser.QueryActiveShellView -> IShellView
if (DllCall(NumGet(NumGet(ptlb+0)+15*A_PtrSize), "ptr", ptlb, "ptr*", psv:=0) = 0)
{
; Define IID_IDispatch.
IID_IDispatch := BufferAlloc(16)
NumPut(0x46000000000000C0, NumPut(0x20400, IID_IDispatch, "int64"), "int64")
; IShellView.GetItemObject -> IDispatch (object which implements IShellFolderViewDual)
DllCall(NumGet(NumGet(psv+0)+15*A_PtrSize), "ptr", psv
, "uint", 0, "ptr", &IID_IDispatch, "ptr*", pdisp:=0)
; Get Shell object.
shellObj := ComObject(9, pdisp, 1).Application
; IShellDispatch2.ShellExecute
shellObj.ShellExecute(prms*)
ObjRelease(psv)
}
ObjRelease(ptlb)
}
}