/* boolean initListBuild(in nsIMutableArray removedItems); */ NS_IMETHODIMP JumpListBuilder::InitListBuild(nsIMutableArray *removedItems, bool *_retval) { NS_ENSURE_ARG_POINTER(removedItems); *_retval = false; if (!mJumpListMgr) return NS_ERROR_NOT_AVAILABLE; if(sBuildingList) AbortListBuild(); IObjectArray *objArray; // The returned objArray of removed items are for manually removed items. // This does not return items which are removed because they were previously // part of the jump list but are no longer part of the jump list. if (SUCCEEDED(mJumpListMgr->BeginList(&mMaxItems, IID_PPV_ARGS(&objArray)))) { if (objArray) { TransferIObjectArrayToIMutableArray(objArray, removedItems); objArray->Release(); } RemoveIconCacheForItems(removedItems); sBuildingList = true; *_retval = true; return NS_OK; } return NS_OK; }
void QWinJumpListCategoryPrivate::loadRecents() { Q_ASSERT(jumpList); IApplicationDocumentLists *pDocList = 0; HRESULT hresult = CoCreateInstance(qCLSID_ApplicationDocumentLists, 0, CLSCTX_INPROC_SERVER, qIID_IApplicationDocumentLists, reinterpret_cast<void **>(&pDocList)); if (SUCCEEDED(hresult)) { if (!jumpList->identifier().isEmpty()) { wchar_t *id = qt_qstringToNullTerminated(jumpList->identifier()); hresult = pDocList->SetAppID(id); delete[] id; } if (SUCCEEDED(hresult)) { IObjectArray *array = 0; hresult = pDocList->GetList(type == QWinJumpListCategory::Recent ? ADLT_RECENT : ADLT_FREQUENT, 0, qIID_IObjectArray, reinterpret_cast<void **>(&array)); if (SUCCEEDED(hresult)) { items = QWinJumpListPrivate::fromComCollection(array); array->Release(); } } pDocList->Release(); } if (FAILED(hresult)) QWinJumpListPrivate::warning("loadRecents", hresult); }
// @pymethod |PyICustomDestinationList|AppendCategory|Adds a custom category to the jump list PyObject *PyICustomDestinationList::AppendCategory(PyObject *self, PyObject *args) { ICustomDestinationList *pICDL = GetI(self); if ( pICDL == NULL ) return NULL; TmpWCHAR Category; PyObject *obCategory, *obItems; IObjectArray *Items; // @pyparm str|Category||Display name of the category, can also be a dll and resource id for localization // @pyparm <o PyIObjectArray>|Items||Collection of IShellItem and/or IShellLink interfaces if ( !PyArg_ParseTuple(args, "OO:AppendCategory", &obCategory, &obItems)) return NULL; if (!PyWinObject_AsWCHAR(obCategory, &Category, FALSE)) return NULL; if (!PyCom_InterfaceFromPyInstanceOrObject(obItems, IID_IObjectArray, (void **)&Items, FALSE)) return NULL; HRESULT hr; PY_INTERFACE_PRECALL; hr = pICDL->AppendCategory(Category, Items); Items->Release(); PY_INTERFACE_POSTCALL; if ( FAILED(hr) ) return PyCom_BuildPyException(hr, pICDL, IID_ICustomDestinationList ); Py_INCREF(Py_None); return Py_None; }
/* boolean initListBuild(in nsIMutableArray removedItems); */ NS_IMETHODIMP JumpListBuilder::InitListBuild(nsIMutableArray *removedItems, bool *_retval) { NS_ENSURE_ARG_POINTER(removedItems); *_retval = false; if (!mJumpListMgr) return NS_ERROR_NOT_AVAILABLE; if(sBuildingList) AbortListBuild(); IObjectArray *objArray; if (SUCCEEDED(mJumpListMgr->BeginList(&mMaxItems, IID_PPV_ARGS(&objArray)))) { if (objArray) { TransferIObjectArrayToIMutableArray(objArray, removedItems); objArray->Release(); } RemoveIconCacheForItems(removedItems); sBuildingList = true; *_retval = true; return NS_OK; } return NS_OK; }
HRESULT SwitchVirtualDesktop(IVirtualDesktopManagerInternal *pDesktopManager, bool reverse) { IVirtualDesktop *pCurrentDesktop = nullptr; HRESULT hr = pDesktopManager->GetCurrentDesktop(&pCurrentDesktop); if (SUCCEEDED(hr)) { IVirtualDesktop *pNextDesktop = nullptr; AdjacentDesktop direction = reverse ? AdjacentDesktop::LeftDirection : AdjacentDesktop::RightDirection; hr = pDesktopManager->GetAdjacentDesktop(pCurrentDesktop, direction, &pNextDesktop); if (FAILED(hr)) { IObjectArray *pObjectArray = nullptr; hr = pDesktopManager->GetDesktops(&pObjectArray); if (SUCCEEDED(hr)) { int nextIndex = 0; if (reverse) { UINT count; hr = pObjectArray->GetCount(&count); if (SUCCEEDED(hr)) nextIndex = count - 1; } hr = pObjectArray->GetAt(nextIndex, __uuidof(IVirtualDesktop), (void**)&pNextDesktop); pObjectArray->Release(); } } if (SUCCEEDED(hr)) { hr = pDesktopManager->SwitchDesktop(pNextDesktop); pNextDesktop->Release(); } pCurrentDesktop->Release(); } return hr; }
// Builds a new custom Jump List for this application. void CreateJumpList() { // Create the custom Jump List object. ICustomDestinationList *pcdl; HRESULT hr = CoCreateInstance(CLSID_DestinationList, NULL, CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&pcdl)); if (SUCCEEDED(hr)) { // Custom Jump Lists follow a push model - applications are responsible for providing an updated // list anytime the contents should be changed. Lists are generated in a list-building // transaction that starts by calling BeginList. Until the list is committed, Windows will // display the previous version of the list, if available. // // The cMinSlots out parameter indicates the minimum number of items that the Jump List UI is // guaranteed to display. Applications can provide more items when building a custom Jump List, // but the extra items may not be displayed. The number is dependant upon a number of factors, // such as screen resolution and the "Number of recent items to display in Jump Lists" user setting. // See the MSDN documentation on BeginList for more information. // // The IObjectArray returned from BeginList contains a list of items the user has chosen to remove // from their Jump List. Applications must respect the user's removal of an item and not re-add any // item in the removed list during this list-building transaction. Applications should also clear any // persited usage-tracking data for any item in the removed list. If the user begins using a // previously removed item in the future, it may be re-added to the list. UINT cMinSlots; IObjectArray *poaRemoved; hr = pcdl->BeginList(&cMinSlots, IID_PPV_ARGS(&poaRemoved)); if (SUCCEEDED(hr)) { // Add content to the Jump List. hr = _AddCategoryToList(pcdl, poaRemoved); if (SUCCEEDED(hr)) { hr = _AddTasksToList(pcdl); if (SUCCEEDED(hr)) { // Commit the list-building transaction. hr = pcdl->CommitList(); } } poaRemoved->Release(); } pcdl->Release(); } }
void JumpListsManager::beginList() { if (m_destList) return; ICustomDestinationList *list; HRESULT res = CoCreateInstance(CLSID_DestinationList, 0, CLSCTX_INPROC_SERVER, IID_ICustomDestinationList, (void**)&list); if (FAILED(res)) { return; } UINT maxSlots; m_destList = list; m_destList->SetAppID(m_appId); m_destList->BeginList(&maxSlots, IID_IObjectArray, (void**)&m_destListContent); m_destListContent->Release(); IObjectArray *objArray; CoCreateInstance(CLSID_EnumerableObjectCollection, 0, CLSCTX_INPROC_SERVER, IID_IObjectArray, (void**)&objArray); objArray->QueryInterface(IID_IObjectCollection, (void**)&m_destListContent); objArray->Release(); }
INT GetCurrentDesktopIndex(UINT *count) { *count = 0; IObjectArray *pObjectArray = nullptr; IVirtualDesktop *pCurrentDesktop = nullptr; if (!InitCom()) { Log("InitCom failed"); return -1; } HRESULT hr = pDesktopManagerInternal->GetDesktops(&pObjectArray); if (FAILED(hr)) { Log("pDesktopManagerInternal->GetDesktops failed %x", hr); return -1; } hr = pObjectArray->GetCount(count); if (FAILED(hr)) { Log("pObjectArray->GetCount failed %x", hr); pObjectArray->Release(); return -1; } hr = pDesktopManagerInternal->GetCurrentDesktop(&pCurrentDesktop); if (FAILED(hr)) { Log("pDesktopManagerInternal->GetCurrentDesktop failed %x", hr); pObjectArray->Release(); return -1; } int index = -1; for (UINT i = 0; i < *count && i < MAXDESKTOPS && index == -1; ++i) { IVirtualDesktop *pDesktop = nullptr; if (FAILED(pObjectArray->GetAt(i, __uuidof(IVirtualDesktop), (void**)&pDesktop))) continue; if (pDesktop == pCurrentDesktop) { index = MOVETOMENU_START + i; } pDesktop->Release(); } pObjectArray->Release(); if (pCurrentDesktop != nullptr) { pCurrentDesktop->Release(); } return index; }
// @pymethod |PyIObjectCollection|AddFromArray|Adds a number of objects contained in an <o PyIObjectArray> collection PyObject *PyIObjectCollection::AddFromArray(PyObject *self, PyObject *args) { IObjectCollection *pIOC = GetI(self); if ( pIOC == NULL ) return NULL; IObjectArray *Source; PyObject *obSource; // @pyparm <o PyIObjectArray>|Source||Objects to be added to the collection if ( !PyArg_ParseTuple(args, "O:AddFromArray", &obSource)) return NULL; if (!PyCom_InterfaceFromPyObject(obSource, IID_IObjectArray, (void **)&Source, FALSE)) return NULL; HRESULT hr; PY_INTERFACE_PRECALL; hr = pIOC->AddFromArray(Source); Source->Release(); PY_INTERFACE_POSTCALL; if ( FAILED(hr) ) return PyCom_BuildPyException(hr, pIOC, IID_IObjectCollection ); Py_INCREF(Py_None); return Py_None; }
// @pymethod |PyICustomDestinationList|AddUserTasks|Sets the entries shown in the Tasks category PyObject *PyICustomDestinationList::AddUserTasks(PyObject *self, PyObject *args) { ICustomDestinationList *pICDL = GetI(self); if ( pICDL == NULL ) return NULL; PyObject *obItems; IObjectArray *Items; // @pyparm <o PyIObjectArray>|Items||Collection of <o PyIShellItem> and/or <o PyIShellLink> interfaces if ( !PyArg_ParseTuple(args, "O:AddUserTasks", &obItems)) return NULL; if (!PyCom_InterfaceFromPyInstanceOrObject(obItems, IID_IObjectArray, (void **)&Items, FALSE)) return NULL; HRESULT hr; PY_INTERFACE_PRECALL; hr = pICDL->AddUserTasks(Items); Items->Release(); PY_INTERFACE_POSTCALL; if ( FAILED(hr) ) return PyCom_BuildPyException(hr, pICDL, IID_ICustomDestinationList ); Py_INCREF(Py_None); return Py_None; }
/* readonly attribute short maxItems; */ NS_IMETHODIMP JumpListBuilder::GetMaxListItems(int16_t *aMaxItems) { if (!mJumpListMgr) return NS_ERROR_NOT_AVAILABLE; *aMaxItems = 0; if (sBuildingList) { *aMaxItems = mMaxItems; return NS_OK; } IObjectArray *objArray; if (SUCCEEDED(mJumpListMgr->BeginList(&mMaxItems, IID_PPV_ARGS(&objArray)))) { *aMaxItems = mMaxItems; if (objArray) objArray->Release(); mJumpListMgr->AbortList(); } return NS_OK; }
// Adds a custom category to the Jump List. Each item that should be in the category is added to // an ordered collection, and then the category is appended to the Jump List as a whole. HRESULT _AddCategoryToList(ICustomDestinationList *pcdl, IObjectArray *poaRemoved) { IObjectCollection *poc; HRESULT hr = CoCreateInstance(CLSID_EnumerableObjectCollection, NULL, CLSCTX_INPROC, IID_PPV_ARGS(&poc)); if (SUCCEEDED(hr)) { for (UINT i = 0; i < ARRAYSIZE(c_rgpszFiles); i++) { IShellItem *psi; if (SUCCEEDED(SHCreateItemInKnownFolder(FOLDERID_Documents, KF_FLAG_DEFAULT, c_rgpszFiles[i], IID_PPV_ARGS(&psi)))) { // Items listed in the removed list may not be re-added to the Jump List during this // list-building transaction. They should not be re-added to the Jump List until // the user has used the item again. The AppendCategory call below will fail if // an attempt to add an item in the removed list is made. if (!_IsItemInArray(psi, poaRemoved)) { poc->AddObject(psi); } psi->Release(); } } IObjectArray *poa; hr = poc->QueryInterface(IID_PPV_ARGS(&poa)); if (SUCCEEDED(hr)) { // Add the category to the Jump List. If there were more categories, they would appear // from top to bottom in the order they were appended. hr = pcdl->AppendCategory(L"Custom Category", poa); poa->Release(); } poc->Release(); } return hr; }
bool wxTaskBarJumpListImpl::CommitUpdate() { m_objectArray->Release(); return SUCCEEDED(m_destinationList->CommitList()); }
void CWin7::CreateCustomList() { #ifndef _NO_HISTORY if ( m_DestList ) { if ( m_List ) { HRESULT hr = CoCreateInstance(CLSID_EnumerableObjectCollection, NULL, CLSCTX_INPROC, IID_PPV_ARGS(&m_CustomList)); if (SUCCEEDED(hr)) { IShellLink * psl; unsigned int uiMax = CMainWindow::m_uiHistoryServers; if ( uiMax > 5 ) uiMax = 5; unsigned int ui = 0, ui1 = 0; CHistoryServer* pHist = 0; CServers* pServer = 0; char szBuf[ 128 ] = { 0 }; wchar_t wszBuf[ 128 ] = { 0 }; while ( ( ui < MAX_SERVERS ) && ( ui1 < uiMax ) ) { pHist = CMainWindow::m_lHistoryServers[ ui ]; if ( pHist ) { pServer = pHist->GetServer(); if ( pServer ) { sprintf( szBuf, "lu://connect/%s:%u", pServer->GetServerIP(), pServer->GetServerPort() ); MultiByteToWideChar( CP_ACP, 0, pServer->GetServerName(), -1, wszBuf, strlen( pServer->GetServerName() )+1 ); hr = _CreateShellLink( szBuf, wszBuf, "", &psl); if (SUCCEEDED(hr)) { hr = m_CustomList->AddObject(psl); psl->Release(); } ++ui1; } } ++ui; } if (SUCCEEDED(hr)) { IObjectArray * poa; hr = m_CustomList->QueryInterface(IID_PPV_ARGS(&poa)); if (SUCCEEDED(hr)) { // Add the tasks to the Jump List. Tasks always appear in the canonical "Tasks" // category that is displayed at the bottom of the Jump List, after all other // categories. hr = m_DestList->AppendCategory( L"Recent Servers", poa); poa->Release(); } } } else m_CustomList = 0; } } #endif }
void CWin7::CreateTasksList() { if ( m_DestList ) { if ( m_List ) { IObjectCollection *poc; HRESULT hr = CoCreateInstance(CLSID_EnumerableObjectCollection, NULL, CLSCTX_INPROC, IID_PPV_ARGS(&poc)); if (SUCCEEDED(hr)) { IShellLink * psl; hr = _CreateShellLink("/Tab-Favs", L"Favourites", "Open Favourites Tab", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } hr = _CreateShellLink("/Tab-Internet", L"Internet", "Open Internet Tab", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } hr = _CreateShellLink("/Tab-Official", L"Official", "Open Official Tab", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } #ifndef _NO_HISTORY hr = _CreateShellLink("/Tab-History", L"History", "Open History Tab", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } #endif #ifndef _NO_LAN_MODE hr = _CreateShellLink("/Tab-Lan", L"LAN", "Open LAN Tab", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } #endif if (SUCCEEDED(hr)) { hr = _CreateSeparatorLink(&psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } } hr = _CreateShellLink("/Win-Settings", L"Settings", "Open the Settings dialog", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } hr = _CreateShellLink("/Win-Help", L"Help", "Get Help & Support and the forums", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } if (SUCCEEDED(hr)) { IObjectArray * poa; hr = poc->QueryInterface(IID_PPV_ARGS(&poa)); if (SUCCEEDED(hr)) { // Add the tasks to the Jump List. Tasks always appear in the canonical "Tasks" // category that is displayed at the bottom of the Jump List, after all other // categories. hr = m_DestList->AddUserTasks(poa); poa->Release(); } } poc->Release(); } } } }
STDMETHODIMP CTaskbar7::CommitList() { // Do nothing on XP & Vista if (!m_isWindows7) return S_OK; UINT uMaxSlots = 20; IObjectArray *poaRemoved; if (!m_appID.empty()) m_pCustomDestinationList->SetAppID(m_appID.c_str()); HRESULT hr = m_pCustomDestinationList->BeginList(&uMaxSlots, IID_PPV_ARGS(&poaRemoved)); // Iterate over the lists to create map<wstring, vector<Destination>>::iterator iterator = destinations.begin(); while (iterator != destinations.end()) { // category wstring category = (*iterator).first; // Special case for known categories if (category.compare(DESTINATION_FREQUENT) == 0 || category.compare(DESTINATION_RECENT) == 0) { KNOWNDESTCATEGORY knownDestination; category.compare(DESTINATION_FREQUENT) == 0 ? knownDestination = KDC_FREQUENT : knownDestination = KDC_RECENT; HRESULT hr = m_pCustomDestinationList->AppendKnownCategory(knownDestination); if (FAILED(hr)) // Should not happen continue; iterator++; continue; } // Create a collection of IShellLink IObjectCollection *poc; hr = CoCreateInstance(CLSID_EnumerableObjectCollection, NULL, CLSCTX_INPROC, IID_PPV_ARGS(&poc)); if (FAILED(hr)) // Should not happen continue; vector<Destination>::iterator destinationIterator = (*iterator).second.begin(); while (destinationIterator != (*iterator).second.end()) { IShellLink *link; if ((*destinationIterator).type == Separator) hr = CreateSeparatorLink(&link); else hr = CreateShellLink(*destinationIterator, &link); if (SUCCEEDED(hr)) { poc->AddObject(link); link->Release(); } ++destinationIterator; } IObjectArray * poa; hr = poc->QueryInterface(IID_PPV_ARGS(&poa)); if (SUCCEEDED(hr)) { // Special treatment for tasks if (category.compare(DESTINATION_TASKS) == 0) hr = m_pCustomDestinationList->AddUserTasks(poa); else hr = m_pCustomDestinationList->AppendCategory(category.c_str(), poa); //int err = GetLastError(); poa->Release(); } poc->Release(); ++iterator; } // Commit the list! hr = m_pCustomDestinationList->CommitList(); SAFE_RELEASE(poaRemoved); destinations.clear(); return S_OK; }
void HandleSysCommand(WPARAM wParam, HWND hwnd) { if (wParam == MOVETOMENU_NEW) { // abort command, too many commands in a short period of time if (nLastCommand > GetTickCount64()) { return; } Log("Getting RootWindow of %X", hwnd); HWND rootHwnd = GetAncestor(hwnd, GA_ROOTOWNER); if (rootHwnd != NULL) { hwnd = rootHwnd; } Log("Moving %X to new", hwnd); IVirtualDesktop *pNewDesktop = nullptr; HRESULT hr = pDesktopManagerInternal->CreateDesktopW(&pNewDesktop); if (FAILED(hr)) { return; } GUID id; hr = pNewDesktop->GetID(&id); if (SUCCEEDED(hr)) { HWND focusHwnd = NULL; if (!bSwitchDesktopAfterMove) { focusHwnd = hwnd; do { focusHwnd = GetNextWindow(focusHwnd, GW_HWNDNEXT); } while (focusHwnd && EnumWindowsProc(focusHwnd, NULL)); } Log("pDesktopManager->MoveWindowToDesktop(%X, %X)", hwnd, id); hr = pDesktopManager->MoveWindowToDesktop(hwnd, id); if (SUCCEEDED(hr)) { if (bSwitchDesktopAfterMove) { pDesktopManagerInternal->SwitchDesktop(pNewDesktop); } else if (focusHwnd) { SetForegroundWindow(focusHwnd); } } else { Log("Error %d on moving %X to %X", hr, hwnd, id); } } pNewDesktop->Release(); nLastCommand = GetTickCount64() + COMMAND_TIMEOUT; } else if (wParam >= MOVETOMENU_START && wParam <= MOVETOMENU_LAST) { // abort command, too many commands in a short period of time if (nLastCommand > GetTickCount64()) { return; } Log("Getting RootWindow of %X", hwnd); HWND rootHwnd = GetAncestor(hwnd, GA_ROOTOWNER); if (rootHwnd != NULL) { hwnd = rootHwnd; } Log("Moving %X to %X", hwnd, wParam); IObjectArray *pObjectArray = nullptr; HRESULT hr = pDesktopManagerInternal->GetDesktops(&pObjectArray); if (FAILED(hr)) { Log("Failed to get desktops for %X", hwnd); return; } IVirtualDesktop *pDesktop = nullptr; if (SUCCEEDED(pObjectArray->GetAt((UINT)wParam - MOVETOMENU_START, __uuidof(IVirtualDesktop), (void**)&pDesktop))) { GUID id; hr = pDesktop->GetID(&id); if (SUCCEEDED(hr)) { HWND focusHwnd = NULL; if (!bSwitchDesktopAfterMove) { focusHwnd = hwnd; do { focusHwnd = GetNextWindow(focusHwnd, GW_HWNDNEXT); } while (focusHwnd && EnumWindowsProc(focusHwnd, NULL)); } Log("pDesktopManager->MoveWindowToDesktop(%X, %X)", hwnd, id); hr = pDesktopManager->MoveWindowToDesktop(hwnd, id); if (SUCCEEDED(hr)) { // If there are no windows delete the desktop if (bDeleteEmptyDesktops) { IVirtualDesktop *pCurrentDesktop = nullptr; hr = pDesktopManagerInternal->GetCurrentDesktop(&pCurrentDesktop); if (SUCCEEDED(hr)) { if (pCurrentDesktop != pDesktop) { if (EnumWindows((WNDENUMPROC)EnumWindowsProc, NULL) != FALSE) { Log("Removing Desktop"); pDesktopManagerInternal->RemoveDesktop(pCurrentDesktop, pDesktop); } } pCurrentDesktop->Release(); } } if (bSwitchDesktopAfterMove) { pDesktopManagerInternal->SwitchDesktop(pDesktop); } else if (focusHwnd != NULL) { SetForegroundWindow(focusHwnd); } } else { Log("Error %X on moving %X to %X", hr, hwnd, id); } } pDesktop->Release(); } pObjectArray->Release(); nLastCommand = GetTickCount64() + COMMAND_TIMEOUT; } else if (wParam == MOVETOMENU_LEFT) { UINT count; int index = GetCurrentDesktopIndex(&count); Log("Current Index is %d", index); Log("Current Count is %d", count); if (index == -1) return; if (index == MOVETOMENU_START) return; Log("Switch to %d", index - 1); HandleSysCommand(--index, hwnd); } else if (wParam == MOVETOMENU_RIGHT) { UINT count; int index = GetCurrentDesktopIndex(&count); Log("Current Index is %d", index); Log("Current Count is %d", count); if (index == -1) return; if (index == MOVETOMENU_LAST) return; if ((++index) <= (int)(count + MOVETOMENU_NEW)) { Log("Switch to %d", index); HandleSysCommand(index, hwnd); } else if (bCreateNewDesktopOnMove) { Log("Create new desktop"); HandleSysCommand(MOVETOMENU_NEW, hwnd); } } }
VOID AddMenu(HWND hwnd, HMENU menu) { if (bAddedMenu == true) return; HMENU systemMenu; if ((systemMenu = GetSystemMenu(hwnd, FALSE)) == NULL) { return; } if (menu != INVALID_HANDLE_VALUE && menu != systemMenu) { return; } bAddedMenu = true; if (!InitCom()) { return; } IObjectArray *pObjectArray = nullptr; IVirtualDesktop *pCurrentDesktop = nullptr; HRESULT hr = pDesktopManagerInternal->GetDesktops(&pObjectArray); if (FAILED(hr)) { return; } UINT count; hr = pObjectArray->GetCount(&count); if (FAILED(hr)) { pObjectArray->Release(); return; } hr = pDesktopManagerInternal->GetCurrentDesktop(&pCurrentDesktop); if (FAILED(hr)) { pCurrentDesktop = nullptr; } MENUITEMINFO MoveToItem = { 0 }; MoveToItem.cbSize = sizeof(MoveToItem); MoveToItem.fMask = MIIM_SUBMENU | MIIM_STATE | MIIM_ID | MIIM_STRING; Log("Add MoveToMenu"); MoveToItem.wID = MOVETOMENU_ID; MoveToItem.dwTypeData = TEXT("Move &To"); MoveToItem.hSubMenu = CreateMenu(); InsertMenuItem(systemMenu, SC_CLOSE, FALSE, &MoveToItem); for (UINT i = 0; i < count && i < MAXDESKTOPS; ++i) { IVirtualDesktop *pDesktop = nullptr; if (FAILED(pObjectArray->GetAt(i, __uuidof(IVirtualDesktop), (void**)&pDesktop))) continue; char desktopName[64] = { 0 }; sprintf_s(desktopName, sizeof(desktopName), "Desktop &%d", i + 1); MENUITEMINFO item = { 0 }; item.cbSize = sizeof(item); item.fMask = MIIM_CHECKMARKS | MIIM_STATE | MIIM_ID | MIIM_STRING; item.fState = (pDesktop == pCurrentDesktop) ? MFS_CHECKED : MFS_UNCHECKED; item.wID = MOVETOMENU_START + i; item.dwTypeData = desktopName; InsertMenuItem(MoveToItem.hSubMenu, -1, FALSE, &item); pDesktop->Release(); } // Create 'New Desktop' Item { MENUITEMINFO item = { 0 }; item.cbSize = sizeof(item); item.fMask = MIIM_ID | MIIM_STRING; item.fState = MFS_UNCHECKED; item.wID = MOVETOMENU_NEW; item.dwTypeData = TEXT("&New Desktop"); InsertMenuItem(MoveToItem.hSubMenu, -1, FALSE, &item); } pObjectArray->Release(); if (pCurrentDesktop != nullptr) { pCurrentDesktop->Release(); } }
void wxTaskBarJumpListImpl::LoadKnownCategory(const wxString& title) { IApplicationDocumentLists *docList = 0; HRESULT hr = CoCreateInstance ( wxCLSID_ApplicationDocumentLists, NULL, CLSCTX_INPROC_SERVER, wxIID_IApplicationDocumentLists, reinterpret_cast<void **>(&docList) ); if ( FAILED(hr) ) { wxLogApiError("CoCreateInstance(wxCLSID_ApplicationDocumentLists)", hr); return; } if ( !m_appID.empty() ) docList->SetAppID(m_appID.wc_str()); IObjectArray *array = NULL; wxASSERT_MSG( title == "Recent" || title == "Frequent", "Invalid title." ); hr = docList->GetList ( title == "Recent" ? ADLT_RECENT : ADLT_FREQUENT, 0, wxIID_IObjectArray, reinterpret_cast<void **>(&array) ); if ( FAILED(hr) ) { wxLogApiError("IApplicationDocumentLists::GetList", hr); return; } UINT count = 0; array->GetCount(&count); for (UINT i = 0; i < count; ++i) { IUnknown *collectionItem = NULL; hr = array->GetAt(i, wxIID_IUnknown, reinterpret_cast<void **>(&collectionItem)); if ( FAILED(hr) ) { wxLogApiError("IObjectArray::GetAt", hr); continue; } IShellLink *shellLink = NULL; IShellItem *shellItem = NULL; wxTaskBarJumpListItem* item = NULL; if ( SUCCEEDED(collectionItem->QueryInterface( wxIID_IShellLink, reinterpret_cast<void**>(&shellLink))) ) { item = GetItemFromIShellLink(shellLink); shellLink->Release(); } else if ( SUCCEEDED(collectionItem->QueryInterface( wxIID_IShellItem, reinterpret_cast<void**>(&shellItem))) ) { item = GetItemFromIShellItem(shellItem); shellItem->Release(); } else { wxLogError("Can not query interfaces: IShellLink or IShellItem."); } if ( item ) { if ( title == wxT("Frequent") ) m_frequent->Append(item); else m_recent->Append(item); } collectionItem->Release(); } array->Release(); docList->Release(); }
void HandleSysCommand(WPARAM wParam, HWND hwnd) { if (wParam == MOVETOMENU_NEW) { Log("Getting RootWindow of %X", hwnd); HWND rootHwnd = GetAncestor(hwnd, GA_ROOTOWNER); if (rootHwnd != NULL) { hwnd = rootHwnd; } Log("Moving %X to new", hwnd); IVirtualDesktop *pNewDesktop = nullptr; HRESULT hr = pDesktopManagerInternal->CreateDesktopW(&pNewDesktop); if (FAILED(hr)) { return; } GUID id; hr = pNewDesktop->GetID(&id); if (SUCCEEDED(hr)) { Log("pDesktopManager->MoveWindowToDesktop(%X, %X)", hwnd, id); hr = pDesktopManager->MoveWindowToDesktop(hwnd, id); if (SUCCEEDED(hr)) { if (bSwitchDesktopAfterMove) { pDesktopManagerInternal->SwitchDesktop(pNewDesktop); } } else { Log("Error %d on moving %X to %X", hr, hwnd, id); } } pNewDesktop->Release(); } else if (wParam >= MOVETOMENU_START && wParam <= MOVETOMENU_LAST) { Log("Getting RootWindow of %X", hwnd); HWND rootHwnd = GetAncestor(hwnd, GA_ROOTOWNER); if (rootHwnd != NULL) { hwnd = rootHwnd; } Log("Moving %X to %X", hwnd, wParam); IObjectArray *pObjectArray = nullptr; HRESULT hr = pDesktopManagerInternal->GetDesktops(&pObjectArray); if (FAILED(hr)) { Log("Failed to get desktops for %X", hwnd); return; } IVirtualDesktop *pDesktop = nullptr; if (SUCCEEDED(pObjectArray->GetAt((UINT)wParam - MOVETOMENU_START, __uuidof(IVirtualDesktop), (void**)&pDesktop))) { GUID id; hr = pDesktop->GetID(&id); if (SUCCEEDED(hr)) { Log("pDesktopManager->MoveWindowToDesktop(%X, %X)", hwnd, id); hr = pDesktopManager->MoveWindowToDesktop(hwnd, id); if (SUCCEEDED(hr)) { if (bSwitchDesktopAfterMove) { pDesktopManagerInternal->SwitchDesktop(pDesktop); } } else { Log("Error %X on moving %X to %X", hr, hwnd, id); } } pDesktop->Release(); } pObjectArray->Release(); } else if (wParam == MOVETOMENU_LEFT) { UINT count; int index = GetCurrentDesktopIndex(&count); Log("Current Index is %d", index); Log("Current Count is %d", count); if (index == -1) return; if (index == MOVETOMENU_START) return; Log("Switch to %d", index - 1); HandleSysCommand(--index, hwnd); } else if (wParam == MOVETOMENU_RIGHT) { UINT count; int index = GetCurrentDesktopIndex(&count); Log("Current Index is %d", index); Log("Current Count is %d", count); if (index == -1) return; if (index == MOVETOMENU_LAST) return; if ((++index) <= (int)(count + MOVETOMENU_NEW)) { Log("Switch to %d", index); HandleSysCommand(index, hwnd); } else { Log("Create new desktop"); HandleSysCommand(MOVETOMENU_NEW, hwnd); } } }
// Builds the collection of task items and adds them to the Task section of the Jump List. All tasks // should be added to the canonical "Tasks" category by calling ICustomDestinationList::AddUserTasks. HRESULT _AddTasksToList(ICustomDestinationList *pcdl) { IObjectCollection *poc; HRESULT hr = CoCreateInstance(CLSID_EnumerableObjectCollection, NULL, CLSCTX_INPROC, IID_PPV_ARGS(&poc)); if (SUCCEEDED(hr)) { IShellLink * psl; hr = _CreateShellLink(L"/Task1", L"Task 1", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } if (SUCCEEDED(hr)) { hr = _CreateShellLink(L"/Task2", L"Second Task", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } } if (SUCCEEDED(hr)) { hr = _CreateSeparatorLink(&psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } } if (SUCCEEDED(hr)) { hr = _CreateShellLink(L"/Task3", L"Task 3", &psl); if (SUCCEEDED(hr)) { hr = poc->AddObject(psl); psl->Release(); } } if (SUCCEEDED(hr)) { IObjectArray * poa; hr = poc->QueryInterface(IID_PPV_ARGS(&poa)); if (SUCCEEDED(hr)) { // Add the tasks to the Jump List. Tasks always appear in the canonical "Tasks" // category that is displayed at the bottom of the Jump List, after all other // categories. hr = pcdl->AddUserTasks(poa); poa->Release(); } } poc->Release(); } return hr; }