4

有没有比获取 FontMetrics 实例更友好的方法

FontMetrics fm = Graphics.getFontMetrics(Font);

由于以下示例,我讨厌这种方式:

如果您想在游戏中创建一个菜单,并且您希望所有菜单项都位于屏幕中央,则您需要 fontmetrics。但是,大多数情况下,菜单项是可点击的。所以我创建了一个数组,Rectangles所有矩形都适合项目,所以当按下鼠标时,我可以简单地使用

for (int i = 0; i < rects.length; i++)
if (rects[i].contains(mouseX, mouseY)) { ... }

但是要创建矩形,我还需要 FontMetrics 作为它们的坐标。所以这意味着我必须在菜单的绘制方法中构建所有矩形。

所以我想要一种获取 FontMetrics 的方法,这样我就可以在构造函数调用的方法中构造矩形。

4

6 回答 6

11

对我来说,最简单的方法是:

Font font = new Font("Helvetica",Font.PLAIN,12);
Canvas c = new Canvas();
FontMetrics fm = c.getFontMetrics(font);

好处:

  1. 如果您调用 c.getGraphics() 它将返回 null (因此没有图形对象)
  2. 这个(画布)也可以在无头模式下工作。

现在您可以轻松获得高度和宽度...

于 2013-08-09T13:48:07.493 回答
6

真正正确的答案是使用 Toolkit。

Font font = new Font("Courier New", Font.PLAIN, 14);
FontMetrics fm = Toolkit.getDefaultToolkit().getFontMetrics(font);
于 2013-02-06T13:04:22.847 回答
2

一旦背景组件(即菜单后面的任何内容)被渲染,它就有一个Graphics对象,您可以使用它来获取给定字体的指标,只需一次。

您当然不想在paint方法中这样做,它应该尽可能轻量级。我会将此代码挂在一个侦听器上,该侦听器在首次呈现组件时被调用。它可以将生成的 FontMetrics 对象存储在您以后可以访问它的某个位置,或者以paint用于绘制这些菜单项框的方法中。

与其在最后一刻(即在 ing 时)确定菜单图形的尺寸,不如paint创建一些组件来表示您的菜单。您可以将这些组件放在 Glass Pane 上更多信息 在这里它们会浮在其他所有东西之上,并且您将获得额外的好处,这些组件都能够接受鼠标点击并在它们上触发侦听器事件,因为它们只在它们自己的几何体上捕获事件,您甚至不必弄清楚点击菜单的哪个部分,如果有的话。

在这里使用组件的另一个优点是,您可以完全绕过摆弄字体度量的要求。有现成的菜单项,或者您可以只使用JLabels,并且您可以指定它们的对齐方式,您可以使用 aLayoutManager将框的大小调整为最大标签的宽度,等等。

于 2010-05-02T13:19:50.543 回答
1

假设菜单文本是固定的,您可以将文本预先绘制到具有 alpha 透明度的BufferedImage中,然后进行计算。然后,当您需要菜单文本时,只需绘制图像即可。

您仍然需要进行一些偏移计算以使图像居中(假设面板大小可以更改),但这些应该相对轻量级。

于 2010-05-02T13:27:55.780 回答
1

我认为这是一个很好的解决方案

private static HashMap<Font, FontMetrics> fontmetrics = new HashMap<Font, FontMetrics>();


public static FontMetrics getFontMetrics(Font font)
{
    if (fontmetrics.containsKey(font))
    {
        return fontmetrics.get(font);
    }
    FontMetrics fm = createFontMetrics(font);
    fontmetrics.put(font, fm);
    return fm;
}

private static FontMetrics createFontMetrics(Font font)
{
    BufferedImage bi = new BufferedImage(1, 1, BufferedImage.TYPE_INT_ARGB_PRE);
    Graphics g = bi.getGraphics();
    FontMetrics fm = g.getFontMetrics(font);
    g.dispose();
    bi = null;
    return fm;
}
于 2010-05-02T14:17:34.950 回答
0

除了朗扎克所说的,这个怎么样:

public static FontMetrics getFontMetrics(Font font){
    GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
    GraphicsDevice gd = ge.getDefaultScreenDevice();
    GraphicsConfiguration config = gd.getDefaultConfiguration();

    Canvas c = new Canvas(config);
    return c.getFontMetrics(font);
}

您可以将“配置”变量存储为静态变量,以便在某个实用字体类中构造一次,该类包含游戏/开发环境的其他字体相关信息。我想你也可以用 canvas 变量来做到这一点。

于 2014-05-10T23:34:44.750 回答