私たちはテキストを描画するアプリケーションを持っていますが、テキストをクリックしたときにテキストを編集するためのJTextAreaを表示します。ただし、これら2つのテキスト処理コンポーネント間の折り返しは異なります。同じ幅、テキスト文字列、およびフォントを使用します。なぜJTextAreaとTextLayoutは単語を異なる方法でラップするのですか?
私はJavaのチュートリアルのテキスト描画を使用しています。これは他の人たちが他のフォーラムや他のフォーラムで使っているのと同じです。ここでは、コードの一部です:
FontRenderContext frc = g2d.getFontRenderContext();
TextLayout layout;
AttributedString attrString = new AttributedString(myText);
AttributedCharacterIterator charIterator;
int paragraphStart;
int paragraphEnd;
LineBreakMeasurer lineMeasurer;
float breakWidth;
float drawPosX;
float drawPosY;
attrString.addAttribute(TextAttribute.FONT, myFont);
charIterator = attrString.getIterator();
paragraphStart = charIterator.getBeginIndex();
paragraphEnd = charIterator.getEndIndex();
lineMeasurer = new LineBreakMeasurer(charIterator, frc);
// Set break width to width of Component.
breakWidth = myTextWidth;
drawPosY = startY
// Set position to the index of the first character in the paragraph.
lineMeasurer.setPosition(paragraphStart);
textBounds = new Rectangle(startX, startY(), 0, 0);
// Get lines from until the entire paragraph has been displayed.
while (lineMeasurer.getPosition() < paragraphEnd) {
layout = lineMeasurer.nextLayout(breakWidth);
// Compute pen x position. If the paragraph is right-to-left we
// will align the TextLayouts to the right edge of the panel.
drawPosX = layout.isLeftToRight()
? startX() : breakWidth - layout.getAdvance();
// Draw the TextLayout at (drawPosX, drawPosY).
layout.draw(g2d, drawPosX, drawPosY);
lineBounds = new Rectangle2D.Float(drawPosX, drawPosY - layout.getAscent(), layout.getAdvance(), (layout.getAscent() + layout.getDescent() + layout.getLeading()));
// Move y-coordinate in preparation for next layout.
drawPosY += layout.getAscent() + layout.getDescent() + layout.getLeading();
}
JTextAreaには、はるかに簡単です:
JTextArea textArea = new JTextArea(myText);
textArea.setSize(myTextWidth, myTextThing.getHeight());
textArea.setOpaque(true);
textArea.setVisible(true);
textArea.setLineWrap(true);
textArea.setWrapStyleWord(true);
textArea.setFont(myFont);
textArea.setBorder(null);
私は破線の領域とテキスト領域の境界の外側に別の四角形を描画したので、私はnullに境界線を設定しますそれがどこにあるかを示します。今はばかげているかもしれませんが、ユーザーが最初に編集したいテキストを選択したときに、テキスト領域の境界を表示するために使用します。その時点で、JTextAreaはまだ作成されていません。編集を開始するには、もう一度クリックする必要があります。その理由は、テキストエリアが選択されると、テキストエリアをドラッグしてサイズ変更することがあり、ドラッグアンドリサイズを開始したときにライブのJTextAreaを持っていれば、混乱し、混乱を招くからです。
これとは別に、描画されたTextLayoutsとJTextAreaの両方が、単語を正しくラップするように見えます。一緒に使用すると違いを見ることができます。この問題は、ユーザーがテキストを編集しているときに、JTextAreaがテキストをラップすることを実行していることです。しかし、ユーザーJTextAreaがフォーカスを失った場合、描画されたテキストに変換され、単語が別の方法で折り返されます。
感謝。私はSSCCEを作成しました。そして、最終的にJTextAreaとTextLayoutが同じようにテキストをラップしました。これにより、元のコードをもう一度見て、そうすることで、JTextArea上でsetSize()とsetBounds()を不必要に使用することがわかりました。一度それをきれいにするとうまくいった。 – user26270