Bug 1687562 - Part 2: Detect whether Firefox is pinned to the taskbar. r=mhowell
Differential Revision: https://phabricator.services.mozilla.com/D105365
This commit is contained in:
@@ -882,6 +882,98 @@ nsWindowsShellService::CheckPinCurrentAppToTaskbar() {
|
||||
return PinCurrentAppToTaskbarImpl(/* aCheckOnly */ true);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowsShellService::IsCurrentAppPinnedToTaskbar(/* out */ bool* aIsPinned) {
|
||||
*aIsPinned = false;
|
||||
|
||||
wchar_t exePath[MAXPATHLEN] = {};
|
||||
if (NS_WARN_IF(NS_FAILED(BinaryPath::GetLong(exePath)))) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
wchar_t folderChars[MAX_PATH] = {};
|
||||
HRESULT hr = SHGetFolderPathW(nullptr, CSIDL_APPDATA, nullptr,
|
||||
SHGFP_TYPE_CURRENT, folderChars);
|
||||
if (NS_WARN_IF(FAILED(hr))) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsAutoString folder;
|
||||
folder.Assign(folderChars);
|
||||
if (NS_WARN_IF(folder.IsEmpty())) {
|
||||
return NS_OK;
|
||||
}
|
||||
if (folder[folder.Length() - 1] != '\\') {
|
||||
folder.AppendLiteral("\\");
|
||||
}
|
||||
folder.AppendLiteral(
|
||||
"Microsoft\\Internet Explorer\\Quick Launch\\User Pinned\\TaskBar");
|
||||
nsAutoString pattern;
|
||||
pattern.Assign(folder);
|
||||
pattern.AppendLiteral("\\*.lnk");
|
||||
|
||||
WIN32_FIND_DATAW findData = {};
|
||||
HANDLE hFindFile = FindFirstFileW(pattern.get(), &findData);
|
||||
if (hFindFile == INVALID_HANDLE_VALUE) {
|
||||
Unused << NS_WARN_IF(GetLastError() != ERROR_FILE_NOT_FOUND);
|
||||
return NS_OK;
|
||||
}
|
||||
// Past this point we don't return until the end of the function,
|
||||
// when FindClose() is called.
|
||||
|
||||
// Check all shortcuts until a match is found
|
||||
do {
|
||||
nsAutoString fileName;
|
||||
fileName.Assign(folder);
|
||||
fileName.AppendLiteral("\\");
|
||||
fileName.Append(findData.cFileName);
|
||||
|
||||
// Create a shell link object for loading the shortcut
|
||||
RefPtr<IShellLinkW> link;
|
||||
HRESULT hr =
|
||||
CoCreateInstance(CLSID_ShellLink, nullptr, CLSCTX_INPROC_SERVER,
|
||||
IID_IShellLinkW, getter_AddRefs(link));
|
||||
if (NS_WARN_IF(FAILED(hr))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// Load
|
||||
RefPtr<IPersistFile> persist;
|
||||
hr = link->QueryInterface(IID_IPersistFile, getter_AddRefs(persist));
|
||||
if (NS_WARN_IF(FAILED(hr))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
hr = persist->Load(fileName.get(), STGM_READ);
|
||||
if (NS_WARN_IF(FAILED(hr))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// Note: AUMID is not checked, so a pin that does not group properly
|
||||
// will still count as long as the exe matches.
|
||||
|
||||
// Check the exe path
|
||||
static_assert(MAXPATHLEN == MAX_PATH);
|
||||
wchar_t storedExePath[MAX_PATH] = {};
|
||||
// With no flags GetPath gets a long path
|
||||
hr = link->GetPath(storedExePath, ArrayLength(storedExePath), nullptr, 0);
|
||||
if (FAILED(hr) || hr == S_FALSE) {
|
||||
continue;
|
||||
}
|
||||
// Case insensitive path comparison
|
||||
// NOTE: Because this compares the path directly, it is possible to
|
||||
// have a false negative mismatch.
|
||||
if (wcsnicmp(storedExePath, exePath, MAXPATHLEN) == 0) {
|
||||
*aIsPinned = true;
|
||||
break;
|
||||
}
|
||||
} while (FindNextFileW(hFindFile, &findData));
|
||||
|
||||
FindClose(hFindFile);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsWindowsShellService::nsWindowsShellService() {}
|
||||
|
||||
nsWindowsShellService::~nsWindowsShellService() {}
|
||||
|
||||
Reference in New Issue
Block a user