1
votes

I am trying to enable Windows 10 toast notifications for our Win32 application. According to win docs (https://docs.microsoft.com/en-us/windows/uwp/design/shell/tiles-and-notifications/send-local-toast-desktop-cpp-wrl) I need to create a shortcut in the start menu with aumi-id and activator-clsid properties set. Win docs example uses WiX installer. Is there any way to set these properties in Inno Setup?

I tried the Pascal Scripting capabilities of Inno Setup and Windows COM components. I managed to set aumi-id but not the activator-clsid.

I got stuck on recreating WinAPI structs and unions which must be passed into IPropertyStore COM interface as an argument.

C code - this struct must be passed into the IPropertyStore method SetValue()

struct tagPROPVARIANT {
   VARTYPE vt;
   PROPVAR_PAD1 wReserved1;
   PROPVAR_PAD2 wReserved2;
   PROPVAR_PAD3 wReserved3;
   union {
   .
   .
   CLSID *puuid;
   .
   .
   }
}

Inno Pascal script - declaration of IPropertyStore interface and recreation of tagPROPVARIANT:

[code]
type
    IPropertyStore = interface(IUnknown)
        procedure dummy;
        procedure dummy2;
        procedure dummy3;
        function SetValue(var key: PROPERTYKEY; var pv: tagPROPVARIANT): HResult;
        procedure dummy4;
    end;
    tagPROPVARIANT = record
        vt: WORD;
        res1: WORD;
        res2: WORD;
        res3: WORD;
        // now somehow recreate union with 72 members where I only need one pointer (CLSID *puuid)
    end;
    // then I use IShellLink, IPropertyStore, IPersistFile
    // interfaces to create shortcut in the start menu, where IPropertyStore must be used to set properties that I need.
    // I managed to recreate IShellLink and IPersistFile because they do not use unions nor pointers

I was able to create start menu shortcut and set its AUMI like this:

[Icons]
Name: "{group}\{#APP_NAME}"; Filename: "{app}\{#EXE_NAME}"; \
  AppUserModelID: "MyCompany.MyApp"

But I think that CLSID can only be set in [Code] section using COM iterfaces.

Basically I am trying to rewrite this C++ code into Inno Setup script to make things cleaner.

ComPtr<IShellLinkW> shellLink;
CoCreateInstance(
  CLSID_ShellLink, nullptr, CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&shellLink));
shellLink->SetPath(exePath);
shellLink->SetArguments(L"");
shellLink->SetWorkingDirectory(exePath);

ComPtr<IPropertyStore> propertyStore;
shellLink.As(&propertyStore);
tagPROPVARIANT appIdPropVar;
InitPropVariantFromString(L"MyComp.MyApp", &appIdPropVar);
propertyStore->SetValue(PKEY_AppUserModel_ID, appIdPropVar);

// main problem
GUID clsid = __uuidof(NotificationActivator); 
tagPROPVARIANT CLSIDofMyToastHandler;
CLSIDofMyToastHandler.vt = VT_CLSID;
CLSIDofMyToastHandler.puuid = &clsid;

propertyStore->SetValue(PKEY_AppUserModel_ToastActivatorCLSID, CLSIDofMyToastHandler)
propertyStore->Commit();

ComPtr<IPersistFile> persistFile;
shellLink.As(&persistFile);
persistFile->Save(startMenuPath, TRUE);
PropVariantClear(&appIdPropVar);
1

1 Answers

1
votes

Inno Setup 6.1 now has the ability to set the CLSID by specifying the AppUserModelToastActivatorCLSID parameter in the Icons section.