如果我们自己写程序的时候检测到一个错误的时候,可能希望向用户显示错误的文本表述,而不是一个干巴巴的错误代码windows提供了一个函数可以将错误代码转换成错误文本描述,这个函数是FormatMessage。
TheFormatMessage function formats a message string. The function requires a message definition as input. The message definition can come from a buffer passed into the function. It can come from a message table resource in an already-loaded module. Or the caller can ask the function to search the system's message table resource(s) for the message definition. The function finds the message definition in a message table resource based on a message identifier and a language identifier. The function copies the formatted message text to an output buffer, processing any embedded insert sequences if requested.
[cpp] view plain copy print ?
- DWORD FormatMessage(
- DWORD dwFlags,
- LPCVOID lpSource,
- DWORD dwMessageId,
- DWORD dwLanguageId,
- LPTSTR lpBuffer,
- DWORD nSize,
- va_list *Arguments
- );
DWORD FormatMessage(
DWORD dwFlags, // source and processing options
LPCVOID lpSource, // message source
DWORD dwMessageId, // message identifier
DWORD dwLanguageId, // language identifier
LPTSTR lpBuffer, // message buffer
DWORD nSize, // maximum size of message buffer
va_list *Arguments // array of message inserts
);
参数说明:
dwFlags:
标志位,决定如何说明lpSource参数,dwFlags的低位制定如何处理换行功能在输出缓冲区,也决定最大宽度的格式化输出行。
可选参数:
标志
|
标志说明
|
FORMAT_MESSAGE_ALLOCATE_BUFFER
0x00000100
|
函数会分配一个足够大的缓冲区保存格式化消息,并且通过lpBuffer指向该
地址。
|
FORMAT_MESSAGE_ARGUMENT_ARRAY
0x00002000
|
Arguments参数不是指向va_list结构体,但是是一个指向保存参数的数据。
|
FORMAT_MESSAGE_FROM_HMODULE
0x00000800
|
lpSource参数是需要去搜索的一个包含消息表的模块线程。如果lpSource
是NULL,当前进程的应用图像会被搜索,这个标志不能同
FORMAT_ME
SSAGE_FROM_STRING使用。
|
FORMAT_MESSAGE_FROM_STRING
0x00000400
|
lpSource参数是一个指向以NULL结尾的字符串,字符串包含一个消息定义,
这个消息定义可以包含插入序列。此标志最好不要和
FORMAT_MESSAGE_F
ROM_HMODULE或者FORMAT_MESSAGE_FROM_SYSTEM使用
|
FORMAT_MESSAGE_FROM_SYSTEM
0x00001000
|
函数会为了请求的信息而搜索系统的消息表资源。如果标志同时也指定了
FORMAT_MESSAGE_FROM_HMODULE,那么函数会先在lpSource指定
的模块中搜索请求的消息,如果搜索不到,就去搜索系统消息表资源。此
标志不能与
FORMAT_MESSAGE_FROM_STRING使用。
|
FORMAT_MESSAGE_IGNORE_INSERTS
0x00000200
|
消息定义中的插入序列会被一直忽略和跳过直到输出缓冲区不改变,并且
Arguments会被忽略。
|
lpSource:
根据dwFlags标志而定。
dwMessageId:
请求的消息的标识符。当dwFlags标志为
FORMAT_MESSAGE_FROM_STRING时会被忽略。
dwLanguageId:
请求的消息的语言标识符。
nSize:
如果
FORMAT_MESSAGE_ALLOCATE_BUFFER标志没有被指定,这个参数必须指定为输出缓冲区的大小,
如果指定,这个参数指定为分配给输出缓冲区的最小数。
Arguments:
保存格式化信息中的插入值的一个数组。
返回值:
如果函数调用成功,返回输出缓冲区的大小,除最后一个空字符。如果失败侧返回0。
资源文件:
[plain] view plain copy print ?
- //
- // Dialog
- //
- IDD_DIALOG1 DIALOGEX 0, 0, 177, 83
- STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU
- EXSTYLE WS_EX_APPWINDOW
- CAPTION "Dialog"
- FONT 8, "MS Shell Dlg", 400, 0, 0x1
- BEGIN
- DEFPUSHBUTTON "确定",IDOK,114,11,50,14
- LTEXT "Error:",IDC_STATIC,10,12,20,14
- EDITTEXT IDC_ERRORCODE,38,11,40,14,ES_AUTOHSCROLL
- EDITTEXT IDC_ERRORTEXT,10,28,156,45,ES_MULTILINE | ES_AUTOHSCROLL
- END
//
// Dialog
//
IDD_DIALOG1 DIALOGEX 0, 0, 177, 83
STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU
EXSTYLE WS_EX_APPWINDOW
CAPTION "Dialog"
FONT 8, "MS Shell Dlg", 400, 0, 0x1
BEGIN
DEFPUSHBUTTON "确定",IDOK,114,11,50,14
LTEXT "Error:",IDC_STATIC,10,12,20,14
EDITTEXT IDC_ERRORCODE,38,11,40,14,ES_AUTOHSCROLL
EDITTEXT IDC_ERRORTEXT,10,28,156,45,ES_MULTILINE | ES_AUTOHSCROLL
END
代码:
[cpp] view plain copy print ?
- #include <windows.h>
- #include "resource.h"
- LRESULT CALLBACK DialogProc(HWND ,UINT,WPARAM,LPARAM) ;
- void OnInitDialog(HWND hDlg);
- void OnOK(HWND hDlg);
- int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd)
- {
- MSG msg;
- HWND hwnd = CreateDialog(hInstance, MAKEINTRESOURCE(IDD_DIALOG1), NULL, (DLGPROC)DialogProc);
- ShowWindow(hwnd, SW_SHOW);
- UpdateWindow(hwnd);
- while(GetMessage(&msg, NULL, 0, 0))
- {
- if( !IsDialogMessage( hwnd, &msg ) )
- {
- TranslateMessage(&msg);
- DispatchMessage(&msg);
- }
- }
- return msg.wParam;
- }
- LRESULT CALLBACK DialogProc(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam)
- {
- switch(uMsg)
- {
- case WM_INITDIALOG:
- OnInitDialog(hWnd);
- SetWindowPos(hWnd,NULL,500,200,0,0,SWP_NOSIZE);
- return TRUE;
- case WM_COMMAND:
- if(LOWORD(wParam) == IDOK)
- {
- OnOK(hWnd);
- return TRUE;
- }
- if(LOWORD(wParam) == IDCANCEL)
- {
- PostQuitMessage(0);
- return TRUE;
- }
- break;
- case WM_DESTROY:
- PostQuitMessage(0);
- break;
- }
- return FALSE;
- }
- void OnInitDialog(HWND hDlg)
- {
- SendMessage(hDlg, WM_SETICON, ICON_SMALL, (LPARAM)LoadIcon(NULL,
- MAKEINTRESOURCE(IDI_ICON1)));
- SendMessage(hDlg, WM_SETICON, ICON_BIG, (LPARAM)LoadIcon(NULL,
- MAKEINTRESOURCE(IDI_ICON1)));
- SetDlgItemInt(hDlg, IDC_ERRORCODE, 0, FALSE);
- }
- void OnOK(HWND hDlg)
- {
- DWORD dwError = GetDlgItemInt(hDlg,IDC_ERRORCODE,NULL, FALSE);
- LPVOID lpMsgBuf;
- FormatMessage(
- FORMAT_MESSAGE_ALLOCATE_BUFFER |
- FORMAT_MESSAGE_FROM_SYSTEM |
- FORMAT_MESSAGE_IGNORE_INSERTS,
- NULL,
- dwError,
- MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
- (PTSTR)&lpMsgBuf, 0, NULL );
- SetDlgItemText(hDlg,IDC_ERRORTEXT,(PCTSTR)lpMsgBuf);
- LocalFree(lpMsgBuf);
- }