字体创建和选择

字体 通用”对话框简化了创建和选择字体的过程。 通过初始化 CHOOSEFONT 结构和调用 CHOOSEFONT 函数,应用程序可以支持以前需要许多自定义代码行的相同字体选择界面。 (有关 “字体 通用”对话框的详细信息,请参阅 Common Dialog Box Library.)

用户选择

大多数字体创建和选择操作都涉及用户。 例如,字处理应用程序允许用户为标题、脚注和正文文本选择唯一字体。 当用户使用 “字体 ”对话框选择字体并按 “确定 ”按钮后, SELECTFONT 函数使用请求字体的属性初始化 LOGFONT 结构的成员。 若要将此字体用于文本输出操作,应用程序必须首先创建一个逻辑字体,然后选择该字体到其设备上下文中。 逻辑字体是理想字体的应用程序提供说明。 开发人员可以通过调用 CreateFontCreateFontIndirect 函数来创建逻辑字体。 在这种情况下,应用程序将调用 CreateFontIndirect,并提供指向 CHOOSEFONT 初始化的 LOGFONT 结构的指针。 通常,调用 CreateFontIndirect 更高效,因为 CreateFont 需要多个参数,而 CreateFontIndirect 只需要一个指向 LOGFONT 的指针。

在应用程序实际上可以使用逻辑字体开始绘制文本之前,它必须从设备上内部存储的字体以及资源已加载到操作系统的字体中找到最接近的匹配项。 存储在设备或操作系统上的 字体称为物理字体。 查找与指定逻辑字体最匹配的物理字体的过程称为字体映射。 当应用程序调用 SelectObject 函数并提供标识逻辑字体的句柄时,将发生此过程。 使用内部算法执行字体映射,该算法将请求的逻辑字体的属性与可用物理字体的属性进行比较。 当字体映射器算法完成搜索并确定最接近的匹配项时, SelectObject 函数返回,应用程序可以使用新字体开始绘制文本。

SetMapperFlags 函数指定字体映射器算法是否仅搜索与物理设备匹配纵横比的物理字体。 设备的纵横比是由该设备上像素的宽度和高度构成的比率。

系统字体 (也称为 shell 或默认字体) 是标题栏、菜单和对话框中文本使用的字体。

特殊字体选择注意事项

尽管大多数字体选择操作都涉及用户,但在某些情况下,这并不真实。 例如,开发人员可能想要在应用程序中使用唯一字体在控件窗口中绘制文本。 若要选择适当的字体,应用程序必须能够确定哪些字体可用,创建描述其中一种可用字体的逻辑字体,然后选择该字体进入相应的设备上下文。

应用程序可以使用 EnumFontsEnumFontFamilies 函数枚举可用的字体。 建议使用 EnumFontFamilies,因为它枚举与家族名称关联的所有样式。 这对于具有许多或不同寻常样式的字体以及跨越国际边界的字体非常有用。

应用程序枚举可用字体并找到适当的匹配项后,它应使用字体枚举函数返回的值来初始化 LOGFONT 结构的成员。 然后,它可以调用 CreateFontIndirect 函数,并将其传递给初始化的 LOGFONT 结构的指针。 如果 CreateFontIndirect 函数成功,则应用程序可以通过调用 SelectObject 函数来选择逻辑字体。 初始化 LOGFONT 结构的成员时,请务必在 lfCharSet 成员中指定特定字符集。 此成员在字体映射过程中非常重要,如果此成员未正确初始化,则结果将不一致。 如果在 LOGFONT 结构的 lfFaceName 成员中指定字号名称,请确保 lfCharSet 值与 lfFaceName 中指定的字样字符集匹配。 例如,如果要选择 MS Mincho 等字体,则必须将 lfCharSet 设置为预定义值SHIFTJIS_CHARSET。

许多东亚语言的字体有两个字号:英语名称和本地化名称。 CreateFont、CreateFontIndirectCreateFontIndirectEx 采用与语言匹配的系统区域设置的本地化字面名称,但它们采用所有其他系统区域设置的英语字样名称。 最好的方法是尝试一个名称,并在失败时尝试另一个名称。 请注意,如果系统区域设置与字体语言不匹配,EnumFontFamiliesExEnumFontFamiliesEx 将返回英语字号。 从 Windows 2000 开始,这不再是问题,因为 CreateFont、CreateFontIndirectCreateFontIndirectEx 的字体映射器会识别任一字号,而不考虑区域设置。