当窗格宽度超过指定值时,在 JTextPane 中换行文本
Wrap text in a JTextPane when pane width exceeds a specified value
我的 GUI 在 JTextPane 中显示日志,它位于 JScrollPane 内,占据了 JSplitPane 的左侧。 JSplitPane 的右侧包含 GUI 中有趣的部分。日志窗格的宽度通常较窄 (20),但当用户想要查看 activity 时会增加。如果日志文本被换行,那么当日志窗格很窄时显示的文本是非常无用的,但是如果一些日志条目很长,则需要增加日志窗格的大小以占据大部分 GUI 来查看条目。
我知道 JTextPane 不会自然换行文本,Stack Overflow 上的其他帖子描述了如何换行文本。但是,我希望仅当窗格宽于某些提供的限制(例如 100)时才换行文本。因此,当窗格变窄时,只显示每条消息的开头,如果用户想要查看完整内容文本,窗格宽度增加,文本换行到 window 宽度。
如果没有办法做到这一点,我将关闭换行并将文本格式化为某个固定宽度,然后再将其写入窗格。
提前致谢!
I understand that JTextPane does not naturally wrap text
这是错误的。默认情况下,JTextPane 会换行文本。
查看 Text Pane No Wrap 了解有关此主题的更多信息,该主题构成了以下解决方案的基础。
您需要覆盖 getScrollableTrackViewportWidth()
方法。我觉得应该是:
JTextPane textPane = new JTextPane()
{
public boolean getScrollableTracksViewportWidth()
{
return getParent().getSize().width > 100;
}
};
编辑:
这个问题似乎与文本窗格中的文本有关。不知道是文字的长度还是文字中的非字母字符造成的差异:
import java.awt.*;
import javax.swing.*;
import javax.swing.event.*;
public class TextPaneNoWrap
{
private static void createAndShowGUI()
{
JTextPane textPane = new JTextPane()
{
@Override
public boolean getScrollableTracksViewportWidth()
{
Dimension d = getParent().getSize();
System.out.println(d);
return false;
}
};
textPane.setText("one two three four five six\nthis wraps at 39");
// textPane.setText("import javax.swing.event.*;\nthis wraps at 111");
JFrame frame = new JFrame("TextPaneNoWrap");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new JLabel("Some Component"), BorderLayout.LINE_START);
frame.add(new JScrollPane( textPane ));
frame.setSize(300, 100);
frame.setLocationByPlatform( true );
frame.setVisible( true );
}
public static void main(String[] args)
{
EventQueue.invokeLater( () -> createAndShowGUI() );
/*
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowGUI();
}
});
*/
}
}
编辑2:
使用实现 Scrollable 接口的 "wrapper" 面板似乎工作正常:
import java.awt.*;
import javax.swing.*;
import javax.swing.event.*;
public class TextPaneNoWrap
{
private static void createAndShowGUI()
{
JTextPane textPane = new JTextPane();
// textPane.setText("one two three four five six\nthis wraps at 39");
textPane.setText("import javax.swing.event.*;\nthis wraps at 111");
JPanel wrapper = new NoWrapPanel(textPane);
JFrame frame = new JFrame("TextPaneNoWrap");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new JLabel("Some Component"), BorderLayout.LINE_START);
frame.add(new JScrollPane( wrapper ));
frame.setSize(300, 100);
frame.setLocationByPlatform( true );
frame.setVisible( true );
}
static class NoWrapPanel extends JPanel implements Scrollable
{
public NoWrapPanel(JComponent component)
{
setLayout( new BorderLayout() );
add( component );
}
@Override
public Dimension getPreferredScrollableViewportSize()
{
return getPreferredSize();
}
@Override
public int getScrollableBlockIncrement(Rectangle visibleRect, int orientation, int direction)
{
return 20;
}
@Override
public boolean getScrollableTracksViewportHeight()
{
return true;
}
@Override
public boolean getScrollableTracksViewportWidth()
{
// return false;
return getParent().getSize().width > 100;
}
@Override
public int getScrollableUnitIncrement(Rectangle visibleRect, int orientation, int direction)
{
return 10;
}
}
public static void main(String[] args)
{
EventQueue.invokeLater( () -> createAndShowGUI() );
/*
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowGUI();
}
});
*/
}
}
我的 GUI 在 JTextPane 中显示日志,它位于 JScrollPane 内,占据了 JSplitPane 的左侧。 JSplitPane 的右侧包含 GUI 中有趣的部分。日志窗格的宽度通常较窄 (20),但当用户想要查看 activity 时会增加。如果日志文本被换行,那么当日志窗格很窄时显示的文本是非常无用的,但是如果一些日志条目很长,则需要增加日志窗格的大小以占据大部分 GUI 来查看条目。
我知道 JTextPane 不会自然换行文本,Stack Overflow 上的其他帖子描述了如何换行文本。但是,我希望仅当窗格宽于某些提供的限制(例如 100)时才换行文本。因此,当窗格变窄时,只显示每条消息的开头,如果用户想要查看完整内容文本,窗格宽度增加,文本换行到 window 宽度。
如果没有办法做到这一点,我将关闭换行并将文本格式化为某个固定宽度,然后再将其写入窗格。 提前致谢!
I understand that JTextPane does not naturally wrap text
这是错误的。默认情况下,JTextPane 会换行文本。
查看 Text Pane No Wrap 了解有关此主题的更多信息,该主题构成了以下解决方案的基础。
您需要覆盖 getScrollableTrackViewportWidth()
方法。我觉得应该是:
JTextPane textPane = new JTextPane()
{
public boolean getScrollableTracksViewportWidth()
{
return getParent().getSize().width > 100;
}
};
编辑:
这个问题似乎与文本窗格中的文本有关。不知道是文字的长度还是文字中的非字母字符造成的差异:
import java.awt.*;
import javax.swing.*;
import javax.swing.event.*;
public class TextPaneNoWrap
{
private static void createAndShowGUI()
{
JTextPane textPane = new JTextPane()
{
@Override
public boolean getScrollableTracksViewportWidth()
{
Dimension d = getParent().getSize();
System.out.println(d);
return false;
}
};
textPane.setText("one two three four five six\nthis wraps at 39");
// textPane.setText("import javax.swing.event.*;\nthis wraps at 111");
JFrame frame = new JFrame("TextPaneNoWrap");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new JLabel("Some Component"), BorderLayout.LINE_START);
frame.add(new JScrollPane( textPane ));
frame.setSize(300, 100);
frame.setLocationByPlatform( true );
frame.setVisible( true );
}
public static void main(String[] args)
{
EventQueue.invokeLater( () -> createAndShowGUI() );
/*
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowGUI();
}
});
*/
}
}
编辑2:
使用实现 Scrollable 接口的 "wrapper" 面板似乎工作正常:
import java.awt.*;
import javax.swing.*;
import javax.swing.event.*;
public class TextPaneNoWrap
{
private static void createAndShowGUI()
{
JTextPane textPane = new JTextPane();
// textPane.setText("one two three four five six\nthis wraps at 39");
textPane.setText("import javax.swing.event.*;\nthis wraps at 111");
JPanel wrapper = new NoWrapPanel(textPane);
JFrame frame = new JFrame("TextPaneNoWrap");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new JLabel("Some Component"), BorderLayout.LINE_START);
frame.add(new JScrollPane( wrapper ));
frame.setSize(300, 100);
frame.setLocationByPlatform( true );
frame.setVisible( true );
}
static class NoWrapPanel extends JPanel implements Scrollable
{
public NoWrapPanel(JComponent component)
{
setLayout( new BorderLayout() );
add( component );
}
@Override
public Dimension getPreferredScrollableViewportSize()
{
return getPreferredSize();
}
@Override
public int getScrollableBlockIncrement(Rectangle visibleRect, int orientation, int direction)
{
return 20;
}
@Override
public boolean getScrollableTracksViewportHeight()
{
return true;
}
@Override
public boolean getScrollableTracksViewportWidth()
{
// return false;
return getParent().getSize().width > 100;
}
@Override
public int getScrollableUnitIncrement(Rectangle visibleRect, int orientation, int direction)
{
return 10;
}
}
public static void main(String[] args)
{
EventQueue.invokeLater( () -> createAndShowGUI() );
/*
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowGUI();
}
});
*/
}
}