CCreditsCtrl - 高级关于框





5.00/5 (14投票s)
2001年1月8日

211310

4937
又一个功能齐全的控件,用于显示滚动字幕...
引言
我试了 Mark Findlay 的 滚动字幕对话框 和 Darren S. Gonzales 的 滚动屏幕字幕,坦白说我很失望。你根本无法进行格式化,除了在 Darren 的版本中选择四种预定义的文本标题中的一种,而且它不符合我对“高级”关于对话框的要求,因为你通常会想要添加一两个超链接,也许还有复活节彩蛋,谁知道呢 :)
而且,恕我直言,如果你不能做得更好,就说(甚至认为)某样东西很糟糕是很懦弱的,所以我开始编码了。
总之,这个控件允许你显示格式化的滚动文本和图像,这通常用于“关于”对话框以显示字幕。其功能包括:
- 扩展格式化功能;
- 支持内嵌资源位图;
- 你可以将文本和图像定义为超链接,这些超链接可以触发 `ShellExecute` 命令或用户定义的(回调)函数;
- 文本字体、大小、样式和颜色以及图像边框颜色,在鼠标指针移到超链接上时可以更改;
- 你可以制作花哨的所有者绘制的背景效果;
- 支持文本和位图透明;
- 如果内容总大小小于控件,则不滚动;
- 可以选择用户是否可以手动滚动内容;
- 抱歉,不支持 UNICODE(我没有办法测试它……我的 VC++ 版本(入门版 :( )甚至没有编译成 Unicode 模式所需的库……如果有人想这样做,欢迎!)
屏幕截图
样式...
...带动画、用户绘制背景的演示应用程序...
...好吧,这只是某些功能的一个演示。我可没说你的关于对话框必须看起来 *那么* 奇怪。
用法
要使用 Credits 控件,请按照这四个简单的步骤进行
- 首先,你需要为你的对话框或窗口类添加一个 `CCreditsCtrl` 类型的变量。不要忘记 `#include` 所需的头文件。
- 接下来,调用 `SetDataString` 或 `FormatDataString` 来 设置控件的内容。
- 如果你想自定义控件的行为和外观,请查看各种 类成员。通常,你会在调用 `Create` 之前调用/设置它们。
- 调用 `Create` 函数。
构造
使用以下函数之一来创建 `CCreditsCtrl` 控件
BOOL Create(DWORD dwExStyle, DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, UINT nID = 0, UINT nDefaultCursorID = 0, UINT nLinkCursorID = 0); BOOL Create(DWORD dwExStyle, DWORD dwStyle, UINT nPlaceholderID, CWnd* pParentWnd, UINT nID = 0, UINT nDefaultCursorID = 0, UINT nLinkCursorID = 0);
这些函数使用你指定的样式和位置来创建控件
- `dwExStyle` 定义扩展样式。
- `dwStyle` 定义控件的窗口样式。
- `pParentWnd` 是父窗口。
- `nID` 是控件的子 ID。
- `nDefaultCursorID` 是光标资源的 ID,或 0 表示默认。
- `nLinkCursorID` 是鼠标悬停在链接上时使用的光标资源的 ID。0 表示默认。
- `rect` 是控件的矩形。
- `nPlaceholderID` 是一个子窗口的 ID,其位置将用于创建窗口。这个在演示中使用。
Content
你使用以下四个函数之一来设置内容
CString SetDataString(LPCTSTR lpszNewString); CString SetDataString(UINT nStringResourceID); CString FormatDataString(LPCTSTR lpszFormat, ...); CString FormatDataString(UINT nFormatID, ...);
它们都返回旧的内容字符串。`SetDataString` 将内部数据字符串设置为 `lpszNewString` 的内容,或设置为 `nStringResourceID` 指定的资源字符串的内容。`FormatDataString` 对内部数据字符串进行与 `CString::Format` 对 `CString` 进行的操作相同的操作...
调用 `FormatDataString(... , ...)` 相当于以下代码片段
CString s; s.Format(... , ...); m_wndCreditsCtrl.SetDataString(s);
有关内容应该是什么样的信息,请参考 语言 部分。
背景
你有两种选择来绘制控件的背景
- 如果你只需要一个单色背景,你可以让 `CCreditsCtrl` 来绘制;你只需使用 `SetDefaultBkColor` 函数指定颜色。
- 另一个选择是通过指定一个负责绘制的(回调)函数来自己绘制背景。
该函数应该这样定义
static void DrawCreditsBackground(CDC *pDC, RECT rect, BOOL bAnimate, DWORD lParam);
- `pDC` 是指向要绘制的设备上下文的指针。这是一个内存设备上下文,所以你不需要执行比必要的更多的 `BitBlt` 操作。
- `rect` 是 Credits 控件的客户区矩形。
- `bAnimate` 是一个标志,表示背景是否应该被动画化……你不必遵守它,但可能会有意外的结果……但先尝试不处理它 :) ..或者查看演示以了解我如何使用它。
- `lParam` 可以是任何你想要的值;看下面。
假设 `DrawCreditsBackground` 是一个名为 `CAboutDlg` 的类的成员,并且 `m_wndCredits` 是一个 `CCreditsCtrl` 类型的变量,那么你将使用以下代码行来覆盖默认的背景绘制器
... m_wndCredits.m_pBackgroundPaint = CAboutDlg::DrawCreditsBackground; m_wndCredits.m_dwBackgroundPaintLParam = <code>dwAnything; ... m_wndCredits.Create(...);
...其中 `dwAnything` 是 `CAboutDlg::DrawCreditsBackground` 将作为 `lParam` 接收的值。
"语言"
好吧,这并非真正的“语言”……它是一些标记标签,用于告诉集成解析器,格式应该是什么样的。它可以被定义为自定义 HTML 和 XML 规则……这是你下一个头痛的完美组合 :)
好了,我们开始吧……首先是一些基本准则
- 换行符**不会**被去除,但是建议使用 `
` 和 `` 标签(见下文)……谁知道呢,也许会有下一个版本。
- 与 HTML 不同,空格会保留。
- 同样,与 HTML 不同,标签参数**必须**用单引号或双引号括起来:`
` 或 ` `。这很重要! - 在需要时,永远、永远不要忘记闭合标签!(见下方的参考)
- 解析器**不容错**……这意味着如果你犯了格式错误,它*可能会*导致你的程序出错……或者更糟!(然而,你仍然可以犯拼写错误 :))
现在来看标签
- font
这是最重要的一个。它允许你为文本和图像指定字体、大小、样式、颜色和背景,以及水平和垂直对齐。
它的用法如下
<font face='FontFace' size='n' style='[b|-b] | [i|-i] | [u|-u] | [s|-s]' color='n,n,n' background='red,green,blue' align='left|center|right' valign='top|middle|bottom'></font>
看起来很混乱?请继续阅读。
参数
face
指定字体名称
size
字体大小(以设备单位计)
样式
`b` 表示粗体,`i` 表示斜体,`u` 表示下划线,`s` 表示删除线。你可以组合使用它们。如果你在其中一个或多个字符前加上减号(-),它会移除相应的样式(在使用嵌套标签时)。
color
字体的颜色。值可以从 0 到 255。
background
文本背景颜色。格式与 `color` 相同。
align
当前行的水平对齐方式。只有在换行之前最后一个打开的 `font` 标签(指定了 `align` 参数)中的对齐方式才会被考虑:(所有这些文本都将居中 :))`this is a test
`valign
定义当前块在行上的对齐方式。例如,如果你有一行高 50 像素的位图和一些旁边高 12 个单位的文本,`valign` 会告诉解析器文本应该与位图的顶部、中部或底部对齐。希望你明白了,否则看看演示。
注释和技巧
- 此标签必须始终与闭合的 `` 标签一起使用。就像在 HTML 中一样,除了在这里,如果你忘了它,情况可能会变得更糟。
- 此标签可以嵌套,这意味着你可以将多个 `font` 标签放在一起。嵌套的 `font` 标签会保留父标签的属性,只更改指定的参数。
- 你还可以使用 `font` 标签来更改图像的对齐方式。
示例
<font face='arial' size="14" color='255,0,0' style='buis'> <font style='-i-s'>some text</font></font>
在这个例子中,“some text”将以 Arial 字体、大小 14、红色显示,并且会粗体和下划线。请注意,第二个标签移除了第一个标签定义的斜体和删除线样式。
- img
此标签允许你插入内嵌图像
<img href='#n' border='n' color='n,n,n'>
参数
src
此参数必须是哈希字符(#),后跟位图的数字资源 ID(以文本形式,见注释)。
border
指定边框宽度。可以是零。
color
边框颜色。可以是 `none` 表示透明。
注释和技巧
指定 `src` 参数的简单方法是做类似的事情
m_wndMyCreditsCtrl.FormatDataString("<img src='#%d'>",nBitmapID);
如果你在 `color` 参数中使用 `none`,`border` 的值将定义图像与周围元素之间的空间。
如果在 `src` 参数的井号后面的不是有效的位图资源 ID,你将得到一个断言!请在此处小心。
- a
此标签用于将文本块和图像定义为超链接...
<a href='TextToExecute | #[UserArgument#]CallbackFunction' face='FontFace' size='n' style='[b|-b] | [i|-i] | [u|-u] | [s|-s]' color='n,n,n' background='red,green,blue' align='left|center|right' valign='top|middle|bottom'></a>
参数
href
链接的操作。你有两个选择:你可以指定任何将作为 `ShellExecute` 命令参数传递的内容,或者你可以通过将第一个字符设置为井号来指定你自己的(回调)函数。
举个例子
class CAboutDlg : public CDialog { ... CCreditsCtrl m_wndCreditsCtrl; ... static void Test(LPCTSTR lpszArg) { AfxMessageBox(lpszArg); } ... afx_msg void OnInitDialog() { ... m_wndCreditsCtrl.FormatDataString( "<a href='#Hello World!#%d'>Click Me!</a>", (long)CAboutDlg::Test); m_wndCreditsCtrl.Create(...); ... } }
这将显示一个 `CCreditsCtrl`,其中包含一个文本为“Click Me!”的链接。如果你点击该文本,它会弹出一个消息框说“Hello World!”。请注意,如果你不指定参数(例如 ``),`lpszArg` 是 `NULL`。
注释和技巧
如果你在 `image` 标签中使用边框宽度为 1 或 2,并将边框颜色设置为 `none`,然后在 `
你可以通过将 `href` 设置为例如“http://www.yourwebpage.com”来打开浏览器窗口并使其导航到特定 URL。
你可以通过将 `href` 设置为 `mailto:foo@foo.org` 或 `mailto:foo@foo.org?SUBJECT=Hello World!` 来启动用户的邮件应用程序,如果你想要一个预设的主题。`` 标签!
- br
插入一个换行符。用法:`
`无评论。
哦,是的……只有一个评论:如果 `br` 标签前面的行是空的(没有文本或图像),换行符的高度将等于当前字体的高度。这对于 `
`(见下文)也同样适用。
- p
插入两个换行符。用法:`
`
空间的高度等于当前字体的高度。
- hspace
插入一个水平空间。
<hspace size='n'>
参数
size
空间的像素大小。
注释和技巧
空间不能是超链接。
- vspace
如果当前行不为空,则换行并在其后插入一个垂直空间。
<vspace size='n'>
参数
size
空间的像素大小
注释和技巧
空间(仍然)不能是超链接
就这些!!——没有更多标签了 :-D
如果你在此“语言”中遇到问题,请查看演示或 `CCreditsCtrl::Initialize()` 函数的源代码(不推荐)。如果你仍然无法解决问题或认为它是 bug,请在此处发布。
...尽情享受吧!!
杂项类成员
在这里,我将简要评论一些有用的公共类成员,以防你将来需要它们...
BOOL Create(...); |
有关详细说明,请参见 构造 |
CString SetDataString(...); |
设置控件的内容。 返回值:旧内容。 有关更多信息,请参见 内容。 |
CString FormatDataString(...); |
设置控件的内容。 返回值:旧内容 有关更多信息,请参见 内容。 |
CString GetDataString(); |
返回 `m_sData` 的值,其中包含控件的内容。 |
int HitTest(CPoint pt); |
返回光标下方的链接的索引。可与 `m_HotRects` 和 `m_HotRectActions` 一起使用。如果光标不在链接上,则返回 `-1`。 |
void SetDefaultBkColor(COLORREF crColor); |
设置默认背景绘制器将使用的背景颜色。如果你使用自己的背景绘制器,请不要调用此函数! |
void Initialize(); |
解析 `m_sData` 的内容并填充 `m_HotRects` 和 `m_HotRectActions`。如果你手动修改 `m_sData`(例如,不调用 `SetDataString` 或 `FormatDataString`),请调用此函数来更新你的更改。 |
void SetDefaultLinkCursor(); |
将链接光标设置为手形光标。我从 Chris Maunder 的 Hyperlink Control 中得到了这个——谢谢! |
-- 变量 -- | |
BOOL m_bCanScroll |
`TRUE` 表示用户应该被允许手动滚动控件内容。 |
int m_nCurBitmapOffset |
当前滚动偏移量……通常你不希望修改它。 |
int m_nTimerSpeed |
`SetTimer()` 中使用的速度。改变它以获得更慢/更快的滚动速度。默认值:40 |
HCURSOR m_hDefaultCursor |
默认光标的句柄。如果你不想在 `Create` 函数中使用资源 ID 指定它,可以在调用 `Create` 之后更改此变量。 |
HCURSOR m_hLinkCursor |
与 `m_hDefaultCursor` 相同,但仅在光标位于链接上时使用。 |
CString m_sData |
包含控件内容的字符串。应使用 `SetDataString` 或 `FormatDataString` 进行设置。 |
CArray<CRect,CRect&> m_HotRects |
一个数组,包含所有链接的矩形,相对于内容位图的顶部(而不是客户区矩形)。你不应修改其内容。 |
CArray<CString,CString&> m_HotRectActions |
包含所有链接操作的数组。索引与 `m_HotRects` 的索引匹配。不应修改。 |
COLORREF m_crInternalTransparentColor |
内部用作透明颜色的颜色。用此颜色绘制的任何内容都将是透明的(包括位图和文本)。你可以用它来为图像添加透明效果。 此外,这是字体初始化的颜色(除非你指定了文本背景),所以选择一种颜色,使其尽可能接近实际背景颜色(例如,如果你有一个深色背景,你可以选择 `black` 作为透明颜色,或者 `RGB(1,1,1)` 如果你不希望位图中黑色部分是透明的)。 |
void(*m_pBackgroundPaint)(CDC*,RECT,BOOL,DWORD) |
此变量保存用于背景绘制的(回调)函数的指针。 有关更多信息,请参考 背景 部分。 |
DWORD m_dwBackgroundPaintLParam |
存储在 `m_pBackgroundPaint` 中的函数将作为其第四个参数(`lParam`)接收的值 |
提示与技巧
- 下载演示!
- 阅读手册!
- 定制 `m_crInternalTransparentColor` 以满足你的需求。
- 大多数颜色参数(如果不是全部)都可以接受 `none` 或 `transparent` 的值,这将使它们……透明!
- 控件在创建后 `(m_nTimerSpeed*10)` 毫秒开始滚动。如果你想改变这个延迟,请在调用 `Create` 之前修改 `m_nTimerSpeed`,并在之后将其改回。例如,如果你想完全消除延迟,你可以这样做
... int nOldSpeed = m_wndCreditsCtrl.m_nTimerSpeed; m_wndCreditsCtrl.m_nTimerSpeed = 0; m_wndCreditsCtrl.Create(...); m_wndCreditsCtrl.m_nTimerSpeed = nOldSpeed; ...
- 在内容的末尾添加大量的 `
`...否则,内容的开头将紧跟在结尾之后显示,这通常不是你想要的。 - 计算机程序会按照你的指示去做,而不是按照你的意愿去做……这是明智的话 :)