【问题标题】:Draw border below the text of a component in Swing在 Swing 中的组件文本下方绘制边框
【发布时间】:2016-01-27 19:38:37
【问题描述】:

我创建了一个自定义边框类,我在其中填充了一个矩形作为组件的背景。请注意,这个边框将来会有更复杂的形状,而不仅仅是一个简单的矩形。

当我将我的边框添加到组件时,组件的文本将出现在边框后面并使文本不可读。 (结果如下图所示。)

有没有办法在文字下方画边框?

我的边框类:

public class CustomBorder extends AbstractBorder {
    private static final long serialVersionUID = 1L;

    @Override
    public void paintBorder(Component c, Graphics g, int x, int y, int width, int height) {
        Graphics2D g2d = (Graphics2D) g;
        g2d.setColor(new Color(125, 125, 125, 255));
        g2d.fillRect(x - 10, y - 10, width + 20, height + 20);
    }

    @Override
    public Insets getBorderInsets(Component c) {
        return super.getBorderInsets(c);
    }

    @Override
    public Insets getBorderInsets(Component c, Insets insets) {
        return super.getBorderInsets(c, insets);
    }

    @Override
    public boolean isBorderOpaque() {
        return super.isBorderOpaque();
    }
}

主要:

public static void main(String[] args) {
    JLabel label = new JLabel("JLabel text");
    label.setBorder(new CompoundBorder(new EmptyBorder(50, 20, 20, 20), new CustomBorder()));

    JFrame frame = new JFrame("");
    frame.setLayout(new FlowLayout());
    frame.setSize(200, 200);
    frame.add(label);
    frame.setVisible(true);
}

编辑:我还应该注意,我将在聊天程序中使用此边框,该程序将使用气泡形消息,因此使用 setBackground() 的彩色方块是禁忌。

【问题讨论】:

  • 在组件的内容上绘制边框。你想要的是画一个背景。

标签: java swing graphics border


【解决方案1】:

参见A Closer Look at the Paint Mechanism,它解释了绘画是如何完成的。绘制标签文本后绘制边框。

你到底想做什么?您的边框绘画代码没有意义。您正在尝试填充一个等于组件的宽度/高度 + 20 像素的矩形,这意味着您正在尝试绘制比组件更大的区域。

如果您只是想在标签上绘制背景,那么您可以使用:

label.setOpaque( true );
label.setBackground(...);

编辑:this answer 中的代码解决了这个问题。

【讨论】:

  • 我正在尝试为我的组件制作自定义边框,它将充当聊天消息,并且边框的形状将像一个气泡;我做了一个矩形来缩短代码。 +20px 背后的原因是为了在文本周围留出一些空间。
  • @Spitz Borders 在“周围”绘制组件。对于您想要做的事情,您可能需要从定义您要使用的形状的基本组件开始,然后向其中添加其他组件。例如,您可以查看thisthis
  • The reason behind the +20px is to make some space around the text. - 您需要设置 BorderInsets 以在文本周围留出空间。查看:Border Bubble,了解如何创建语音气泡的示例。
  • @camickr 我尝试将 10 添加到覆盖的 getBorderInsets() 中返回的 Insets 对象的每个值,但没有任何效果。此外,我所做的事情是否被认为是不好的做法?
  • @Spitz,您的代码将不起作用,因此您需要重新开始。我给了你一个链接,解释为什么它不起作用。 Swing 组件只能在组件边界内绘制,因此您不能在组件外部绘制 20 像素。我还为您提供了一个工作示例的链接,您可以根据自己的具体要求进行自定义。
【解决方案2】:

您始终可以使用g2d.drawString()。 但是,如果由于某种原因不使用它,您可以这样做:

JLabel l = new JLabel("foo");
l.setBackground(Color.GRAY);
l.setOpaque(true);

【讨论】:

  • 我怀疑如果我将长行文本绘制到组件上会被换行。
  • 哦,我不知道他们会被包装......我会尝试找到另一个解决方案。编辑:所以只需将 JLabel 放在矩形前面?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-06-19
  • 1970-01-01
  • 1970-01-01
  • 2012-02-26
  • 1970-01-01
  • 2021-10-27
  • 1970-01-01
相关资源
最近更新 更多