CMFCToolBar双停靠面板Tooltip异常:如何禁用或单独处理?
问题描述
我创建了两组CMFCToolBar工具栏并完成停靠,代码如下:
m_wndToolBar1 创建代码
if (!m_wndToolBar1.CreateEx(this, TBSTYLE_FLAT, WS_CHILD | CBRS_TOOLTIPS | WS_VISIBLE | CBRS_TOP | CBRS_GRIPPER | CBRS_FLYBY | CBRS_SIZE_DYNAMIC) || !m_wndToolBar1.LoadToolBar(IDR_MAINFRAME_256)) return -1; m_wndToolBar1.EnableDocking(CBRS_ALIGN_ANY); EnableDocking(CBRS_ALIGN_ANY); DockPane(&m_wndToolBar1);
m_wndToolBar2 创建代码
if (!m_wndToolBar2.CreateEx(this, TBSTYLE_FLAT, WS_CHILD | WS_VISIBLE | CBRS_TOP | CBRS_GRIPPER | CBRS_TOOLTIPS | CBRS_FLYBY | CBRS_SIZE_DYNAMIC) || !m_wndToolBar2.LoadToolBar(IDR_MAINFRAME_256_3D)) return -1; m_wndToolBar2.EnableDocking(CBRS_ALIGN_ANY); EnableDocking(CBRS_ALIGN_ANY); DockPane(&m_wndToolBar2);
添加了消息映射:
ON_NOTIFY_EX(TTN_NEEDTEXT, 0, &CTunnelMainFrame::OnNeedText)
以及Tooltip处理函数:
BOOL CTunnelMainFrame::OnNeedText(UINT id, NMHDR* pNMHDR, LRESULT* pResult) { UINT_PTR nId = pNMHDR->idFrom - 1; CMFCToolBarButton* pBtnToolBar = m_wndToolBar1.GetButton(nId); if (pBtnToolBar) { TCHAR szBuff[64]; ::LoadString(AfxGetResourceHandle(), pBtnToolBar->m_nID, szBuff, sizeof(szBuff) / sizeof(TCHAR)); pTTT->lpszText = szBuff; pTTT->hinst = AfxGetResourceHandle(); } return TRUE; }
预期仅m_wndToolBar1显示Tooltip,但实际m_wndToolBar2也显示了m_wndToolBar1的STRINGTABLE文本。需要解决两个问题:
- 如何禁用
m_wndToolBar2的Tooltip? - 如何为
m_wndToolBar2设置独立的OnNeedText处理函数?
解决方案
一、禁用m_wndToolBar2的Tooltip
直接在创建m_wndToolBar2时移除CBRS_TOOLTIPS风格即可,无需修改消息映射:
修改后的m_wndToolBar2创建代码:
if (!m_wndToolBar2.CreateEx(this, TBSTYLE_FLAT, WS_CHILD | WS_VISIBLE | CBRS_TOP | CBRS_GRIPPER | CBRS_FLYBY | CBRS_SIZE_DYNAMIC) || !m_wndToolBar2.LoadToolBar(IDR_MAINFRAME_256_3D)) return -1; m_wndToolBar2.EnableDocking(CBRS_ALIGN_ANY); EnableDocking(CBRS_ALIGN_ANY); DockPane(&m_wndToolBar2);
如果需要在创建后动态禁用Tooltip,可调用:
m_wndToolBar2.SetPaneStyle(m_wndToolBar2.GetPaneStyle() & ~CBRS_TOOLTIPS);
二、为m_wndToolBar2设置独立的Tooltip处理
步骤1:为m_wndToolBar2设置唯一的Tooltip通知ID
在m_wndToolBar2创建完成后,获取其Tooltip控件并设置自定义通知ID:
// 创建m_wndToolBar2后添加 CToolTipCtrl* pToolTip2 = m_wndToolBar2.GetToolTipCtrl(); if (pToolTip2 != nullptr) { pToolTip2->SetOwner(this); // 设置与m_wndToolBar1不同的通知ID,比如1 pToolTip2->SetNotifyID(1); }
步骤2:添加多组消息映射
在消息映射中分别为两个工具栏的Tooltip通知添加处理函数:
ON_NOTIFY_EX(TTN_NEEDTEXT, 0, &CTunnelMainFrame::OnNeedTextToolBar1) ON_NOTIFY_EX(TTN_NEEDTEXT, 1, &CTunnelMainFrame::OnNeedTextToolBar2)
步骤3:编写独立的处理函数
分别为两个工具栏编写Tooltip文本加载逻辑,注意补上TOOLTIPTEXT的类型转换:
BOOL CTunnelMainFrame::OnNeedTextToolBar1(UINT id, NMHDR* pNMHDR, LRESULT* pResult) { TOOLTIPTEXT* pTTT = reinterpret_cast<TOOLTIPTEXT*>(pNMHDR); UINT_PTR nId = pNMHDR->idFrom - 1; CMFCToolBarButton* pBtnToolBar = m_wndToolBar1.GetButton(nId); if (pBtnToolBar) { TCHAR szBuff[64]; ::LoadString(AfxGetResourceHandle(), pBtnToolBar->m_nID, szBuff, sizeof(szBuff) / sizeof(TCHAR)); pTTT->lpszText = szBuff; pTTT->hinst = AfxGetResourceHandle(); } return TRUE; } BOOL CTunnelMainFrame::OnNeedTextToolBar2(UINT id, NMHDR* pNMHDR, LRESULT* pResult) { TOOLTIPTEXT* pTTT = reinterpret_cast<TOOLTIPTEXT*>(pNMHDR); UINT_PTR nId = pNMHDR->idFrom - 1; CMFCToolBarButton* pBtnToolBar = m_wndToolBar2.GetButton(nId); if (pBtnToolBar) { // 加载m_wndToolBar2对应的STRINGTABLE文本 TCHAR szBuff[64]; ::LoadString(AfxGetResourceHandle(), pBtnToolBar->m_nID, szBuff, sizeof(szBuff) / sizeof(TCHAR)); pTTT->lpszText = szBuff; pTTT->hinst = AfxGetResourceHandle(); } return TRUE; }
内容的提问来源于stack exchange,提问作者Kang Gilar
相关产品推荐
相关产品推荐

