|
【對比】Windows7系統下五種獲取系統默認字體代碼的效果 |
一派掌门 二十级 |
[1] hfontCaption = (HFONT)GetStockObject(DEFAULT_GUI_FONT);  運行結果: 文本框、單選框、複選框完全無法顯示。 按鈕和下拉菜單框的字顯示正常。
|
一派掌门 二十级 |
[2] hfontCaption = NULL;  運行結果: 文本框、單選框、複選框完全無法顯示。 按鈕和下拉菜單框的字的字體不正常。
|
|
一派掌门 二十级 |
[3] ncm.cbSize = sizeof(NONCLIENTMETRICS); SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, (UINT)NULL); hfontCaption = (HFONT)GetStockObject(DEFAULT_GUI_FONT); [4] ncm.cbSize = sizeof(NONCLIENTMETRICS) - sizeof(int); SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, (UINT)NULL); hfontCaption = (HFONT)GetStockObject(DEFAULT_GUI_FONT);  運行結果: 所有控件字體正常。(僅僅是加了獲取ncm的代碼,而變量ncm後面根本沒有用到)
|
|
一派掌门 二十级 |
[5] ncm.cbSize = sizeof(NONCLIENTMETRICS) - sizeof(int); SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, (UINT)NULL); hfontCaption = CreateFontIndirect(&ncm.lfCaptionFont);  運行結果: 所有控件字體正常。但和3、4字體不同。
|
|
一派掌门 二十级 |
至於XP系統,上述五段代碼編譯後運行,效果都是一樣的:  所有的控件都無法顯示! 就連楷體都無法識別!
|
|
一派掌门 二十级 |
楷體字的代碼: void InitFont(void) { LOGFONT logfont; ZeroMemory(&logfont, sizeof(logfont)); logfont.lfCharSet = GB2312_CHARSET; // 字符集 lstrcpy(logfont.lfFaceName, TEXT("楷體")); // 字體名稱 logfont.lfHeight = 48; // 字體大小 logfont.lfQuality = ANTIALIASED_QUALITY; // 字體品質 logfont.lfWeight = FW_BOLD; // 是否為粗體 //logfont.lfItalic = TRUE; // 是否為斜體 hfontCustom = CreateFontIndirect(&logfont); }
|
|
一派掌门 二十级 |
本人似乎明白了一點! 因為自己忘了在主函數裏加InitCommonControls();了! 所以XP系統下無法初始化XP風格的控件!
|
|
一派掌门 二十级 |
於是趕快加上這句話:
|
|
一派掌门 二十级 |
[1] hfontCaption = (HFONT)GetStockObject(DEFAULT_GUI_FONT);
|
|
一派掌门 二十级 |
[2] hfontCaption = NULL;
|
|
一派掌门 二十级 |
[3] ncm.cbSize = sizeof(NONCLIENTMETRICS); SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, (UINT)NULL); hfontCaption = (HFONT)GetStockObject(DEFAULT_GUI_FONT);  【說明】 ncm.cbSize = sizeof(NONCLIENTMETRICS); 這句話不兼容XP系統 必須減掉一個sizeof(int),SystemParametersInfo才能正常工作
|
|
一派掌门 二十级 |
[4] ncm.cbSize = sizeof(NONCLIENTMETRICS) - sizeof(int); SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, (UINT)NULL); hfontCaption = (HFONT)GetStockObject(DEFAULT_GUI_FONT);
|
|
一派掌门 二十级 |
[5] ncm.cbSize = sizeof(NONCLIENTMETRICS) - sizeof(int); SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, (UINT)NULL); hfontCaption = CreateFontIndirect(&ncm.lfCaptionFont);
|
|
一派掌门 二十级 |
[6] ncm.cbSize = sizeof(NONCLIENTMETRICS) - sizeof(int); SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, (UINT)NULL); ncm.lfCaptionFont.lfWeight = FW_NORMAL; // 取消粗體屬性 hfontCaption = CreateFontIndirect(&ncm.lfCaptionFont);
|
|
一派掌门 二十级 |
|
|
一派掌门 二十级 |
我覺得代碼4的字體在兩個系統下都很好。 代碼6的字體在Win7下很常見(例如記事本的字體對話框就是用的這個字體),但XP中很不常見。
|
|
一派掌门 二十级 |
XP系統下只讀文本框的黑色背景塊可以在消息處理函數的switch語句中添加如下代碼解決: case WM_CTLCOLORSTATIC: // 消除Static控件、滑塊控件和只讀文本框的背景顏色 return (LRESULT)GetStockObject(WHITE_BRUSH); 效果:
|
|
一派掌门 二十级 |
這幅截圖的字體是用的代碼4
|
|
一派掌门 二十级 |
我記得,Win7中文版下設置IP位址的對話框上的字體就是用的代碼4的字體
|
|
一派掌门 二十级 |
Windows XP中文版下只有「楷體_GB2312」字體,沒有「楷體」字體。 而Windows 7下只有「楷體」字體,沒有「楷體_GB2312」字體。(我用的是英文版的系統,中文版不知道是不是這樣) 所以上面的截圖中XP系統下楷體字沒有正常顯示。 但是把字體名稱改成「楷體_GB2312」後,XP下正常了,但Win7下卻反而不正常了 
|
|
一派掌门 二十级 |
|
|
一派掌门 二十级 |
【XP下楷體字不能顯示的解決方案】 int CALLBACK FontExistsProc(const LOGFONT *lpelfe, const TEXTMETRIC *lpntme, DWORD FontType, LPARAM lParam) { return 0; // 直接終止EnumFontFamiliesEx函數的運行 }
// 判斷字體是否存在的函數 BOOL FontExists(LPLOGFONT lpFont) { HDC hdc = GetDC(NULL); BOOL bResult = (EnumFontFamiliesEx(hdc, lpFont, FontExistsProc, (LPARAM)NULL, (DWORD)NULL) == 0); ReleaseDC(NULL, hdc); return bResult; }
// 創建自定義字體對象 void InitFont(void) { LOGFONT logfont; ZeroMemory(&logfont, sizeof(logfont)); logfont.lfCharSet = GB2312_CHARSET; // 字符集 lstrcpy(logfont.lfFaceName, TEXT("楷體")); // 字體名稱 logfont.lfHeight = 48; // 字體大小 logfont.lfQuality = ANTIALIASED_QUALITY; // 字體品質 logfont.lfWeight = FW_BOLD; // 是否為粗體 //logfont.lfItalic = TRUE; // 是否為斜體
// 如果字體不存在, 就更換名稱 if (!FontExists(&logfont)) lstrcpy(logfont.lfFaceName, TEXT("楷體_GB2312")); hfontCustom = CreateFontIndirect(&logfont); }
|
|
一派掌门 二十级 |
代碼[1]和代碼[4]在兩個系統下有着相似的效果。雖然hFontCaption都是賦的一樣的值,僅僅是多獲取了一下NCM,就會產生截然不同的效
果。據此可推測一定是SystemParametersInfo在獲取NCM的同時也影響了GetStockObject。
|
|