由于关于 CDateTimeCtrl 的用法,在MSDN 和百度、谷歌上已经很多很多,这里就不在啰嗦 。
因为CDateTimeCtrl本身没有border 属性,所以不能像 其他 控件那样直接,勾选掉,就能去掉边框。
而且重载的时候问题多多。
1. 如果想要改变 CDateTimeCtrl 的边框
介绍一个函数,
virtual BOOL ModifyStyleEx( DWORD dwRemove, DWORD dwAdd, UINT nFlags );
第一个参数是移除的属性,第二参数是增加的属性。
最后一个是标志:
WS_BORDER Creates a window that has a border.创建一个有边界的窗口。
WS_EX_CLIENTEDGE Specifies that a window has a 3D look — that is, a border with a sunken edge.指定窗口具有3D外观,也即是一个下沉的边缘
MFC 创建 CDateTimeCtrl 的时候给与 其 的是 WS_EX_CLIENTEDGE 属性,所以这里需要去掉 WS_EX_CLIENTEDGE 属性才能 去掉边框 。
调用函数 :
ModifyStyleEx (WS_EX_CLIENTEDGE, 0, SWP_DRAWFRAME);
这里还有一个知识点 , 很多人在调用 这个函数之后,窗口风格并没有改变,而必须在之后调用 setwindowpos 才行,那是因为你没有 为 ModifyStyleEx 的第三个参数添加 风格。这里 添加的 是 SWP_DRAWFRAME 风格。
一边 调用过次函数之后,就能去掉 CDateTimeCtrl 的3D边框 。
2. 改变之后,很多人发现,CDateTimeCtrl 的背景色 并不能 于自己当前的 窗口 格调一致 。于是想要修改 其 背景色。但是 CDateTimeCtrl 想要修改其背景色,就必须要进行重载了,在主函数的 OnCtlColor 中 和 PreTranslateMessage 中并不能修改其 颜色。
重载 需要注意的 :
如果只是修改背景色,那么只需要重载 CDateTimeCtrl 函数的 OnEraseBkgnd 函数,其余的不动。也就是说,整个重载函数中,只有
afx_msg BOOL OnEraseBkgnd(CDC* pDC); 和 构造 、析构 函数而已。
千万不要在 OnCtlColor中 进行 setbkcolour settextcolour 类似这样的操作,虽然 这样也能修改背景色,但是你会发现如果改变日期,字体就会重叠,而且鼠标双击会有阴影,这个时候进行强制刷新也没有实质的效果。
千万不要重载 OnPaint 函数,如果你只想修改其背景色的话 。 如果重载,那么你就要实现一下,CDateTimeCtrl 日期 的 显示。
修改 背景色 的代码 :
CBrush bBrush(RGB(255, 255, 255));
CBrush* pOldBrush = pDC->SelectObject(&bBrush);
CRect rect;
pDC->GetClipBox(&rect);
pDC->PatBlt(rect.left, rect.top, rect.Width(), rect.Height(), PATCOPY);
pDC->SelectObject(pOldBrush);
注意一下,下面三个函数的区别。
GetClipBox 该函数得到一个能够完整包含当前可见区域的最小矩形的大小。
GetWindowRect获取窗口的整个区域,包括菜单,标题栏,边界。
GetClientRect获取的窗口的客户区,这里是在用于给用户作图用的。
这样应该就能修改 CDateTimeCtrl 的背景色。
3. 其实 很多人 在去掉边框之后 发现 很丑 ,和整个窗口 并不能 想融合,这个时候 就需要 在 整个 CDateTimeCtrl 控件之外 添加一个边框 ,当然 添加边框,就直接加载一张图片 就行了 ,这个就比较容易了,图片中间全透明,可以使用 GDI+ 的 BMP 图片进行加载,也可以使用 ATL 里面的 CImage 类 进行加载,方法太多,就不说了,实现起来也比较容易,这里搞出来一张,我做出来的效果,大家做个参考 。