В Windows 8+ как вывести приложение Window Desktop на передний план, если приложение Metro на переднем плане через API?

Мое настольное приложение перехватывает некоторые горячие клавиши, например: CTRL+SHIFT+F12, при нажатии горячих клавиш окно моего настольного приложения выводится на передний план или остается на вершине. Но в Windows 8 или 8.1, когда он находится в стартовом окне Windows или приложение Metro работает на переднем плане, моя программа не смогла вернуться в режим рабочего стола и вывести мое окно на передний план. Я пробовал следующий API, SetFocus(hwnd); ShowWindow(hwnd, SW_SHOW); SetActiveWindow(HWND); SetForegroundWindow(HWND); SwitchToThisWindow(HWND);

Я даже пытаюсь использовать ShellExecute на "explorer.exe shell:::{3080F90D-D7AD-11D9-BD98-0000947B0257}", это не работает.

Я не уверен, как последняя версия Classic Shell ( http://www.classicshell.net/) смогла сделать это, когда я нажала клавишу SHIFT+WIN, она смогла переключиться из режима Metro обратно в режим рабочего стола и показать Classic Shell Окно.

Благодарю.

1 ответ

Решение

Вы должны иметь возможность установить идентификатор модели пользователя для своего приложения и использовать некоторые из более новых API, чтобы привлечь его внимание, когда пользователь находится в "Метро". Вот некоторые фрагменты кода на C++ для иллюстрации:

Где-то поделился:

const wchar_t MY_APP_USER_MODEL_ID[] = L"CompanyName.ProductSuite.AppName";

При запуске "настольного" приложения:

HRESULT hr = SetCurrentProcessExplicitAppUserModelID(const_cast<PWSTR>(MY_APP_USER_MODEL_ID));
// Check that SUCCEEDED(hr)

В вашем коде ввода в фокус:

IApplicationActivationManager* appMgr = nullptr;
if(SUCCEEDED(::CoCreateInstance(CLSID_ApplicationActivationManager, nullptr, CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&appMgr)))) {
  DWORD pid = 0;
  appMgr->ActivateApplication(MY_APP_USER_MODEL_ID, nullptr, AO_NOERRORUI, &pid);
  appMgr->Release();
}

Ваш ярлык:

Microsoft вводит и другие глупые правила, связанные со всем этим. Возможно, вам придется добавить некоторую дополнительную информацию в ярлык вашего приложения и закрепить его в меню "Пуск", чтобы все это работало (нет, серьезно). Если вы обнаружите, что это так, вот небольшой код для обновления вашего ярлыка и добавления идентификатора модели:

// Assuming you already have a valid IShellLink to work with
ComPtr<IPropertyStore> propertyStore;
if(SUCCEEDED(shellLink.As(&propertyStore))) {
  PROPVARIANT appIdPropVar;
  if(SUCCEEDED(::InitPropVariantFromString(MY_APP_USER_MODEL_ID, &appIdPropVar))) {
    if(SUCCEEDED(propertyStore->SetValue(PKEY_AppUserModel_ID, appIdPropVar)) &&
      SUCCEEDED(propertyStore->Commit()))
    {
     // go on to save your link/shortcut to disk...
    }
  }
}
Другие вопросы по тегам