[英]Let JTextField resize automatically
我想顯示JTextField的二維數組,以供用戶編輯。 初始化后(帶有文本),它們顯示為合適的大小。 當“文本”被編輯時,它們不會調整大小。 我將它們放在JSrolePane中帶有GridbagLayout的JPanel中。 試圖“手動”調整它們的大小,因此在接收事件時調用.setPrefferedSize,但是很難獲得不同的letterSize的TextLength精確原因。 而且所有JTextField都顯示在一行中,因此我可能對GridBagConstraints出錯了。 (以前使用過JTable,但不喜歡它)。
GridBagConstraints c = new GridBagConstraints();
c.gridx = 0;
c.gridy = 0;
c.weighty = 0.1;
c.weightx = 0.1;
c.fill = GridBagConstraints.BOTH;
for(int row=0; row<initText.length; row++) {
for(int col=0; col<initText[row].length; col++) {
jTextFields[row][col] = new JTextField(initText[row][col]);
jTextFields[row][col].getDocument().addDocumentListener(new DocumentListener() {
@Override
public void removeUpdate(DocumentEvent arg0) {
}
@Override
public void insertUpdate(DocumentEvent dE) {
int row = -1;
int col = -1;
for(int i=0; i<jTextFields.length; i++) {
for(int ii=0; ii<jTextFields[i].length; ii++) {
if(jTextFields[i][ii].getDocument()==dE.getDocument()) {
row=i;
col=ii;
break;
}
}
if(col!=-1) {
break;
}
}
//Tried it so to make resize "by Hand" but initalisation size is better
jTextFields[row][col].setPreferredSize(new Dimension(jTextFields[row][col].getText().length()*jTextFields[row][col].getPreferredSize().height, jTextFields[row][col].getPreferredSize().height));
System.out.println("insertUpdate in cell "+row+" "+col);
Main.gui.frame.repaint();
}
@Override
public void changedUpdate(DocumentEvent arg0) {
// TODO Auto-generated method stub
}
});
c.gridx = col;
c.gridy = row;
innerContentPane.add(jTextFields[row][col], c);
}
}
contentPane = new JScrollPane(innerContentPane);
frame.repaint();
您不想繼續重置組件的首選大小。 讓每個組件確定自己的首選大小。
相反,您想調用布局管理器,以便可以重新計算每個組件的大小並可以調整面板的布局。 一種簡單的方法是對包含文本字段的面板進行revalidate()
。
我不是多層次循環代碼和多層次循環代碼的忠實擁護者。 您可以通過創建要由所有文檔共享的通用DocumentListener來簡化代碼。
另外,您的代碼僅處理添加文本的情況。 如果刪除了文本,文本字段的大小不應該縮小嗎?
應用以上所有建議,邏輯將類似於:
// Create shared DocumentListener
DocumentListener dl = new DocumentListener()
{
@Override
public void removeUpdate(DocumentEvent de)
{
resizeTextField(de);
}
@Override
public void insertUpdate(DocumentEvent de)
{
resizeTextField(de);
}
@Override
public void changedUpdate(DocumentEvent de) {}
private void resizeTextField(DocumentEvent de)
{
innerContentPane.revalidate();
}
};
GridBagConstraints c = new GridBagConstraints();
c.gridx = 0;
c.gridy = 0;
//c.weighty = 0.1;
//c.weightx = 0.1;
//c.fill = GridBagConstraints.BOTH;
// Create text fields and add listener to the Document
for(int row = 0; row < 3; row++)
{
for(int col = 0; col <3; col++)
{
JTextField textField = new JTextField("0");
textFields[row][col] = textField;
textField.getDocument().addDocumentListener(dl);
c.gridx = col;
c.gridy = row;
innerContentPane.add(textField, c);
}
}
注意,DocumentListener也應該作為內部類創建,以使代碼更加清晰。
而且所有JTextFields都顯示在一行中,所以我可能對GridBagConstraints有點誤解
JPanel的默認布局管理器是FlowLayout。如果要使用的布局,則需要將布局設置為GridBagLayout:
innerContentPane.setLayout( new GridBagLayout() );
GridBagConstraints c = new GridBagConstraints();
否則,GridBagConstraints對FlowLayout毫無意義。
閱讀有關布局管理器的Swing教程中的部分,以獲取更多信息。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.