gpt4 book ai didi

java - Swing drawString : Text bounds and line wrapping

转载 作者:塔克拉玛干 更新时间:2023-11-01 21:53:30 24 4
gpt4 key购买 nike

我需要用 Graphics#drawString 绘制文本

我在宽度和高度都发生变化(通过拖动)的 JPanel 上绘图。

我正在寻找一种生成边界的解决方案,以便我可以自动扭曲线条并相应地调整文本,而不会溢出。

我想我可以通过使用 fontMetrics 获取以像素为单位的长度来自己硬编码,但是,我宁愿有一个自动执行此操作的组件(drawString 也不支持 '\n').

在文档以及 this 中我发现的其他答案:

Graphics2D g = ...;
Point2D loc = ...;
Font font = Font.getFont("Helvetica-bold-italic");
FontRenderContext frc = g.getFontRenderContext();
TextLayout layout = new TextLayout("This is a string", font, frc);
layout.draw(g, (float)loc.getX(), (float)loc.getY());

Rectangle2D bounds = layout.getBounds();
bounds.setRect(bounds.getX()+loc.getX(),
bounds.getY()+loc.getY(),
bounds.getWidth(),
bounds.getHeight());
g.draw(bounds);

它确实绘制了字符串和边界,但它们没有任何效果,所以这里没有运气。

我可以使用任何类(class)吗?

最佳答案

Any class I could use?

另一种选择是使用 LineBreakMeasurer :

import java.awt.*;
import java.awt.font.*;
import java.awt.geom.*;
import java.text.*;
import java.util.Objects;
import javax.swing.*;
import javax.swing.border.Border;

public final class LineBreakMeasurerTest {
private static final String TEXT = "1234567890 ABCDEFG HIJKLMN OPQRSTU VWXYZ";
private final JLabel lbl1 = new JLabel(TEXT);
private final JTextArea lbl2 = new JTextArea(TEXT);
private final JLabel lbl3 = new WrappingLabel(TEXT);
public JComponent makeUI() {
Border b = BorderFactory.createLineBorder(Color.GREEN, 5);
lbl1.setBorder(
BorderFactory.createTitledBorder(b, "JLabel"));
lbl2.setBorder(
BorderFactory.createTitledBorder(b, "JTextArea"));
lbl3.setBorder(
BorderFactory.createTitledBorder(b, "LineBreakMeasurer"));

lbl2.setFont(lbl1.getFont());
lbl2.setEditable(false);
lbl2.setLineWrap(true);
lbl2.setWrapStyleWord(true);
lbl2.setBackground(lbl1.getBackground());

JPanel p = new JPanel(new GridLayout(3, 1));
p.add(lbl1);
p.add(lbl2);
p.add(lbl3);
return p;
}

public static void main(String... args) {
EventQueue.invokeLater(() -> {
UIManager.put("swing.boldMetal", Boolean.FALSE);
JFrame f = new JFrame();
f.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
f.getContentPane().add(new LineBreakMeasurerTest().makeUI());
f.setSize(320, 240);
f.setLocationRelativeTo(null);
f.setVisible(true);
});
}
}

class WrappingLabel extends JLabel {
//TEST: private AffineTransform at = AffineTransform.getScaleInstance(.8, 1d);
protected WrappingLabel(String text) {
super(text);
}
@Override protected void paintComponent(Graphics g) {
Graphics2D g2 = (Graphics2D) g.create();
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
g2.setPaint(getForeground());
Insets i = getInsets();
float x = i.left;
float y = i.top;
int w = getWidth() - i.left - i.right;

AttributedString as = new AttributedString(getText());
//TEST: as.addAttribute(TextAttribute.FONT, g2.getFont());
//TEST: as.addAttribute(TextAttribute.TRANSFORM, at);
AttributedCharacterIterator aci = as.getIterator();
FontRenderContext frc = g2.getFontRenderContext();
LineBreakMeasurer lbm = new LineBreakMeasurer(aci, frc);

while (lbm.getPosition() < aci.getEndIndex()) {
TextLayout tl = lbm.nextLayout(w);
tl.draw(g2, x, y + tl.getAscent());
y += tl.getDescent() + tl.getLeading() + tl.getAscent();
}
g2.dispose();
}
}

关于java - Swing drawString : Text bounds and line wrapping,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41111870/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com