windows - Compruebe la presencia de un atajo en Inno Setup
installation inno-setup (1)
En mi instalador de Inno Setup, necesito asegurarme de que haya un acceso directo a un determinado archivo en una carpeta. El nombre del atajo es arbitrario y no está bajo mi control. Solo sé a qué archivo debe apuntar. Si falta el acceso directo, necesito generar el acceso directo. Si ya está presente, no debe crearse nuevamente.
Supongo que de alguna manera es posible recorrer todos los archivos de acceso directo en la carpeta correspondiente y verificar a qué archivo apuntan. En un comentario de una respuesta a accesos directos / iconos compartidos , se menciona una interfaz IShellLink
, pero no sé cómo hacer que esté disponible en la sección Code
. ( Uses ShlObj;
no se reconoce)
¿Alguien tiene una sugerencia de cómo podría resolver este problema?
Residencia en
- el ejemplo oficial de Inno Setup
CodeAutomation2.iss
y - respuesta eliminada por @TLama a Cómo obtener acceso directo a destino con InnoSetup .
Requiere la versión Unicode de Inno Setup.
const
MAX_PATH = 260;
STGM_READ = $00000000;
SLGP_SHORTPATH = $1;
SLGP_RAWPATH = $4;
SLGP_RELATIVEPRIORITY = $8;
CLSID_ShellLink = ''{00021401-0000-0000-C000-000000000046}'';
type
TWin32FindDataW = record
dwFileAttributes: DWORD;
ftCreationTime: TFileTime;
ftLastAccessTime: TFileTime;
ftLastWriteTime: TFileTime;
nFileSizeHigh: DWORD;
nFileSizeLow: DWORD;
dwReserved0: DWORD;
dwReserved1: DWORD;
cFileName: array[0..MAX_PATH-1] of Char;
cAlternateFileName: array[0..13] of Char;
end;
IShellLinkW = interface(IUnknown)
''{000214F9-0000-0000-C000-000000000046}''
function GetPath(pszFile: string; cchMaxPath: Integer;
var FindData: TWin32FindDataW; fFlags: DWORD): HRESULT;
procedure Dummy2;
procedure Dummy3;
function GetDescription(pszName: string; cchMaxName: Integer): HRESULT;
function SetDescription(pszName: string): HRESULT;
function GetWorkingDirectory(pszDir: string; cchMaxPath: Integer): HRESULT;
function SetWorkingDirectory(pszDir: string): HRESULT;
function GetArguments(pszArgs: string; cchMaxPath: Integer): HRESULT;
function SetArguments(pszArgs: string): HRESULT;
function GetHotkey(var pwHotkey: Word): HRESULT;
function SetHotkey(wHotkey: Word): HRESULT;
function GetShowCmd(out piShowCmd: Integer): HRESULT;
function SetShowCmd(iShowCmd: Integer): HRESULT;
function GetIconLocation(pszIconPath: string; cchIconPath: Integer;
out piIcon: Integer): HRESULT;
function SetIconLocation(pszIconPath: string; iIcon: Integer): HRESULT;
function SetRelativePath(pszPathRel: string; dwReserved: DWORD): HRESULT;
function Resolve(Wnd: HWND; fFlags: DWORD): HRESULT;
function SetPath(pszFile: string): HRESULT;
end;
IPersist = interface(IUnknown)
''{0000010C-0000-0000-C000-000000000046}''
function GetClassID(var classID: TGUID): HRESULT;
end;
IPersistFile = interface(IPersist)
''{0000010B-0000-0000-C000-000000000046}''
function IsDirty: HRESULT;
function Load(pszFileName: string; dwMode: Longint): HRESULT;
function Save(pszFileName: string; fRemember: BOOL): HRESULT;
function SaveCompleted(pszFileName: string): HRESULT;
function GetCurFile(out pszFileName: string): HRESULT;
end;
function GetLinkFileTarget(const FileName: string): string;
var
FindData: TWin32FindDataW;
ComObject: IUnknown;
ShellLink: IShellLinkW;
PersistFile: IPersistFile;
begin
ComObject := CreateComObject(StringToGuid(CLSID_ShellLink));
PersistFile := IPersistFile(ComObject);
OleCheck(PersistFile.Load(FileName, STGM_READ));
ShellLink := IShellLinkW(ComObject);
SetLength(Result, MAX_PATH);
OleCheck(ShellLink.GetPath(Result, MAX_PATH, FindData, SLGP_RAWPATH));
SetLength(Result, Pos(#0, Result) - 1);
end;
procedure IterateShortcuts(Path: string);
var
FindRec: TFindRec;
ShortcutPath: string;
TargetPath: string;
begin
Path := AddBackslash(Path);
Log(Format(''Looking for .lnk in [%s]'', [Path]));
if FindFirst(Path + ''*.lnk'', FindRec) then
begin
try
repeat
ShortcutPath := Path + FindRec.Name;
TargetPath := GetLinkFileTarget(ShortcutPath);
Log(Format(''Target of shortcut [%s] is [%s]'', [ShortcutPath, TargetPath]));
until not FindNext(FindRec);
finally
FindClose(FindRec);
end;
end;
end;