Hi!

I would like to create textfields that will serve for sorting data in JTable, and the width of these textfields will correspond to a column width. So, below you may see the code that worked until I did not use an array of textfields. Now, the size of txtRegNum and txtRegDate corresponds to the conlumn width, however all remaining textfields created from an array are very short. Why does it happen? Should I use any other method for an array of textfields?

Thanks!

sorter = new TableRowSorter<QueryTableModel>(SystClasses.Form.tableModel);
table.setRowSorter(sorter);

table.getColumnModel().addColumnModelListener(new TableColumnModelListener() {
public void columnMarginChanged(ChangeEvent e) {
     txtRegNum.setPreferredSize(new Dimension(table.getColumn("reg_num").getPreferredWidth(),txtRegNum.getPreferredSize().height));
     txtRegDate.setPreferredSize(new Dimension(table.getColumn("reg_date").getPreferredWidth(),txtRegDate.getPreferredSize().height));
     for (int i=0; i < NrOfTextFields; i++) {
         txtAttrTextFields[i].setPreferredSize(new Dimension(table.getColumn(attrTitle.elementAt(i).toString()).getPreferredWidth(),txtAttrTextFields[i].getPreferredSize().height));
     }
     txtAttachedFile.setPreferredSize(new Dimension(table.getColumn("attached_file").getPreferredWidth(),txtAttachedFile.getPreferredSize().height));
  }

public void columnAdded(TableColumnModelEvent e) {}
public void columnRemoved(TableColumnModelEvent e) {}
public void columnMoved(TableColumnModelEvent e) {}
public void columnSelectionChanged(ListSelectionEvent e) {}
});

Experimental look - not tested
use getPreferredSize, then setPreferredSize

private JTextField[] txtAttrTextFields = new JTextField[NrOfTextFields];

    {
        for (int i = 0; i < NrOfTextFields; i++) { // int i can't be final
            txtAttrTextFields[i] = new JTextField(){

                @Override
                public Dimension getPreferredSize() {
                    // return new Dimension((10+10*Integer.valueOf(getName())),40);
                    return new Dimension(table.getColumn(attrTitle.elementAt(Integer.valueOf(getName())).toString()).getPreferredWidth(), 40);
                    //no ,  txtAttrTextFields[Integer.valueOf(getName())].getPreferredSize().height  --> to avoid cycle!

                }
            };
            txtAttrTextFields[i].setName("" + i);// name used as index parameter
        }
    }

Inside public void columnMarginChanged(ChangeEvent e) { -method simply repaint all textfields (or find other method)

Then I receive the following message:

Exception in thread "AWT-EventQueue-0" java.lang.NullPointerException
        at SystClasses.TreeEditTest$1.columnMarginChanged(TreeEditTest.java:230)
        at javax.swing.table.DefaultTableColumnModel.fireColumnMarginChanged(DefaultTableColumnModel.java:611)
        at javax.swing.table.DefaultTableColumnModel.propertyChange(DefaultTableColumnModel.java:675)
        at java.beans.PropertyChangeSupport.firePropertyChange(PropertyChangeSupport.java:339)
        at javax.swing.event.SwingPropertyChangeSupport.firePropertyChange(SwingPropertyChangeSupport.java:75)
        at java.beans.PropertyChangeSupport.firePropertyChange(PropertyChangeSupport.java:276)
        at javax.swing.table.TableColumn.firePropertyChange(TableColumn.java:261)
        at javax.swing.table.TableColumn.firePropertyChange(TableColumn.java:267)
        at javax.swing.table.TableColumn.setWidth(TableColumn.java:497)
        at javax.swing.JTable$2.setSizeAt(JTable.java:3201)
        at javax.swing.JTable$5.setSizeAt(JTable.java:3293)
        at javax.swing.JTable.adjustSizes(JTable.java:3329)
        at javax.swing.JTable.adjustSizes(JTable.java:3297)
        at javax.swing.JTable.setWidthsFromPreferredWidths(JTable.java:3209)
        at javax.swing.JTable.doLayout(JTable.java:3097)
        at java.awt.Container.validateTree(Container.java:1507)
        at java.awt.Container.validateTree(Container.java:1513)
        at java.awt.Container.validateTree(Container.java:1513)
        at java.awt.Container.validate(Container.java:1480)
        at javax.swing.RepaintManager.validateInvalidComponents(RepaintManager.java:669)
        at javax.swing.SystemEventQueueUtilities$ComponentWorkRequest.run(SystemEventQueueUtilities.java:124)
        at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:209)
        at java.awt.EventQueue.dispatchEvent(EventQueue.java:597)
        at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:269)
        at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:184)
        at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:174)
        at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:169)
        at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:161)
        at java.awt.EventDispatchThread.run(EventDispatchThread.java:122)

