问题背景
CMFCToolBar是可以停靠的工具条,当停靠时,不显示标题栏、标题以及关闭按钮,而当处于悬浮状态时,这些内容优又会显示出来,下面两张图分别是停靠和悬浮状态。
那如何实现悬浮状态下也不显示(隐藏/取消) 标题栏、标题、关闭按钮呢,这个问题还是有一些难度的。经过大量的网络搜索之后,虽然有找到明确的答案,但确实发现了一些灵感。通过反复的试验和修改,终于把这个问题解决了,主要代码整理如下。
解决方法
1、继承CPaneFrameWnd类
class CMyPaneFrameWnd : public CPaneFrameWnd
{
DECLARE_SERIAL(CMyPaneFrameWnd)
public:
CMyPaneFrameWnd();
virtual void RecalcCaptionHeight() override;
};
CMyPaneFrameWnd::CMyPaneFrameWnd()
{
m_nCaptionHeight = 2;
}
void CMyPaneFrameWnd::RecalcCaptionHeight()
{
m_nCaptionHeight = GetSystemMetrics(SM_CYSMCAPTION) + CMFCVisualManager::GetInstance()->GetCaptionButtonExtraBorder().cy;
m_nCaptionHeight = 2;
m_sizeMinSize.cx = m_sizeMinSize.cy = m_nCaptionHeight + 15;
}
添加CMyPaneFrameWnd 类来继承CPaneFrameWnd,CPaneFrameWnd就是当CMFCToolBar浮动时背后的那个对话框,我们看到的标题栏也就是他的。
核心代码是
m_nCaptionHeight = 2;
顾名思义,将标题栏的高度改为2,接近为零,几乎不绘制了。如果再小,工具条边框宽度会上下不对称,如果再大,标题栏又出来了。
2、继承CMFCToolBar类
class CMyMFCToolBar : public CMFCToolBar
{
public:
CMyMFCToolBar();
};
CMyMFCToolBar::CMyMFCToolBar()
{
SetMiniFrameRTC(RUNTIME_CLASS(CMyPaneFrameWnd));
SetPermament(TRUE);
}
其中,
SetMiniFrameRTC(RUNTIME_CLASS(CMyPaneFrameWnd));
用于告诉主框架,我要使用 CMyPaneFrameWnd作为工具条浮动时背后的窗口,从而可以控制标题栏的宽度。
SetPermament(TRUE);
用于设置不显示右上角的关闭按钮,其实是为了让CanBeClosed()虚函数返回false,从而不绘制关闭按钮。
3、不显示标题
CMyMFCToolBar m_toolbar;
m_toolbar.SetWindowText("");
将标题设置为空,否则虽然标题栏很矮,但仍然会显示一点文字,很不美观。
结论
如果隐藏CMFCToolBar工具条的标题栏,网上没有明确的解决方案。
通过查看MFC源码和反复验证,实现了该特性。继承CPaneFrameWnd类,重写其RecalcCaptionHeight虚函数,控制标题栏高度。继承CMFCToolBar类,隐藏关闭按钮并使用继承CPaneFrameWnd的子类。