IContextMenu::QueryContextMenu 返回不相关的菜单
IContextMenu::QueryContextMenu return not relevant menu
网络连接快捷方式(以太网、Wi-Fi 等)根据连接状态(已连接/断开连接)具有不同的上下文菜单。我使用以下代码(Delphi)来检索和显示此菜单。
var pidl, child: PItemIdList;
pFolder: IShellFolder;
pMenu: IContextMenu;
menu: HMENU;
begin
SHParseDisplayName(PChar('%USERPROFILE%Desktopeth0.lnk'), nil, pidl, 0, PDWORD(nil)^);
SHBindToParent(pidl, IID_IShellFolder, Pointer(pFolder), child);
CoTaskMemFree(pidl);
pFolder.GetUIObjectOf(0, 1, child, IID_IContextMenu, nil, pMenu);
menu := CreatePopupMenu;
pMenu.QueryContextMenu(menu, 0, 0, $7fff, CMF_NORMAL);
TrackPopupMenuEx(menu, TPM_LEFTBUTTON, 0, 0, Handle, nil);
DestroyMenu(menu);
end;
但是在更改连接状态后,我不断获得旧菜单。重新启动应用程序后,我有时会得到正确的菜单,但是,大多数时候我没有。
为什么会发生这种情况以及如何解决?
操作系统:32 位和 64 位 Windows 7/8/10
C++代码:
PIDLIST_ABSOLUTE pidl;
if SUCCEEDED(SHParseDisplayName(L"%USERPROFILE%\Desktop\eth0.lnk", NULL, &pidl, 0, NULL))
{
PCUITEMID_CHILD child;
CComQIPtr<IShellFolder> pFolder;
if SUCCEEDED(SHBindToParent(pidl, IID_IShellFolder, (void**)&pFolder, &child))
{
CComQIPtr<IContextMenu> pMenu;
if SUCCEEDED(pFolder->GetUIObjectOf(0, 1, &child, IID_IContextMenu, NULL, (void**)&pMenu))
{
HMENU menu = CreatePopupMenu();
if SUCCEEDED(pMenu->QueryContextMenu(menu, 0, 0, 0x7fff, CMF_NORMAL))
TrackPopupMenuEx(menu, TPM_LEFTBUTTON, 0, 0, hWnd, NULL);
DestroyMenu(menu);
}
}
CoTaskMemFree(pidl);
}
加:也许是Windows错误。来自互联网和文件管理器(如资源管理器(XYPlorer,Explorer++等)的任何示例都有相同的问题。现在我在Windows 10资源管理器上看到了同样的问题。如果您通过拖放从桌面上的"控制面板\所有控制面板项\网络和共享中心\更改适配器设置\adapter_name"创建网络连接的快捷方式,您将看到相同的问题。
我认为该问题与正在缓存的网络连接快捷方式的上下文菜单信息有关,当您更改连接状态时,窗口可能不会自动刷新缓存的信息。
您可能需要通过调用函数 SHChangeNotify
来手动刷新缓存,它将通知系统应用程序已执行的事件并触发缓存刷新。
这是德尔福的一个例子:
begin
// ... your code here ...
SHChangeNotify(SHCNE_ASSOCCHANGED, SHCNF_IDLIST, nil, nil);
end;
在C++:
SHChangeNotify(SHCNE_ASSOCCHANGED, SHCNF_IDLIST, NULL, NULL);
若要确保上下文菜单是最新的,请尝试在显示之前调用SHChangeNotify
。
相关文章:
- 如果条件不相关,我应该更喜欢两个 if 语句而不是 if-else 语句吗?
- 虚假唤醒是否会解锁所有等待线程,甚至是不相关的线程?
- std::less是否应该允许在编译时比较不相关的指针?
- 0 的 2D 数组 不相关循环的破坏逻辑 - C++
- 为什么数组到指针的输出不相关
- 如何使用模板元编程在自由函数C++链接两个不相关的类
- 为什么在使用不相关的宏时会阻止 while 循环结束?
- 将积分类型的数组作为另一个不相关的积分类型的阵列进行访问的安全且符合标准的方法
- 强制转换为不相关的引用类型是否违反严格的别名规则?
- 为什么我的代码在添加不相关的代码行后工作方式不同?
- 尝试编写函数尝试从字符串中提取数字,但它返回不相关的数字
- VSCODE C++ IntelliSense为替代定义找到不相关的Yocto Sysroots
- 试图调节我的 do-while 以停止在终端中退出程序.菜单不会根据需要循环使用当前语句
- 创建小部件的GUI菜单不会出现在QT创建者中
- 什么保证两个不相关的线程中的不同不相关对象没有(不可避免的)争用条件?
- 对类型 'A *' 的非常量左值引用不能绑定到不相关的类型 'std::shared_ptr<A>' 的值
- 对话框菜单不响应单击
- 将函数从控制台应用程序移动到共享库项目似乎会带来不相关的编译错误
- 将不相关类型的对象reinterpret_cast空类是未定义的行为吗?
- IContextMenu::QueryContextMenu 返回不相关的菜单