web-dev-qa-db-ja.com

MFCダイアログコントロールのデフォルトのフォントはどれですか?

下の図(拡大されているので、違いがよくわかります)は、動的に作成された編集コントロール(上の2つの例)とダイアログエディターから作成された編集コントロール(下の例)のフォントの違いを示しています。動的に作成されたCEditコントロールのフォントをデフォルト(下の例)のようにするにはどうすればよいですか?

enter image description here

次のようなCEditコントロールを作成しました。

obj->CreateEx(WS_EX_CLIENTEDGE, _T("EDIT"), _T(""),
              WS_CHILD | WS_VISIBLE | WS_TABSTOP,
              rect.left, rect.top, rect.Width(), rect.Height(),
              GetSafeHwnd(), reinterpret_cast<HMENU>(mId));

obj->SetFont(&mFont); // mFont was created in the Dialog Constructor
                      // with mFont.CreatePointFont(80, _T("MS Shell Dlg"));

ご協力いただきありがとうございます!

40
Christian Ammer

最初の例は、 GetStockObject function で取得したシステムフォント(SYSTEM_FONT)を使用しています。これは、Windowsの時代から使用されていないビットマップフォントです。 3. Raymond Chenのブログ 、および Michael Kaplanのブログ で詳細情報を利用できます。

2番目の例では、 "MS Shell Dlg"フォント を使用しています。これは、実際にはWindows 95および98の時代のUIフォントである「Microsoft Sans Serif」または「MS Sans Serif」と呼ばれるフォントにマッピングされます。これはDEFAULT_GUI_FONTとも呼ばれます。名前はありますが、残念ながら、もはや正確ではありません。

Windows 2000以降(XPでも継続)、TahomaがデフォルトのUIフォントとして使用されました。これが3番目の例で見られるものです:Tahoma 8 pt。残念ながら、これらのオペレーティングシステム上でも、「MS Shell Dlg」はTahomaを返しません。MSSans Serifを返します。

したがって、TahomaをGUIフォントとして単純に指定することはできますが、Tahomaがインストールまたはサポートされていない古いバージョンのOSや、外国語バージョンのオペレーティングシステムでは破損するため、実際には正しくありません。必然的に別のフォントが使用される場合。代わりに、DS_SHELLFONTフラグを指定することになっています。これは Raymondがここで説明しています です。

そして、Windows Vistaがリリースされるまで、すべてがうまくいきました。また、Windows Vistaでは、Microsoftの力により、Tahomaは少し歯が長くなり、Windowsには 別のUIフォントのアップグレード が必要であると判断されました。社内で Segoe UI と呼ばれる独自の特別なフォントを開発しました。そして、特別な少しひねりを加えて、デフォルトのサイズは、OSのすべての以前のバージョンで使用されていた8 ptではなく、9 ptになりました。 、フォントフェイスに関係なく。そして、おそらく「MS Shell Dlg」、「MS Shell Dlg2」、またはDS_SHELLFONT(または3つすべて)のいずれかが、この新しいおかしなSegoeを取得すると思いますUIフォントですが、間違っているでしょう。

ええとああ。今や物事は難しくなります... Vistaは、XPとは異なるフォントを使用していますが、これはワンサイズフィット識別子では簡単にアクセスできないだけでなく、異なるsize、ダイアログを表示する方法を変更します(表示できるようになった場合)。多くの場所で、Windows Shellチームが登場しました。単にチャレンジをパントするために、Tegoma 8 ptが場所全体で使用されます。Aeroテーマが有効になっている場合でも、Segoe UI 9 ptを使用することになっています。 UIが洗練されていないように見え、Vistaの初期の頃には多くの問題がありました。今では、ほとんどの人がそれを忘れているように見えますが、UIはそれほど散らばらず、一貫性がありません。

そして、あなたはWindows Shellチームではありません。自分のアプリでこれを回避することはできません。 Windows Vistaユーザーエクスペリエンスのトップルール は、次のことを常に明示的に示しています。

  • 新しいWindows VistaシステムフォントであるSegoe UIを使用します。
  • WindowsテーマAPIを使用してシステムフォント、サイズ、および色を常に参照することにより、ユーザーの設定を尊重します。フォント、サイズ、または色に固定値を使用しないでください。

正直に言うと、私はまだこの問題に対する良い解決策を聞いていません。そして、私は今までに、誰もWindowsをサポートする必要がないと思うXP(ほとんどの人はそこにいないquit-yet)。しかし、ここで私は何をします: SystemParametersInfo function を使用して、実行時にデフォルトのシステムフォントを抽出します。メッセージボックスフォント(lfMessageFont)は、Windowsの現在のバージョンとユーザーが選択したテーマに関係なく、正しいフォントとサイズです。

ウィンドウまたはダイアログを初期化するための私のコードは一般的に次のようになります(SystemInfo::IsVistaOrLaterは私が書いたヘルパー関数です;実装は明らかです):

// Get the system message box font
NONCLIENTMETRICS ncm;
ncm.cbSize = sizeof(ncm);

// If we're compiling with the Vista SDK or later, the NONCLIENTMETRICS struct
// will be the wrong size for previous versions, so we need to adjust it.
#if(_MSC_VER >= 1500 && WINVER >= 0x0600)
if (!SystemInfo::IsVistaOrLater())
{
    // In versions of Windows prior to Vista, the iPaddedBorderWidth member
    // is not present, so we need to subtract its size from cbSize.
    ncm.cbSize -= sizeof(ncm.iPaddedBorderWidth);
}
#endif

SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, 0);
HFONT hDlgFont = CreateFontIndirect(&(ncm.lfMessageFont));

// Set the dialog to use the system message box font
SetFont(m_DlgFont, TRUE);
SendMessage(hWnd, WM_SETFONT, (WPARAM)hDlgFont, MAKELPARAM(FALSE, 0));

または、便利なSendMessageToDescendantsメソッドを使用して、MFCでさらに簡単に
m_DlgFontはクラスに定義されたCFontオブジェクトです):

// Get the system message box font
NONCLIENTMETRICS ncm;
ncm.cbSize = sizeof(ncm);
SystemParametersInfo(SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, 0);
LOGFONT lfDlgFont = ncm.lfMessageFont;
m_DlgFont.CreateFontIndirect(&lfDlgFont);

// Set the dialog and all its controls to use the system message box font
SetFont(m_DlgFont, TRUE);
SendMessageToDescendants(WM_SETFONT, (WPARAM)m_DlgFont.m_hFont, MAKELPARAM(FALSE, 0), TRUE);

MFCを使用していない場合は、SendMessageToDescendantsの独自の再帰バージョンを実装することを強くお勧めします。これにより、初期化コードがlotより簡単になります。

84
Cody Gray