问题
I'm working with a pair of programs, the "starter"(updater) and the "main" program. Where starter updates and launches main.
The program must behave nicely when pinned to the windows taskbar or start-menu. For example the user should be able to:
- Start "starter"
- Pin the running "main" to the task bar
- Close the program
- Starts the program using the pinned item on the taskbar.
Is it possible to make the pinned shortcut point to the "starter" and not the "main" directly?
I've tried to group them using a common ID, but that doesn't affect the path being pinned.
Right now I'm loading "main" within the process of "starter". This works as expected but have the problem that all updates are limited by the .NET version of "starter" which right now is getting quite old, .NET 3.5.
回答1:
Set the following properties for System.AppUserModel.
- System.AppUserModel.ID
- System.AppUserModel.RelaunchCommand
- System.AppUserModel.RelaunchDisplayNameResource
In C# you can use Windows-API-Code-Pack or its NuGet package WindowsAPICodePack-Shell.
Note that for unknown reason you can't easily change the path once it's set.
void SetTaskbarRelaunchCommand(Form form)
{
// WARNING, once RelaunchCommand has been set it can't be changed for any given appID.
// Workaround: delete all links here related to our app.
// %AppData%\Microsoft\Internet Explorer\Quick Launch\User Pinned\ImplicitAppShortcuts
// %AppData%\Microsoft\Internet Explorer\Quick Launch\User Pinned\TaskBar
// Source: https://stackoverflow.com/a/28388958/33236
var appID = "MyAppID";
var path = @"C:\Program Files (x86)\MyApp\Updater.exe");
var handle = form.Handle;
var propGuid = new Guid("{9F4C2855-9F79-4B39-A8D0-E1D42DE1D5F3}");
var ID = new PropertyKey(propGuid, 5); // System.AppUserModel.ID
var RelaunchCommand = new PropertyKey(propGuid, 2); // System.AppUserModel.RelaunchCommand
var RelaunchDisplayNameResource = new PropertyKey(propGuid, 4); // System.AppUserModel.RelaunchDisplayNameResource
WindowProperties.SetWindowProperty(handle, ID, appID);
WindowProperties.SetWindowProperty(handle, RelaunchCommand, path);
WindowProperties.SetWindowProperty(handle, RelaunchDisplayNameResource, "Label of My App");
}
You can also prevent pinning the app completely. As opposed to RelaunchCommand you can change this value any time.
void PreventPinning(IntPtr handle)
{
var appID = "MyAppNoPin";
var propGuid = new Guid("{9F4C2855-9F79-4B39-A8D0-E1D42DE1D5F3}");
var ID = new PropertyKey(propGuid, 5); // System.AppUserModel.ID
var PreventPinning = new PropertyKey(propGuid, 9); // System.AppUserModel.PreventPinning
//Important: Set PreventPinning before ID
WindowProperties.SetWindowProperty(handle, PreventPinning, "True");
WindowProperties.SetWindowProperty(handle, ID, appID);
}
回答2:
I wasn't successful in setting the RelaunchCommand and the RelaunchDisplayNameResource on the newest Windows 10 update. But i have found a solution to set that the Launcher is pinned to the taskbar using your first approach, setting a common AppID: Pinning to the taskbar a "chained process"
来源:https://stackoverflow.com/questions/55550770/control-path-to-pinned-exe-in-windows-taskbar-and-start-menu