where? whats null, and why?

If I run the code shown below, the I receive the message that I posted above. Attached you could see the figure that illustrates the hell produced by this code:)

And I tried the solution proposed by quuba, but it did not help me to solve the problem, because I got the same error message. Where is the problem?!

txtRegNum = new JTextField(); txtRegDate = new JTextField(); txtAttachedFile = new JTextField();
        txtAttrTextFields = new JTextField[NrOfTextFields];
        
        for (int i=0; i < NrOfTextFields; i++) {
            txtAttrTextFields[i] = new JTextField();
        }

        sorter = new TableRowSorter<QueryTableModel>(tableModel);
        table.setRowSorter(sorter);

        table.getColumnModel().addColumnModelListener(new TableColumnModelListener() {
        public void columnMarginChanged(ChangeEvent e) {
            txtRegNum.setPreferredSize(new Dimension(table.getColumn("reg_num").getPreferredWidth(),txtRegNum.getPreferredSize().height));
            txtRegDate.setPreferredSize(new Dimension(table.getColumn("reg_date").getPreferredWidth(),txtRegDate.getPreferredSize().height));

            for (int i=0; i < NrOfTextFields; i++) {
                txtAttrTextFields[i].setPreferredSize(new Dimension(table.getColumn(attrTitle.elementAt(i).toString()).getPreferredWidth(),txtAttrTextFields[i].getPreferredSize().height));
            }
            txtAttachedFile.setPreferredSize(new Dimension(table.getColumn("attached_file").getPreferredWidth(),txtAttachedFile.getPreferredSize().height));
        }
        public void columnAdded(TableColumnModelEvent e) {}
        public void columnRemoved(TableColumnModelEvent e) {}
        public void columnMoved(TableColumnModelEvent e) {}
        public void columnSelectionChanged(ListSelectionEvent e) {}
        });

Inside public void columnMarginChanged(ChangeEvent e) { -method simply repaint all textfields (or find other method)

this other method is:

// last line
jpanelWithTextFields.validate();

//

Exception in thread "AWT-EventQueue-0" java.lang.NullPointerException
        at SystClasses.TreeEditTest$1.columnMarginChanged(TreeEditTest.java:230)

show line 230

Experimental look - not tested
use getPreferredSize, then setPreferredSize

private JTextField[] txtAttrTextFields = new JTextField[NrOfTextFields];

    {
        for (int i = 0; i < NrOfTextFields; i++) { // int i can't be final
            txtAttrTextFields[i] = new JTextField(){

                @Override
                public Dimension getPreferredSize() {
                    // return new Dimension((10+10*Integer.valueOf(getName())),40);
                    return new Dimension(table.getColumn(attrTitle.elementAt(Integer.valueOf(getName())).toString()).getPreferredWidth(), 40);
                    //no ,  txtAttrTextFields[Integer.valueOf(getName())].getPreferredSize().height  --> to avoid cycle!

                }
            };
            txtAttrTextFields[i].setName("" + i);// name used as index parameter
        }
    }

Inside public void columnMarginChanged(ChangeEvent e) { -method simply repaint all textfields (or find other method)

You have a method public Dimension getPreferredSize() { in the middle of your code.
You just cannot do that.
You might want to extend class JTextField and overload one of the methods getPreferredSize(), getSize() or whichever

correction to my (quuba) last post
should be revalidate();
attrTitle/table are empty during the init process, before reading the database

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.