Serialization of JTable

Hi,
we encounter some exceptions trying to serialize a JTable to XML:
java.lang.NoSuchMethodException: javax.swing.plaf.basic.BasicTableUI$PropertyChangeHandler.<init>()
     at java.lang.Class.getConstructor0(Class.java:1930)
We already patched the PropertyChangeHandler and gave it a default C'tor, but this would not work either. (Obviously inner classes make some problems here...)
Does anyone have an idea what this comes from?
Does anyone encounter similar problems?
Thanks,
Mauritius.

Hi,
we do not have any data in the table, except the names of the columns in the TableHeader. This is for a GUI editor, where only the properties of the JTable shall be edited.
We are some steps further in seeking the problem, but still haven't found a solution:
We try to serialize a JScrollPane containing a JTable. If you write an example that just creates the two and saves them to XML, this works fine. But if you add a Button to your application triggering an action which then saves the XML file, the described exceptions are thrown. If you leave the JScrollPane around the JTable away in the latter case, it also works.
Our solution will probably be to write the JTable contained in a JScrollPane individually, storing only the JTable, as this works. When loading the file again and a JTable is found, a JScrollPane will be put around it. This is not satisfying, but should work.
Greetings,
Mauritius.

Similar Messages

  • Serialization and the JTable

    Hello!
    I'm having some trouble to serialize my JTable.. The first time I click the SaveAs button, it save without problems, but the second time I click the SaveAs, even saving with another name, it throws the exception:
    java.io.NotSerializableException: com.sun.java.swing.plaf.windows.WindowsTableHeaderUI
    This problem do not occur in other computers, only on mine. I tryed to update my JKD and JRE from 1.5 to 1.6 update4, but still don't work..
    (I'm using Windows XP Professional, and Eclipse 3.3)
    Any idea??

    Hello,
    i tried serializing my Jtable data with the DefaultTableModel method but i get a class cast exception saying JTable cannot be cast to Table model..
    Is the a JTable model function?
    or what should i do?

  • How to reorder columns in JTable between sessions without serialization?

    I have a situation where the column widths and names of a JTable are saved to DB(there is no serialization). Upon starting a new session, the JTable needs to be displayed with reordered column.
    For example, let us say the default JTable has columns as A, B, C, D ...
    The user rearranges the columns to B, A, D, C....
    How do I tell JTable model to not use the default but the new values? Is serialization the only way?
    Here is some sample code I use to set the widths. But what I really want to do is reorder columns by reading their names.
    Thanks for your help
    for(int i=0;i<count;i++) {
                        int width=(int)(ttsDefaults.getColumnWidth(i)*
                             DesktopEnvironment.getInstance().getDesktopRootFrame().getWidth());
                        sumWidth+=width;
                        treeTable.getColumnModel().getColumn(i).setPreferredWidth(width);
                        //treeTable.getColumnModel().getColumn(i).setWidth(width);
                   }

    Hi Jules,
    You need a user with XDBADMIN rights to access the WebDav. Once you have access, you can open the URL as webfolder (in IE).
    Regards,
    Christian

  • Questions about Using Vector To File And JTable

    hi all
    I want to write all data from Vector To File and read from file To Vector
    And I want To show all data from vector to JTable
    Note: I'm using the JBuilder Compiler
    This is Class A that my datamember  And Methods in it
    import java.io.*;
    * <p>Title: </p>
    * <p>Description: </p>
    * <p>Copyright: Copyright (c) 2008</p>
    * <p>Company: </p>
    * @author unascribed
    * @version 1.0
    public  class A implements Serializable {
      int no;
      String name;
      int age;
      public void setA (int n,String na,int a)
        no=n;
        name=na;
        age=a;
      public void set_no(int n)
        no = n;
      public void set_age(int a)
        age = a;
        public int getage ()
        return age;
      public void setName(String a)
        name  = a;
      public String getname ()
        return name;
      public int getno ()
        return no;
    This is The Frame That the JTextFeild And JButtons & JTable in it
    import java.awt.*;
    import java.io.*;
    import java.util.*;
    import com.borland.jbcl.layout.*;
    import javax.swing.*;
    import java.awt.event.*;
    import javax.swing.table.*;
    import javax.swing.border.*;
    * <p>Title: </p>
    * <p>Description: </p>
    * <p>Copyright: Copyright (c) 2008</p>
    * <p>Company: </p>
    * @author unascribed
    * @version 1.0
    public class Frame1 extends JFrame {
    /* Vector v = new Vector ();
      public int i=0;*/
      A a = new A();
      XYLayout xYLayout1 = new XYLayout();
      JTextField txtno = new JTextField();
      JTextField txtname = new JTextField();
      JTextField txtage = new JTextField();
      JButton add = new JButton();
      JButton search = new JButton();
      /*JTable jTable1 = new JTable();
      TableModel tableModel1 = new MyTableModel(*/
                TableModel dataModel = new AbstractTableModel() {
              public int getColumnCount() { return 2; }
              public int getRowCount() { return 2;}
              public Object getValueAt(int row, int col) { return new A(); }
          JTable table = new JTable(dataModel);
          JScrollPane scrollpane = new JScrollPane(table);
      TitledBorder titledBorder1;
      TitledBorder titledBorder2;
      ObjectInputStream in;
      ObjectOutputStream out;
      JButton read = new JButton();
      public Frame1() {
        try {
          jbInit();
        catch(Exception e) {
          e.printStackTrace();
      private void jbInit() throws Exception {
        titledBorder1 = new TitledBorder(BorderFactory.createEmptyBorder(),"");
        titledBorder2 = new TitledBorder("");
        this.getContentPane().setLayout(xYLayout1);
        add.setBorder(BorderFactory.createRaisedBevelBorder());
        add.setNextFocusableComponent(txtno);
        add.setMnemonic('0');
        add.setText("Add");
        add.addActionListener(new java.awt.event.ActionListener() {
          public void actionPerformed(ActionEvent e) {
            add_actionPerformed(e);
        add.addActionListener(new java.awt.event.ActionListener() {
          public void actionPerformed(ActionEvent e) {
            add_actionPerformed(e);
        search.setFocusPainted(false);
        search.setText("Search");
        search.addActionListener(new java.awt.event.ActionListener() {
          public void actionPerformed(ActionEvent e) {
            search_actionPerformed(e);
        xYLayout1.setWidth(411);
        xYLayout1.setHeight(350);
        read.setText("Read");
        read.addActionListener(new java.awt.event.ActionListener() {
          public void actionPerformed(ActionEvent e) {
            read_actionPerformed(e);
        this.getContentPane().add(txtno, new XYConstraints(43, 35, 115, 23));
        this.getContentPane().add(txtname,  new XYConstraints(44, 67, 114, 22));
        this.getContentPane().add(txtage,      new XYConstraints(44, 97, 115, 23));
        this.getContentPane().add(add,      new XYConstraints(60, 184, 97, 26));
        this.getContentPane().add(search,  new XYConstraints(167, 185, 88, 24));
        this.getContentPane().add(table,   new XYConstraints(187, 24, 205, 119));
        this.getContentPane().add(read,   new XYConstraints(265, 185, 75, 24));
        this.setSize(450,250);
        table.setGridColor(new Color(0,0,255));
      void add_actionPerformed(ActionEvent e)
        a.set_no(Integer.parseInt(txtno.getText()));
        a.setName(txtname.getText());
        a.set_age(Integer.parseInt(txtage.getText()));
        fileOutput();
        txtno.setText(null);
        txtname.setText(null);
        txtage.setText(null);
        try
          out.writeObject(a);
          out.close();
        }catch (Exception excep){};
    /*  try
           add.setDefaultCapable(true);
          v.addElement(new A());
         ((A)v.elementAt(i)).setA(Integer.parseInt(txtno.getText()),txtname.getText(),Integer.parseInt(txtage.getText()));
        JOptionPane.showMessageDialog(null,"The Record is Added");
        txtno.setText(null);
        txtname.setText(null);
        txtage.setText(null);
        i++;
      }catch (Exception excep){};*/
      void search_actionPerformed(ActionEvent e) {
        int n = Integer.parseInt(JOptionPane.showInputDialog("Enter No:"));
        for (int i=0;i<v.size();i++)
          if (((A)v.elementAt(i)).getno()==n)
            txtno.setText(Integer.toString(((A)v.elementAt(i)).getno()));
            txtname.setText(((A)v.elementAt(i)).getname() );
            txtage.setText(Integer.toString(((A)v.elementAt(i)).getage()));
      public void fileOutput()
        try
          out = new ObjectOutputStream(new FileOutputStream("c:\\UserData.txt",true));
        }catch(Exception excep){};
      public void fileInput()
        try
          in = new ObjectInputStream(new FileInputStream("c:\\UserData.txt"));
        }catch(Exception excep){};
      void read_actionPerformed(ActionEvent e) {
      fileInput();
        try
          a = (A)in.readObject();
          txtno.setText(Integer.toString(a.getno()));
          txtname.setText(a.getname());
          txtage.setText(Integer.toString(a.getage()));
        }catch (Exception excep){};
    }

    //program which copies string data between vector and file
    import java.util.*;
    import java.io.*;
    class Util
    private Vector v;
    private FileReader filereader;
    private FileWriter filewriter;
    Util(String data[])throws Exception
      v=new Vector();
      for(String o:data)
        v.add(o);
    public void listData()throws Exception
      int size=v.size();
      for(int i=0;i<size;i++)
       System.out.println(v.get(i));
    public void copyToFile(String data,String fname)throws Exception
      filewriter =new FileWriter(fname);
      filewriter.write(data);
      filewriter.flush();
      System.out.println("Vector content copied into file..."+fname);
    public void copyFromFile(String fname)throws Exception
      filereader=new FileReader(fname);
      char fcont[]=new char[(int)new File(fname).length()];
      filereader.read(fcont,0,fcont.length);
      String temp=new String(fcont); 
      String fdata[]=temp.substring(1,temp.length()-1).split(",");
      for(String s:fdata)
        v.add(s.trim()); 
      System.out.println("File content copied into Vector...");
    public String getData()throws Exception
       return(v.toString());
    class TestUtil
    public static void main(String a[])throws Exception
      String arr[]={"siva","rama","krishna"};
      Util util=new Util(arr);
      System.out.println("before copy from file...");
      util.listData();
      String fname=System.getProperty("user.home")+"\\"+"vecdata";
      util.copyToFile(util.getData(),fname);
      util.copyFromFile(fname);
      System.out.println("after copy from file...");
      util.listData();
    }

  • One model for JTree and JTable

    Hi.
    Is it possible for a JTree and a JTable to share one model?
    Thank you

    Hope u r not using Comonent TreeTable
    If u have Tree & Table different components, just want to have a common model then u can try this,
    It is nothing but default implementation given in DefaultTableModel
    public class MyTreeTableModel extends DefaultTreeModel implements TableModel, Serializable {
    protected Vector dataVector;
    /** List of listeners */
    protected EventListenerList listenerList = new EventListenerList();
    /** The <code>Vector</code> of column identifiers. */
    protected Vector columnIdentifiers;
    public MyTreeTableModel(TreeNode root) {
    this(root, false);
    // constructor for TreeModel only
    public MyTreeTableModel(TreeNode root, boolean asksAllowsChildren) {
    super(root, asksAllowsChildren);
    // constructor for TableModel only
    public MyTreeTableModel() {
    this(0, 0);
    private static Vector newVector(int size) {
    Vector v = new Vector(size);
    v.setSize(size);
    return v;
    // constructor for TableModel only
    public MyTreeTableModel(int rowCount, int columnCount) {
    this(newVector(columnCount), rowCount);
    // constructor for TableModel only
    public MyTreeTableModel(Vector columnNames, int rowCount) {
    super(null);
    setDataVector(newVector(rowCount), columnNames);
    // constructor for TableModel only
    public MyTreeTableModel(Object[] columnNames, int rowCount) {
    this(convertToVector(columnNames), rowCount);
    // constructor for TableModel only
    public MyTreeTableModel(Vector data, Vector columnNames) {
    super(null);
    setDataVector(data, columnNames);
    // constructor for TableModel only
    public MyTreeTableModel(Object[][] data, Object[] columnNames) {
    super(null);
    setDataVector(data, columnNames);
    * Returns a default name for the column using spreadsheet conventions:
    * A, B, C, ... Z, AA, AB, etc. If <code>column</code> cannot be found,
    * returns an empty string.
    * @param column the column being queried
    * @return a string containing the default name of <code>column</code>
    private String getDefaultColumnName(int column) {
    String result = "";
    for (; column >= 0; column = column / 26 - 1) {
    result = (char)((char)(column%26)+'A') + result;
    return result;
    * Returns a column given its name.
    * Implementation is naive so this should be overridden if
    * this method is to be called often. This method is not
    * in the <code>TableModel</code> interface and is not used by the
    * <code>JTable</code>.
    * @param columnName string containing name of column to be located
    * @return the column with <code>columnName</code>, or -1 if not found
    public int findColumn(String columnName) {
    for (int i = 0; i < getColumnCount(); i++) {
    if (columnName.equals(getColumnName(i))) {
    return i;
    return -1;
    * Returns <code>Object.class</code> regardless of <code>columnIndex</code>.
    * @param columnIndex the column being queried
    * @return the Object.class
    public Class getColumnClass(int columnIndex) {
    return Object.class;
    // Managing Listeners
    * Adds a listener to the list that's notified each time a change
    * to the data model occurs.
    * @param     l          the TableModelListener
    public void addTableModelListener(TableModelListener l) {
    listenerList.add(TableModelListener.class, l);
    * Removes a listener from the list that's notified each time a
    * change to the data model occurs.
    * @param     l          the TableModelListener
    public void removeTableModelListener(TableModelListener l) {
    listenerList.remove(TableModelListener.class, l);
    * Returns an array of all the table model listeners
    * registered on this model.
    * @return all of this model's <code>TableModelListener</code>s
    * or an empty
    * array if no table model listeners are currently registered
    public TableModelListener[] getTableModelListeners() {
    return (TableModelListener[])listenerList.getListeners(
    TableModelListener.class);
    // Fire methods
    * Notifies all listeners that all cell values in the table's
    * rows may have changed. The number of rows may also have changed
    * and the <code>JTable</code> should redraw the
    * table from scratch. The structure of the table (as in the order of the
    * columns) is assumed to be the same.
    public void fireTableDataChanged() {
    fireTableChanged(new TableModelEvent(this));
    * Notifies all listeners that the table's structure has changed.
    * The number of columns in the table, and the names and types of
    * the new columns may be different from the previous state.
    * If the <code>JTable</code> receives this event and its
    * <code>autoCreateColumnsFromModel</code>
    * flag is set it discards any table columns that it had and reallocates
    * default columns in the order they appear in the model. This is the
    * same as calling <code>setModel(TableModel)</code> on the
    * <code>JTable</code>.
    public void fireTableStructureChanged() {
    fireTableChanged(new TableModelEvent(this, TableModelEvent.HEADER_ROW));
    * Notifies all listeners that rows in the range
    * <code>[firstRow, lastRow]</code>, inclusive, have been inserted.
    * @param firstRow the first row
    * @param lastRow the last row
    public void fireTableRowsInserted(int firstRow, int lastRow) {
    fireTableChanged(new TableModelEvent(this, firstRow, lastRow,
    TableModelEvent.ALL_COLUMNS, TableModelEvent.INSERT));
    * Notifies all listeners that rows in the range
    * <code>[firstRow, lastRow]</code>, inclusive, have been updated.
    * @param firstRow the first row
    * @param lastRow the last row
    public void fireTableRowsUpdated(int firstRow, int lastRow) {
    fireTableChanged(new TableModelEvent(this, firstRow, lastRow,
    TableModelEvent.ALL_COLUMNS, TableModelEvent.UPDATE));
    * Notifies all listeners that rows in the range
    * <code>[firstRow, lastRow]</code>, inclusive, have been deleted.
    * @param firstRow the first row
    * @param lastRow the last row
    public void fireTableRowsDeleted(int firstRow, int lastRow) {
    fireTableChanged(new TableModelEvent(this, firstRow, lastRow,
    TableModelEvent.ALL_COLUMNS, TableModelEvent.DELETE));
    * Notifies all listeners that the value of the cell at
    * <code>[row, column]</code> has been updated.
    * @param row row of cell which has been updated
    * @param column column of cell which has been updated
    public void fireTableCellUpdated(int row, int column) {
    fireTableChanged(new TableModelEvent(this, row, row, column));
    * Forwards the given notification event to all
    * <code>TableModelListeners</code> that registered
    * themselves as listeners for this table model.
    * @param e the event to be forwarded
    public void fireTableChanged(TableModelEvent e) {
    // Guaranteed to return a non-null array
    Object[] listeners = listenerList.getListenerList();
    // Process the listeners last to first, notifying
    // those that are interested in this event
    for (int i = listeners.length-2; i>=0; i-=2) {
    if (listeners==TableModelListener.class) {
    ((TableModelListener)listeners[i+1]).tableChanged(e);
    * Returns an array of all the objects currently registered
    * as <code><em>Foo</em>Listener</code>s
    * upon this <code>AbstractTableModel</code>.
    * <code><em>Foo</em>Listener</code>s are registered using the
    * <code>add<em>Foo</em>Listener</code> method.
    * <p>
    * You can specify the <code>listenerType</code> argument
    * with a class literal,
    * such as
    * <code><em>Foo</em>Listener.class</code>.
    * For example, you can query a
    * model <code>m</code>
    * for its table model listeners with the following code:
    * <pre>TableModelListener[] tmls = (TableModelListener[])(m.getListeners(TableModelListener.class));</pre>
    * If no such listeners exist, this method returns an empty array.
    * @param listenerType the type of listeners requested; this parameter
    * should specify an interface that descends from
    * <code>java.util.EventListener</code>
    * @return an array of all objects registered as
    * <code><em>Foo</em>Listener</code>s on this component,
    * or an empty array if no such
    * listeners have been added
    * @exception ClassCastException if <code>listenerType</code>
    * doesn't specify a class or interface that implements
    * <code>java.util.EventListener</code>
    public EventListener[] getListeners(Class listenerType) {
    return listenerList.getListeners(listenerType);
    * Returns the <code>Vector</code> of <code>Vectors</code>
    * that contains the table's
    * data values. The vectors contained in the outer vector are
    * each a single row of values. In other words, to get to the cell
    * at row 1, column 5: <p>
    * <code>((Vector)getDataVector().elementAt(1)).elementAt(5);</code><p>
    * @return the vector of vectors containing the tables data values
    public Vector getDataVector() {
    return dataVector;
    private static Vector nonNullVector(Vector v) {
    return (v != null) ? v : new Vector();
    * Replaces the current <code>dataVector</code> instance variable
    * with the new Vector of rows, <code>dataVector</code>.
    * <code>columnIdentifiers</code> are the names of the new
    * columns. The first name in <code>columnIdentifiers</code> is
    * mapped to column 0 in <code>dataVector</code>. Each row in
    * <code>dataVector</code> is adjusted to match the number of
    * columns in <code>columnIdentifiers</code>
    * either by truncating the <code>Vector</code> if it is too long,
    * or adding <code>null</code> values if it is too short.
    * <p>Note that passing in a <code>null</code> value for
    * <code>dataVector</code> results in unspecified behavior,
    * an possibly an exception.
    * @param dataVector the new data vector
    * @param columnIdentifiers the names of the columns
    public void setDataVector(Vector dataVector, Vector columnIdentifiers) {
    this.dataVector = nonNullVector(dataVector);
    this.columnIdentifiers = nonNullVector(columnIdentifiers);
    justifyRows(0, getRowCount());
    fireTableStructureChanged();
    * Replaces the value in the <code>dataVector</code> instance
    * variable with the values in the array <code>dataVector</code>.
    * The first index in the <code>Object[][]</code>
    * array is the row index and the second is the column index.
    * <code>columnIdentifiers</code> are the names of the new columns.
    * @param dataVector          the new data vector
    * @param columnIdentifiers     the names of the columns
    public void setDataVector(Object[][] dataVector, Object[] columnIdentifiers) {
    setDataVector(convertToVector(dataVector), convertToVector(columnIdentifiers));
    * Equivalent to <code>fireTableChanged</code>.
    * @param event the change event
    public void newDataAvailable(TableModelEvent event) {
    fireTableChanged(event);
    // Manipulating rows
    private void justifyRows(int from, int to) {
    // Sometimes the MyTreeTableModel is subclassed
    // instead of the AbstractTableModel by mistake.
    // Set the number of rows for the case when getRowCount
    // is overridden.
    dataVector.setSize(getRowCount());
    for (int i = from; i < to; i++) {
    if (dataVector.elementAt(i) == null) {
    dataVector.setElementAt(new Vector(), i);
    ((Vector)dataVector.elementAt(i)).setSize(getColumnCount());
    * Ensures that the new rows have the correct number of columns.
    * This is accomplished by using the <code>setSize</code> method in
    * <code>Vector</code> which truncates vectors
    * which are too long, and appends <code>null</code>s if they
    * are too short.
    * This method also sends out a <code>tableChanged</code>
    * notification message to all the listeners.
    * @param e this <code>TableModelEvent</code> describes
    * where the rows were added.
    *                    If <code>null</code> it assumes
    * all the rows were newly added
    public void newRowsAdded(TableModelEvent e) {
    justifyRows(e.getFirstRow(), e.getLastRow() + 1);
    fireTableChanged(e);
    * Equivalent to <code>fireTableChanged</code>.
    * @param event the change event
    public void rowsRemoved(TableModelEvent event) {
    fireTableChanged(event);
    * Obsolete as of Java 2 platform v1.3. Please use <code>setRowCount</code> instead.
    * Sets the number of rows in the model. If the new size is greater
    * than the current size, new rows are added to the end of the model
    * If the new size is less than the current size, all
    * rows at index <code>rowCount</code> and greater are discarded. <p>
    * @param rowCount the new number of rows
    public void setNumRows(int rowCount) {
    int old = getRowCount();
    if (old == rowCount) {
    return;
    dataVector.setSize(rowCount);
    if (rowCount <= old) {
    fireTableRowsDeleted(rowCount, old-1);
    else {
    justifyRows(old, rowCount);
    fireTableRowsInserted(old, rowCount-1);
    * Sets the number of rows in the model. If the new size is greater
    * than the current size, new rows are added to the end of the model
    * If the new size is less than the current size, all
    * rows at index <code>rowCount</code> and greater are discarded. <p>
    public void setRowCount(int rowCount) {
    setNumRows(rowCount);
    * Adds a row to the end of the model. The new row will contain
    * <code>null</code> values unless <code>rowData</code> is specified.
    * Notification of the row being added will be generated.
    * @param rowData optional data of the row being added
    public void addRow(Vector rowData) {
    insertRow(getRowCount(), rowData);
    * Adds a row to the end of the model. The new row will contain
    * <code>null</code> values unless <code>rowData</code> is specified.
    * Notification of the row being added will be generated.
    * @param rowData optional data of the row being added
    public void addRow(Object[] rowData) {
    addRow(convertToVector(rowData));
    * Inserts a row at <code>row</code> in the model. The new row
    * will contain <code>null</code> values unless <code>rowData</code>
    * is specified. Notification of the row being added will be generated.
    * @param row the row index of the row to be inserted
    * @param rowData optional data of the row being added
    * @exception ArrayIndexOutOfBoundsException if the row was invalid
    public void insertRow(int row, Vector rowData) {
    dataVector.insertElementAt(rowData, row);
    justifyRows(row, row+1);
    fireTableRowsInserted(row, row);
    * Inserts a row at <code>row</code> in the model. The new row
    * will contain <code>null</code> values unless <code>rowData</code>
    * is specified. Notification of the row being added will be generated.
    * @param row the row index of the row to be inserted
    * @param rowData optional data of the row being added
    * @exception ArrayIndexOutOfBoundsException if the row was invalid
    public void insertRow(int row, Object[] rowData) {
    insertRow(row, convertToVector(rowData));
    private static int gcd(int i, int j) {
    return (j == 0) ? i : gcd(j, i%j);
    private static void rotate(Vector v, int a, int b, int shift) {
    int size = b - a;
    int r = size - shift;
    int g = gcd(size, r);
    for(int i = 0; i < g; i++) {
    int to = i;
    Object tmp = v.elementAt(a + to);
    for(int from = (to + r) % size; from != i; from = (to + r) % size) {
    v.setElementAt(v.elementAt(a + from), a + to);
    to = from;
    v.setElementAt(tmp, a + to);
    * Moves one or more rows from the inlcusive range <code>start</code> to
    * <code>end</code> to the <code>to</code> position in the model.
    * After the move, the row that was at index <code>start</code>
    * will be at index <code>to</code>.
    * This method will send a <code>tableChanged</code> notification
    * message to all the listeners. <p>
    * <pre>
    * Examples of moves:
    * <p>
    * 1. moveRow(1,3,5);
    * a|B|C|D|e|f|g|h|i|j|k - before
    * a|e|f|g|h|B|C|D|i|j|k - after
    * <p>
    * 2. moveRow(6,7,1);
    * a|b|c|d|e|f|G|H|i|j|k - before
    * a|G|H|b|c|d|e|f|i|j|k - after
    * <p>
    * </pre>
    * @param start the starting row index to be moved
    * @param end the ending row index to be moved
    * @param to the destination of the rows to be moved
    * @exception ArrayIndexOutOfBoundsException if any of the elements
    * would be moved out of the table's range
    public void moveRow(int start, int end, int to) {
    int shift = to - start;
    int first, last;
    if (shift < 0) {
    first = to;
    last = end;
    else {
    first = start;
    last = to + end - start;
    rotate(dataVector, first, last + 1, shift);
    fireTableRowsUpdated(first, last);
    * Removes the row at <code>row</code> from the model. Notification
    * of the row being removed will be sent to all the listeners.
    * @param row the row index of the row to be removed
    * @exception ArrayIndexOutOfBoundsException if the row was invalid
    public void removeRow(int row) {
    dataVector.removeElementAt(row);
    fireTableRowsDeleted(row, row);
    // Manipulating columns
    * Replaces the column identifiers in the model. If the number of
    * <code>newIdentifier</code>s is greater than the current number
    * of columns, new columns are added to the end of each row in the model.
    * If the number of <code>newIdentifier</code>s is less than the current
    * number of columns, all the extra columns at the end of a row are
    * discarded. <p>
    * @param newIdentifiers vector of column identifiers. If
    *                    <code>null</code>, set the model
    * to zero columns
    public void setColumnIdentifiers(Vector columnIdentifiers) {
    setDataVector(dataVector, columnIdentifiers);
    * Replaces the column identifiers in the model. If the number of
    * <code>newIdentifier</code>s is greater than the current number
    * of columns, new columns are added to the end of each row in the model.
    * If the number of <code>newIdentifier</code>s is less than the current
    * number of columns, all the extra columns at the end of a row are
    * discarded. <p>
    * @param newIdentifiers array of column identifiers.
    *                    If <code>null</code>, set
    * the model to zero columns
    public void setColumnIdentifiers(Object[] newIdentifiers) {
    setColumnIdentifiers(convertToVector(newIdentifiers));
    * Sets the number of columns in the model. If the new size is greater
    * than the current size, new columns are added to the end of the model
    * with <code>null</code> cell values.
    * If the new size is less than the current size, all columns at index
    * <code>columnCount</code> and greater are discarded.
    * @param columnCount the new number of columns in the model
    public void setColumnCount(int columnCount) {
    columnIdentifiers.setSize(columnCount);
    justifyRows(0, getRowCount());
    fireTableStructureChanged();
    * Adds a column to the model. The new column will have the
    * identifier <code>columnName</code>, which may be null. This method
    * will send a
    * <code>tableChanged</code> notification message to all the listeners.
    * This method is a cover for <code>addColumn(Object, Vector)</code> which
    * uses <code>null</code> as the data vector.
    * @param columnName the identifier of the column being added
    public void addColumn(Object columnName) {
    addColumn(columnName, (Vector)null);
    * Adds a column to the model. The new column will have the
    * identifier <code>columnName</code>, which may be null.
    * <code>columnData</code> is the
    * optional vector of data for the column. If it is <code>null</code>
    * the column is filled with <code>null</code> values. Otherwise,
    * the new data will be added to model starting with the first
    * element going to row 0, etc. This method will send a
    * <code>tableChanged</code> notification message to all the listeners.
    * @param columnName the identifier of the column being added
    * @param columnData optional data of the column being added
    public void addColumn(Object columnName, Vector columnData) {
    columnIdentifiers.addElement(columnName);
    if (columnData != null) {
    int columnSize = columnData.size();
    if (columnSize > getRowCount()) {
    dataVector.setSize(columnSize);
    justifyRows(0, getRowCount());
    int newColumn = getColumnCount() - 1;
    for(int i = 0; i < columnSize; i++) {
    Vector row = (Vector)dataVector.elementAt(i);
    row.setElementAt(columnData.elementAt(i), newColumn);
    else {
    justifyRows(0, getRowCount());
    fireTableStructureChanged();
    * Adds a column to the model. The new column will have the
    * identifier <code>columnName</code>. <code>columnData</code> is the
    * optional array of data for the column. If it is <code>null</code>
    * the column is filled with <code>null</code> values. Otherwise,
    * the new data will be added to model starting with the first
    * element going to row 0, etc. This method will send a
    * <code>tableChanged</code> notification message to all the listeners.
    public void addColumn(Object columnName, Object[] columnData) {
    addColumn(columnName, convertToVector(columnData));
    // Implementing the TableModel interface
    * Returns the number of rows in this data table.
    * @return the number of rows in the model
    public int getRowCount() {
    return dataVector.size();
    * Returns the number of columns in this data table.
    * @return the number of columns in the model
    public int getColumnCount() {
    return columnIdentifiers.size();
    * Returns the column name.
    * @return a name for this column using the string value of the
    * appropriate member in <code>columnIdentifiers</code>.
    * If <code>columnIdentifiers</code> does not have an entry
    * for this index, returns the default
    * name provided by the superclass
    public String getColumnName(int column) {
    Object id = null;
    // This test is to cover the case when
    // getColumnCount has been subclassed by mistake ...
    if (column < columnIdentifiers.size()) {
    id = columnIdentifiers.elementAt(column);
    return (id == null) ? getDefaultColumnName(column)
    : id.toString();
    * Returns true regardless of parameter values.
    * @param row the row whose value is to be queried
    * @param column the column whose value is to be queried
    * @return true
    public boolean isCellEditable(int row, int column) {
    return true;
    * Returns an attribute value for the cell at <code>row</code>
    * and <code>column</code>.
    * @param row the row whose value is to be queried
    * @param column the column whose value is to be queried
    * @return the value Object at the specified cell
    * @exception ArrayIndexOutOfBoundsException if an invalid row or
    * column was given
    public Object getValueAt(int row, int column) {
    Vector rowVector = (Vector)dataVector.elementAt(row);
    return rowVector.elementAt(column);
    * Sets the object value for the cell at <code>column</code> and
    * <code>row</code>. <code>aValue</code> is the new value. This method
    * will generate a <code>tableChanged</code> notification.
    * @param aValue the new value; this can be null
    * @param row the row whose value is to be changed
    * @param column the column whose value is to be changed
    * @exception ArrayIndexOutOfBoundsException if an invalid row or
    * column was given
    public void setValueAt(Object aValue, int row, int column) {
    Vector rowVector = (Vector)dataVector.elementAt(row);
    rowVector.setElementAt(aValue, column);
    fireTableCellUpdated(row, column);
    // Protected Methods
    * Returns a vector that contains the same objects as the array.
    * @param anArray the array to be converted
    * @return the new vector; if <code>anArray</code> is <code>null</code>,
    *                    returns <code>null</code>
    protected static Vector convertToVector(Object[] anArray) {
    if (anArray == null) {
    return null;
    Vector v = new Vector(anArray.length);
    for (int i=0; i < anArray.length; i++) {
    v.addElement(anArray[i]);
    return v;
    * Returns a vector of vectors that contains the same objects as the array.
    * @param anArray the double array to be converted
    * @return the new vector of vectors; if <code>anArray</code> is
    *                    <code>null</code>, returns <code>null</code>
    protected static Vector convertToVector(Object[][] anArray) {
    if (anArray == null) {
    return null;
    Vector v = new Vector(anArray.length);
    for (int i=0; i < anArray.length; i++) {
    v.addElement(convertToVector(anArray[i]));
    return v;

  • Image in a JTable (2)

    Thanks for the code, it does compile but it does not display the image.
    Maybe if you give a look at the whole code it will be easier.
    You said to use MyTableRenderer() but maybe you meant MyCellRenderer().
    What do you think ?
    import java.awt.*;
    import java.awt.event.*;
    import javax.swing.*;
    import javax.swing.table.*;
    import javax.swing.event.*;
    import java.io.*;
    import java.beans.*;
    import javax.imageio.*;
    public class yearPlannerBean extends JFrame implements ListSelectionListener,ActionListener,Serializable
    private String dayNames[] = {"Saturday","Sunday","Monday","Tuesday","Wednesday","Thursday","Friday"};
    private String engMonths[] = {"January","February","March","April","May","June","July","August","September","October","November","December"};
    private String spaMonths[] = {"Enero", "Febrero", "Marzo", "Abril", "Mayo", "Junio", "Julio", "Agosto", "Septiembre", "Octubre", "Noviembre", "Diciembre"};
    private String spadays[]={"S�bado", "Domingo", "Lunes", "Martes", "Mi�rcoles", "Jueves", "Viernes"};
    private String itaMonths[] = {"Gennaio","Febbraio","Marzo","Aprile","Maggio","Giugno","luglio","Agosto","Settembre","Ottobre","Novembre","Dicembre"};
    private String itadays[]={"Sabato","Domenica","Lunedi","Martedi","Mercoledi","Giovedi","Venerdi"};
    private Object fieldValues[][];
    private String panelTitle;
    private JPanel container;
    private JPanel languages;
    private JPanel choice;
    private JTable planner;
    private String days[];
    private JScrollPane scrollPane;
    private int month;
    private int noOfDays;
    private int year;
    private Zellar zell;
    private PropertyChangeSupport support;
    private Image icon;
    private next bbnext;
    private previous bbpre;
    private JLabel lan;
    private JLabel curry;
    private JTextField curye;
    private JList linlist;
    public yearPlannerBean()
    panelTitle = ("Year Planner");
    setTitle(panelTitle);
    setSize(300,300);
    month = 0;
    noOfDays = 0;
    year = 2003;
    zell = new Zellar(1,month,year);
    container = new JPanel();
    container.setLayout(new BorderLayout());
    languages = new JPanel();
    choice= new JPanel();
    lan= new JLabel("Select Language: ");
    String[] words={"English","Italian","Spanish"};
    JList linlist= new JList(words);
    JScrollPane sc =new JScrollPane(linlist);
    linlist.addListSelectionListener(this);
    planner = new JTable(getFieldValues(),setColumnNames());
    planner.setRowHeight(100);
    planner.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
    planner.setRowSelectionAllowed(true);
    planner.setColumnSelectionAllowed(true);
    //myTable.setDefaultRenderer(Object.class, new MyTableRenderer());
    planner.setDefaultRenderer(Object.class,new MyCellRenderer());
    scrollPane = new JScrollPane(planner);
    bbnext= new next();
    bbpre=new previous();
    bbnext.addActionListener(this);
    bbpre.addActionListener(this);
    getContentPane().setLayout(new BorderLayout());
    container.add(scrollPane,BorderLayout.CENTER);
    curry= new JLabel("Current Year");
    curye= new JTextField(5);
    curye.setText(Integer.toString(year));
    choice.add(bbpre);
    choice.add(bbnext);
    languages.add(curry);
    languages.add(curye);
    languages.add(lan);
    languages.add(linlist);
    container.add(choice,BorderLayout.SOUTH);
    container.add(languages,BorderLayout.NORTH);
    setContentPane(container);
    pack();
    addWindowListener(new WindowAdapter()
    public void windowClosing(WindowEvent e)
    System.exit(0);
    }//End constructor
    public String[] setColumnNames()
    days = new String[38];
    int count = 0;
    int index = 0;
    for (index = 0; index < 38; index++)
    if (index == 0)
    days[index] = "";
    else
    days[index] = dayNames[count];
    if (count != 6)
    count++;
    else
    count = 0;
    return days;
    }//End getColumnNames
    public Object[][] getFieldValues()
    int countY = 0;
    int countX = 0;
    String firstDay = "";
    int dayInt;
    int dayCount = 0;
    int tempCount = 0;
    fieldValues = new Object[12][38];
    for (countX = 0; countX < 38; countX++)
    for (countY = 0; countY < 12; countY++)
    monthToInt(engMonths[countY]);
    firstDay = zell.getFirstDay(month,year);
    dayInt = dayToInt(firstDay);
    for (month = 1; month < 12; month++)
    tempCount = 1;
    for (dayCount = dayInt; dayCount < (noOfDays+dayInt); dayCount++)
    if (countX == 0)
    fieldValues[countY][countX] = engMonths[countY];
    else
    //fieldValues.setCellRenderer(new acellrenderer());
    fieldValues[countY][dayCount]="" + tempCount;//setIcon(new ImageIcon(icon));
    tempCount++;
    return fieldValues;
    }//End getFieldValues
    public void monthToInt(String monthIn)
    boolean temp = false;
    if (monthIn == "January")
    month = 1;
    noOfDays = 31;
    else
    if (monthIn == "February")
    month = 2;
    if ((year % 4 == 0) && ((year % 100 != 0) || (year % 400 == 0)))
    noOfDays = 29;
    else
    noOfDays = 28;
    else
    if (monthIn == "March")
    month = 3;
    noOfDays = 31;
    else
    if (monthIn == "April")
    month = 4;
    noOfDays = 30;
    else
    if (monthIn == "May")
    month = 5;
    noOfDays = 31;
    else
    if (monthIn == "June")
    month = 6;
    noOfDays = 30;
    else
    if (monthIn == "July")
    month = 7;
    noOfDays = 31;
    else
    if (monthIn == "August")
    month = 8;
    noOfDays = 31;
    else
    if (monthIn == "September")
    month = 9;
    noOfDays = 30;
    else
    if (monthIn == "October")
    month = 10;
    noOfDays = 31;
    else
    if (monthIn == "November")
    month = 11;
    noOfDays = 30;
    else
    if (monthIn == "December")
    month = 12;
    noOfDays = 31;
    }//End monthToInt
    public int dayToInt(String dayIn)
    int dayOut = 0;
    if (dayIn == "Saturday")
    dayOut = 1;
    else
    if (dayIn == "Sunday")
    dayOut = 2;
    else
    if (dayIn == "Monday")
    dayOut = 3;
    else
    if (dayIn == "Tuesday")
    dayOut = 4;
    else
    if (dayIn == "Wednesday")
    dayOut = 5;
    else
    if (dayIn == "Thursday")
    dayOut = 6;
    else
    if (dayIn == "Friday")
    dayOut = 7;
    return dayOut;
    }//End dayToInt
    /*class acellrenderer extends DefaultTableCellRenderer
    public acellrenderer()
    super();
    public Component getTableCellRendererComponent (JTable planner)
    Component component=super.getTableCellRenderer();
    String filepa;
    filepa="caley.GIF";
    ImageIcon nn;
    component.setIcon(new ImageIcon(filepa));
    return component;
    static class MyCellRenderer extends DefaultTableCellRenderer
    { final Icon icon = new ImageIcon("caley.gif");
    public MyCellRenderer ()
    super();
    public void setValue(Object value)
    if(value == null)
    { setText("");
    setIcon(icon);
    else
    setText(String.valueOf(value));
    public void actionPerformed(ActionEvent event)
    Object source=event.getSource();
    int a;
    if (source==bbnext)
    // button next pressed
    a=Integer.parseInt(curye.getText());
    curye.setText(Integer.toString(a+1));
    else
    if (source==bbpre)
    // button previous pressed
    a=Integer.parseInt(curye.getText());
    curye.setText(Integer.toString(a-1));
    private int getindex(String astring)
    int index=-1;
    if(astring.toUpperCase().equals("ENGLISH"))
    index=0;
    else
    if (astring.toUpperCase().equals("ITALIAN"))
    index=1;
    else
    index=2;
    return index;
    public void valueChanged(ListSelectionEvent event)
    JList source=(JList)event.getSource();
    Object asel;
    int index;
    if (source==linlist)
    asel=linlist.getSelectedValue();
    index=getindex((String)asel);
    if (index==0)
    // set header in English;
    else
    if (index==1)
    // set header in Italian;
    else
    if (index==2)
    // set header in Spanish;
    public static void main(String args[])
    yearPlannerBean test = new yearPlannerBean();
    test.setVisible(true);
    }//End Main
    }//End class

    There are too many unresolved classes in your code for me to use it. Here is a simple example of putting an icon in a table.import java.awt.event.*;
    import java.awt.*;
    import javax.swing.*;
    import javax.swing.table.*;
    public class Test extends JFrame {
      public Test() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        Container content = getContentPane();
        String[] head = {"One","Two","Three"};
        String[][] data = {{"R1-C1","R1-C2","R1-C3"},
                           {"R1-C1","R1-C2","R1-C3"},
                           {"R1-C1","R1-C2","R1-C3"}};
        JTable jt = new JTable(data,head);
        content.add(new JScrollPane(jt), BorderLayout.CENTER);
        jt.setDefaultRenderer(Object.class,
                              new MyCellRenderer(new ImageIcon("C:\\duke\\t1.gif")));
        setSize(200, 200);
        show();
      public static void main(String args[]) { new Test(); }
    class MyCellRenderer extends JLabel implements TableCellRenderer {
      Icon icon;
      public MyCellRenderer(Icon icon) { this.icon = icon; }
      public Component getTableCellRendererComponent(
                                JTable table, Object color,
                                boolean isSelected, boolean hasFocus,
                                int row, int column) {
        if ((row+column)%3==0) setIcon(null);
        else setIcon(icon);
        return this;
    }

  • Must click then click and drag for JTable Drag and Drop

    Hi All,
    I've been using Java 1.4 to drag and drop data between two tables in our application. Basically I need to drag the data from individual rows of the source table and insert it into one of the cells in the new table. This works absolutely fine and has made a huge improvement to this portion of our app. I've included example source code below that does a similar thing by transferring data from one table and inserting it into another (it's quite big and also not as well done as the example in our real app but unfortunately I can't send the source for that).
    The thing I've noticed though is that in order to start dragging data I need to click to select it and then press and hold the mouse button to start dragging, whereas under W**dows and just about every other OS you can just press and hold and start dragging straight away. If you try this with a JTable though it just changes the rows you have selected so the drag and drop works but feels a bit clunky and amateurish. I'd like to do something about this such that it works like Windows Explorer (or similar) where you can just press the mouse button and start dragging.
    Any help would be greatly appreciated - and if anybody finds the code useful you're more than welcome to it. Note that the business end of this is CustomTransferHandler.java - this will show you how to insert data at a specific position in a JTable, it's a bit of a faff but not too bad once you've got it sussed.
    Thanks,
    Bart Read
    ===============================================================
    TestFrame.java
    * TestFrame.java
    * Created on October 21, 2002, 4:59 PM
    import java.awt.*;
    import java.awt.datatransfer.*;
    import java.awt.dnd.*;
    import java.awt.event.*;
    import java.util.TooManyListenersException;
    import javax.swing.*;
    * @author  readb
    public class TestFrame extends javax.swing.JFrame
         private static final String [] NAMES     = {
              "John", "Geoff", "Madeleine", "Maria", "Flanders",
              "Homer", "Marge", "Bart", "Lisa", "Weird Baby" };
         private JTable source;
         private JTable dest;
         private MyTableModel     sourceModel;
         private MyTableModel     destModel;
         private Clipboard          clipboard;
         /** Creates a new instance of TestFrame */
         public TestFrame()
              clipboard = getToolkit().getSystemClipboard();
              Container c = getContentPane();
              c.setLayout( new BorderLayout( 40, 40 ) );
              source = new MyJTable();
              sourceModel = new MyTableModel();
              source.setModel( sourceModel );
              source.setDragEnabled( true );
              CustomTransferHandler handler = new CustomTransferHandler( "Source handler" );
              source.setTransferHandler( handler );
              try
                   source.getDropTarget().addDropTargetListener( handler );
              catch ( TooManyListenersException tmle )
                   tmle.printStackTrace();
              dest = new MyJTable();
              destModel = new MyTableModel();
              dest.setModel( destModel );
              dest.setDragEnabled( true );
              handler = new CustomTransferHandler( "Dest handler" );
              dest.setTransferHandler( handler );
              try
                   dest.getDropTarget().addDropTargetListener( handler );
              catch ( TooManyListenersException tmle )
                   tmle.printStackTrace();
              c.add( new JScrollPane( source ), BorderLayout.WEST );
              c.add( new JScrollPane( dest ), BorderLayout.EAST );
              populate();
         private void populate( MyTableModel model )
              for ( int index = 0; index < NAMES.length; ++index )
                   model.setRow( index, new DataRow( index + 1, NAMES[ index ] ) );
         private void populate()
              populate( sourceModel );
              populate( destModel );
         public static void main( String [] args )
              TestFrame app = new TestFrame();
              app.addWindowListener(
                   new WindowAdapter() {
                        public void windowClosing( WindowEvent we )
                             System.exit( 0 );
              app.pack();
              app.setSize( 1000, 600 );
              app.show();
         private class MyJTable extends JTable
              public boolean getScrollableTracksViewportHeight()
                   Component parent = getParent();
                   if (parent instanceof JViewport)
                        return parent.getHeight() > getPreferredSize().height;
                   return false;
    }=====================================================================
    MyTableModel.java
    * MyTableModel.java
    * Created on October 21, 2002, 4:43 PM
    import java.util.ArrayList;
    * @author  readb
    public class MyTableModel extends javax.swing.table.AbstractTableModel
         private static final int          NUMBER               = 0;
         private static final int          NAME               = 1;
         private static final String []     COLUMN_HEADINGS     = { "Number", "Name" };
         private ArrayList data;
         /** Creates a new instance of MyTableModel */
         public MyTableModel()
              super();
              data = new ArrayList();
         public int getColumnCount()
              return COLUMN_HEADINGS.length;
         public String getColumnName( int index )
              return COLUMN_HEADINGS[ index ];
         public Class getColumnClass( int index )
              switch ( index )
                   case NUMBER:
                        return Integer.class;
                   case NAME:
                        return String.class;
                   default:
                        throw new IllegalArgumentException( "Illegal column index: " + index );
         public int getRowCount()
              return ( null == data ? 0 : data.size() );
         public Object getValueAt( int row, int column )
              DataRow dataRow = ( DataRow ) data.get( row );
              switch ( column )
                   case NUMBER:
                        return new Integer( dataRow.getNumber() );
                   case NAME:
                        return dataRow.getName();
                   default:
                        throw new IllegalArgumentException( "Illegal column index: " + column );
         public void addRow( DataRow row )
              int rowIndex = data.size();
              data.add( row );
              fireTableRowsInserted( rowIndex, rowIndex );
         public void addRows( DataRow [] rows )
              int firstRow = data.size();
              for ( int index = 0; index < rows.length; ++index )
                   data.add( rows[ index ] );
              fireTableRowsInserted( firstRow, data.size() - 1 );
         public void setRow( int index, DataRow row )
              if ( index == data.size() )
                   data.add( row );
              else
                   data.set( index, row );
              fireTableRowsUpdated( index, index );
         public void insertRows( int index, DataRow [] rows )
              for ( int rowIndex = rows.length - 1; rowIndex >= 0; --rowIndex )
                   data.add( index, rows[ rowIndex ] );
              fireTableRowsInserted( index, index + rows.length - 1 );
         public DataRow getRow( int index )
              return ( DataRow ) data.get( index );
         public DataRow removeRow( int index )
              DataRow retVal = ( DataRow ) data.remove( index );
              fireTableRowsDeleted( index, index );
              return retVal;
         public boolean removeRow( DataRow row )
              int index = data.indexOf( row );
              boolean retVal = data.remove( row );
              fireTableRowsDeleted( index, index );
              return retVal;
         public void removeRows( DataRow [] rows )
              for ( int index = 0; index < rows.length; ++index )
                   data.remove( rows[ index ] );
              fireTableDataChanged();
    }=====================================================================
    DataRow.java
    * DataRow.java
    * Created on October 21, 2002, 4:41 PM
    import java.io.Serializable;
    * @author  readb
    public class DataRow implements Serializable
         private int          number;
         private String     name;
         /** Creates a new instance of DataRow */
         public DataRow( int number, String name )
              this.number = number;
              this.name = name;
         public int getNumber()
              return number;
         public String getName()
              return name;
         public String toString()
              return String.valueOf( number ) + ": " + name;
    }======================================================================
    CustomTransferHandler.java
    * CustomTransferHandler.java
    * Created on October 22, 2002, 8:36 AM
    import java.awt.*;
    import java.awt.datatransfer.Clipboard;
    import java.awt.datatransfer.ClipboardOwner;
    import java.awt.datatransfer.DataFlavor;
    import java.awt.datatransfer.Transferable;
    import java.awt.datatransfer.UnsupportedFlavorException;
    import java.awt.dnd.*;
    import java.awt.event.InputEvent;
    import java.io.IOException;
    import java.util.Arrays;
    import javax.swing.Icon;
    import javax.swing.ImageIcon;
    import javax.swing.JComponent;
    import javax.swing.JTable;
    import javax.swing.TransferHandler;
    * @author  readb
    public class CustomTransferHandler
                   extends TransferHandler
                   implements Transferable, ClipboardOwner, DropTargetListener
         public static final DataFlavor     ROW_ARRAY_FLAVOR     = new DataFlavor( DataRow[].class, "Multiple rows of data" );
         private String               name;
         private ImageIcon          myIcon;
         private     DataRow []          data;
         private boolean               clipboardOwner                    = false;
         private int                    rowIndex                         = -1;
         /** Creates a new instance of CustomTransferHandler */
         public CustomTransferHandler( String name )
              this.name = name;
         public boolean canImport( JComponent comp, DataFlavor [] transferFlavors )
              System.err.println( "CustomTransferHandler::canImport" );
              if ( comp instanceof JTable && ( ( JTable ) comp ).getModel() instanceof MyTableModel )
                   for ( int index = 0; index < transferFlavors.length; ++index )
                        if ( ! transferFlavors[ index ].equals( ROW_ARRAY_FLAVOR ) )
                             return false;
                   return true;
              else
                   return false;
         protected Transferable createTransferable( JComponent c )
              System.err.println( "CustomTransferHandler::createTransferable" );
              if ( ! ( c instanceof JTable ) || ! ( ( ( JTable ) c ).getModel() instanceof MyTableModel ) )
                   return null;
              this.data = null;
              JTable               table     = ( JTable ) c;
              MyTableModel     model     = ( MyTableModel ) table.getModel();
              Clipboard          cb          = table.getToolkit().getSystemClipboard();
              cb.setContents( this, this );
              clipboardOwner = true;
              int [] selectedRows = table.getSelectedRows();
              Arrays.sort( selectedRows );
              data = new DataRow[ selectedRows.length ];
              for ( int index = 0; index < data.length; ++index )
                   data[ index ] = model.getRow( selectedRows[ index ] );
              return this;
         public void exportAsDrag( JComponent comp, InputEvent e, int action )
              super.exportAsDrag( comp, e, action );
              Clipboard          cb          = comp.getToolkit().getSystemClipboard();
              cb.setContents( this, this );
         protected void exportDone( JComponent source, Transferable data, int action )
              System.err.println( "CustomTransferHandler::exportDone" );
              if ( TransferHandler.MOVE == action && source instanceof JTable && ( ( JTable ) source ).getModel() instanceof MyTableModel )
                   JTable table = ( JTable ) source;
                   MyTableModel model = ( MyTableModel ) table.getModel();
                   int [] selected = table.getSelectedRows();
                   for ( int index = selected.length - 1; index >= 0; --index )
                        model.removeRow( selected[ index ] );
         public void exportToClipboard( JComponent comp, Clipboard clip, int action )
              System.err.println( "CustomTransferHandler::exportToClipboard" );
         public int getSourceActions( JComponent c )
              System.err.println( "CustomTransferHandler::getSourceActions" );
              if ( ( c instanceof JTable ) && ( ( JTable ) c ).getModel() instanceof MyTableModel )
                   return MOVE;
              else
                   return NONE;
          *     I've commented this out because it doesn't appear to work in any case.
          *     The image isn't null but as far as I can tell this method is never
          *     invoked.
    //     public Icon getVisualRepresentation( Transferable t )
    //          System.err.println( "CustomTransferHandler::getVisualRepresentation" );
    //          if ( t instanceof CustomTransferHandler )
    //               if ( null == myIcon )
    //                    try
    //                         myIcon = new ImageIcon( getClass().getClassLoader().getResource( "dragimage.gif" ) );
    //                    catch ( Exception e )
    //                         System.err.println( "CustomTransferHandler::getVisualRepresentation: exception loading image" );
    //                         e.printStackTrace();
    //                    if ( null == myIcon )
    //                         System.err.println( "CustomTransferHandler::getVisualRepresentation: myIcon is still NULL" );
    //               return myIcon;
    //          else
    //               return null;
         public boolean importData( JComponent comp, Transferable t )
              System.err.println( "CustomTransferHandler::importData" );
              super.importData( comp, t );
              if ( ! ( comp instanceof JTable ) )
                   return false;
              if ( ! ( ( ( JTable ) comp ).getModel() instanceof MyTableModel ) )
                   return false;
              if ( clipboardOwner )
                   return false;
              if ( !t.isDataFlavorSupported( ROW_ARRAY_FLAVOR ) )
                   return false;
              try
                   data = ( DataRow [] ) t.getTransferData( ROW_ARRAY_FLAVOR );
                   return true;
              catch ( IOException ioe )
                   data = null;
                   return false;
              catch ( UnsupportedFlavorException ufe )
                   data = null;
                   return false;
         public Object getTransferData(DataFlavor flavor) throws UnsupportedFlavorException, IOException
              System.err.println( "MyTransferable::getTransferData" );
              if ( flavor.equals( ROW_ARRAY_FLAVOR ) )
                   return data;
              else
                   throw new UnsupportedFlavorException( flavor );
         public DataFlavor[] getTransferDataFlavors()
              System.err.println( "MyTransferable::getTransferDataFlavors" );
              DataFlavor [] flavors = new DataFlavor[ 1 ];
              flavors[ 0 ] = ROW_ARRAY_FLAVOR;
              return flavors;
         public boolean isDataFlavorSupported( DataFlavor flavor )
              System.err.println( "MyTransferable::isDataFlavorSupported" );
              return flavor.equals( ROW_ARRAY_FLAVOR );
         public void lostOwnership( Clipboard clipboard, Transferable transferable )
              clipboardOwner = false;
         /** Called while a drag operation is ongoing, when the mouse pointer enters
          * the operable part of the drop site for the <code>DropTarget</code>
          * registered with this listener.
          * @param dtde the <code>DropTargetDragEvent</code>
         public void dragEnter(DropTargetDragEvent dtde)
         /** Called while a drag operation is ongoing, when the mouse pointer has
          * exited the operable part of the drop site for the
          * <code>DropTarget</code> registered with this listener.
          * @param dte the <code>DropTargetEvent</code>
         public void dragExit(DropTargetEvent dte)
         /** Called when a drag operation is ongoing, while the mouse pointer is still
          * over the operable part of the drop site for the <code>DropTarget</code>
          * registered with this listener.
          * @param dtde the <code>DropTargetDragEvent</code>
         public void dragOver(DropTargetDragEvent dtde)
         /** Called when the drag operation has terminated with a drop on
          * the operable part of the drop site for the <code>DropTarget</code>
          * registered with this listener.
          * <p>
          * This method is responsible for undertaking
          * the transfer of the data associated with the
          * gesture. The <code>DropTargetDropEvent</code>
          * provides a means to obtain a <code>Transferable</code>
          * object that represents the data object(s) to
          * be transfered.<P>
          * From this method, the <code>DropTargetListener</code>
          * shall accept or reject the drop via the
          * acceptDrop(int dropAction) or rejectDrop() methods of the
          * <code>DropTargetDropEvent</code> parameter.
          * <P>
          * Subsequent to acceptDrop(), but not before,
          * <code>DropTargetDropEvent</code>'s getTransferable()
          * method may be invoked, and data transfer may be
          * performed via the returned <code>Transferable</code>'s
          * getTransferData() method.
          * <P>
          * At the completion of a drop, an implementation
          * of this method is required to signal the success/failure
          * of the drop by passing an appropriate
          * <code>boolean</code> to the <code>DropTargetDropEvent</code>'s
          * dropComplete(boolean success) method.
          * <P>
          * Note: The data transfer should be completed before the call  to the
          * <code>DropTargetDropEvent</code>'s dropComplete(boolean success) method.
          * After that, a call to the getTransferData() method of the
          * <code>Transferable</code> returned by
          * <code>DropTargetDropEvent.getTransferable()</code> is guaranteed to
          * succeed only if the data transfer is local; that is, only if
          * <code>DropTargetDropEvent.isLocalTransfer()</code> returns
          * <code>true</code>. Otherwise, the behavior of the call is
          * implementation-dependent.
          * <P>
          * @param dtde the <code>DropTargetDropEvent</code>
         public void drop(DropTargetDropEvent dtde)
              System.err.println( "CustomTransferHandler::drop" );
              Component c = dtde.getDropTargetContext().getDropTarget().getComponent();
              if ( ! ( c instanceof JComponent ) )
                   dtde.rejectDrop();
                   return;
              JComponent comp = ( JComponent ) c;
              if ( ! ( c instanceof JTable ) || ! ( ( ( JTable ) c ).getModel() instanceof MyTableModel ) )
                   dtde.rejectDrop();
                   return;
              dtde.acceptDrop( TransferHandler.MOVE );
              //     THIS is such a mess -- you can't do the following because
              //     getTransferable() throws an (undocumented) exception - what's that
              //     all about.
    //          Transferable t = dtde.getTransferable();
    //               if ( !t.isDataFlavourSupported( ROW_ARRAY_FLAVOR ) )
    //                    dtde.rejectDrop();
    //                    return false;
    //          TransferHandler handler = comp.getTransferHandler();
    //          if ( null == handler || ! handler.importData( comp, t ) )
    //               dtde.rejectDrop();
    //               return;
              Point p = dtde.getLocation();
              JTable table = ( JTable ) comp;
              rowIndex = table.rowAtPoint( p );
              //     So you have to do this instead and use the data that's been
              //     stored in the data member via import data.  Total mess.
              if ( null == data )
                   dtde.rejectDrop();
                   return;
              MyTableModel model = ( MyTableModel ) table.getModel();
              if ( rowIndex == -1 )
                   model.addRows( data );
              else
                   model.insertRows( rowIndex, data );
              dtde.acceptDrop( TransferHandler.MOVE );
         /** Called if the user has modified
          * the current drop gesture.
          * <P>
          * @param dtde the <code>DropTargetDragEvent</code>
         public void dropActionChanged(DropTargetDragEvent dtde)
    }

    Hi again,
    Well I've tried using the MouseListener / MouseMotionListener approach but it doesn't quite seem to work, although it does get the events correctly. I think the reason is that it doesn't interact correctly with the Java DnD machinery which is something that V.V hinted at. It's something that I may need to look into if / when I have more time available.
    I have to say though that I haven't had any problems with scrollbars - we're making fairly heavy use of large tables and if you drag over a table with a scroll bar and move to the top or bottom then it scrolls as you would expect and allows you to drop the data where you like. For this situation I've used pretty much the same approach as for the toy example above except that I've implemented separate source and destination TransferHandlers (the source table is read-only, and it really doesn't make sense to allow people to drag from the destination table so I've essentially split the functionality of the example handler down the middle).
    I'm not actually particularly in favour of messing too much with the mechanics of DnD, more because of lack of time than anything else. Guess I'll just have to put up with this for the moment. Doesn't help that DnD is so poorly documented by Sun.
    Thanks for all your help.
    Bart

  • JTable data back-up (re-visited)

    Hi!
    I need to persist the data in my jTable rows and columns. Right now I get and set them with java preferences with two x and y loops ... this works fine.
    but ..... is there a way to save to a file the jTable row and column data without first extracting the row and column data cell for cell?
    ie; to serialize only the cell data?

    Thanks!
    Is there an example code for me to look at? (didnt see much on Google so far)

  • JTable data back-up

    Hi!
    I'm currently using preferences API to back-up my jTable (lots of coding).
    can I back up my entire jTable with single serialization file?
        try {
          FileOutputStream fos = new FileOutputStream (jTable);
          ObjectOutputStream oos = new ObjectOutputStream (fos);
          oos.writeObject (table.ser); 
          oos.flush();
          oos.close();
              } catch (IOException e) {
                e.printStackTrace();
    }

    can you show me an example of how that is done?Sorry, I don't feel like writing the code, but I
    would guess that opening a file, writing a loop,
    write some data, and close the file is done inless
    than 30-40 lines of code.
    KajWhen you say "write a loop" do you infer that the
    data must be extracted by row and column coordinates?Yes

  • Image in a JTable

    Hello, i am trying to display an image.gif in a JTable using cellrenderer but i always get an error message. Everybodys help its always accepted.
    I did paste just a few parts of the code since its very long. In the cellrenderer class i have scored out those 3 lines.
    In all the books that i have read ( quite a few there is not a single full coded program that shows how to insert a picture in a cell of the table).
    What i am trying to do is, when creating the table insert all pictures in all cells and then with a loop insert the relevant data.
    In other words the picture should appear only in cells containing no data.
         planner = new JTable(getFieldValues(),setColumnNames());
              planner.setRowHeight(30);
              planner.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
              planner.setRowSelectionAllowed(true);
              planner.setColumnSelectionAllowed(true);
              planner.setDefaultRenderer(ImageIcon.class,new cellrenderer());
         class cellrenderer implements TableCellRenderer
              public Component getTableCellRendererComponent (JTable planner, Object xw, boolean isSelected,boolean hasFocus, int row, int column)
                   String cd;
                   cd="xx.gif";
                   //xw= new ImageIcon(cd);
                   //panel.setBackground(ImageIcon(xw));
                   //setImage(new ImageIcon(cd));
                   return panel;
                   JPanel panel=new JPanel();

    Thanks for the code, it does compile but it does not display the image.
    Maybe if you give a look at the whole code it will be easier.
    You said to use MyTableRenderer() but maybe you meant MyCellRenderer().
    What do you think ?
    import java.awt.*;
    import java.awt.event.*;
    import javax.swing.*;
    import javax.swing.table.*;
    import javax.swing.event.*;
    import java.io.*;
    import java.beans.*;
    import javax.imageio.*;
    public class yearPlannerBean extends JFrame implements ListSelectionListener,ActionListener,Serializable
         private String dayNames[] = {"Saturday","Sunday","Monday","Tuesday","Wednesday","Thursday","Friday"};
         private String engMonths[] = {"January","February","March","April","May","June","July","August","September","October","November","December"};
         private String spaMonths[] = {"Enero", "Febrero", "Marzo", "Abril", "Mayo", "Junio", "Julio", "Agosto", "Septiembre", "Octubre", "Noviembre", "Diciembre"};
         private String spadays[]={"S�bado", "Domingo", "Lunes", "Martes", "Mi�rcoles", "Jueves", "Viernes"};
         private String itaMonths[] = {"Gennaio","Febbraio","Marzo","Aprile","Maggio","Giugno","luglio","Agosto","Settembre","Ottobre","Novembre","Dicembre"};
         private String itadays[]={"Sabato","Domenica","Lunedi","Martedi","Mercoledi","Giovedi","Venerdi"};
         private Object fieldValues[][];
         private String panelTitle;
         private JPanel container;
         private JPanel languages;
         private JPanel choice;
         private JTable planner;
         private String days[];
         private JScrollPane scrollPane;
         private int month;
         private int noOfDays;
         private int year;
         private Zellar zell;
         private PropertyChangeSupport support;
         private Image icon;
         private next bbnext;
         private previous bbpre;
         private JLabel lan;
         private JLabel curry;
         private JTextField curye;
         private JList linlist;
         public yearPlannerBean()
              panelTitle = ("Year Planner");
              setTitle(panelTitle);
              setSize(300,300);
              month = 0;
              noOfDays = 0;
              year = 2003;
              zell = new Zellar(1,month,year);
              container = new JPanel();
              container.setLayout(new BorderLayout());
              languages = new JPanel();
              choice= new JPanel();
              lan= new JLabel("Select Language: ");
              String[] words={"English","Italian","Spanish"};
              JList linlist= new JList(words);
              JScrollPane sc =new JScrollPane(linlist);
              linlist.addListSelectionListener(this);
              planner = new JTable(getFieldValues(),setColumnNames());
              planner.setRowHeight(100);
              planner.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
              planner.setRowSelectionAllowed(true);
              planner.setColumnSelectionAllowed(true);
              //myTable.setDefaultRenderer(Object.class, new MyTableRenderer());
              planner.setDefaultRenderer(Object.class,new MyCellRenderer());
              scrollPane = new JScrollPane(planner);
              bbnext= new next();
              bbpre=new previous();
              bbnext.addActionListener(this);
              bbpre.addActionListener(this);
              getContentPane().setLayout(new BorderLayout());
              container.add(scrollPane,BorderLayout.CENTER);
              curry= new JLabel("Current Year");
              curye= new JTextField(5);
              curye.setText(Integer.toString(year));
              choice.add(bbpre);
              choice.add(bbnext);
              languages.add(curry);
              languages.add(curye);
              languages.add(lan);
              languages.add(linlist);
              container.add(choice,BorderLayout.SOUTH);
              container.add(languages,BorderLayout.NORTH);
              setContentPane(container);
              pack();
              addWindowListener(new WindowAdapter()
                   public void windowClosing(WindowEvent e)
                        System.exit(0);
         }//End constructor
         public String[] setColumnNames()
              days = new String[38];
              int count = 0;
              int index = 0;
              for (index = 0; index < 38; index++)
                   if (index == 0)
                        days[index] = "";
                   else
                        days[index] = dayNames[count];
                        if (count != 6)
                             count++;
                        else
                             count = 0;
              return days;
         }//End getColumnNames
         public Object[][] getFieldValues()
              int countY = 0;
              int countX = 0;
              String firstDay = "";
              int dayInt;
              int dayCount = 0;
              int tempCount = 0;
              fieldValues = new Object[12][38];
              for (countX = 0; countX < 38; countX++)
                   for (countY = 0; countY < 12; countY++)
                        monthToInt(engMonths[countY]);
                        firstDay = zell.getFirstDay(month,year);
                        dayInt = dayToInt(firstDay);
                        for (month = 1; month < 12; month++)
                             tempCount = 1;
                             for (dayCount = dayInt; dayCount < (noOfDays+dayInt); dayCount++)
                                  if (countX == 0)
                                       fieldValues[countY][countX] = engMonths[countY];
                                  else
                                       //fieldValues.setCellRenderer(new acellrenderer());
                                       fieldValues[countY][dayCount]="" + tempCount;//setIcon(new ImageIcon(icon));
                                  tempCount++;
              return fieldValues;
         }//End getFieldValues
         public void monthToInt(String monthIn)
              boolean temp = false;
              if (monthIn == "January")
                   month = 1;
                   noOfDays = 31;
              else
                   if (monthIn == "February")
                        month = 2;
                        if ((year % 4 == 0) && ((year % 100 != 0) || (year % 400 == 0)))
                             noOfDays = 29;
                        else
                             noOfDays = 28;
                   else
                        if (monthIn == "March")
                             month = 3;
                             noOfDays = 31;
                        else
                             if (monthIn == "April")
                                  month = 4;
                                  noOfDays = 30;
                             else
                                  if (monthIn == "May")
                                       month = 5;
                                       noOfDays = 31;
                                  else
                                       if (monthIn == "June")
                                            month = 6;
                                            noOfDays = 30;
                                       else
                                            if (monthIn == "July")
                                                 month = 7;
                                                 noOfDays = 31;
                                            else
                                                 if (monthIn == "August")
                                                      month = 8;
                                                      noOfDays = 31;
                                                 else
                                                      if (monthIn == "September")
                                                           month = 9;
                                                           noOfDays = 30;
                                                      else
                                                           if (monthIn == "October")
                                                                month = 10;
                                                                noOfDays = 31;
                                                           else
                                                                if (monthIn == "November")
                                                                     month = 11;
                                                                     noOfDays = 30;
                                                                else
                                                                     if (monthIn == "December")
                                                                          month = 12;
                                                                          noOfDays = 31;
         }//End monthToInt
         public int dayToInt(String dayIn)
              int dayOut = 0;
              if (dayIn == "Saturday")
                   dayOut = 1;
              else
                   if (dayIn == "Sunday")
                        dayOut = 2;
                   else
                        if (dayIn == "Monday")
                             dayOut = 3;
                        else
                             if (dayIn == "Tuesday")
                                  dayOut = 4;
                             else
                                  if (dayIn == "Wednesday")
                                       dayOut = 5;
                                  else
                                       if (dayIn == "Thursday")
                                            dayOut = 6;
                                       else
                                            if (dayIn == "Friday")
                                                 dayOut = 7;
              return dayOut;
         }//End dayToInt
         /*class acellrenderer extends DefaultTableCellRenderer
              public acellrenderer()
                   super();
              public Component getTableCellRendererComponent (JTable planner)
                   Component component=super.getTableCellRenderer();
                   String filepa;
                   filepa="caley.GIF";
                   ImageIcon nn;
                   component.setIcon(new ImageIcon(filepa));
                   return component;
    static class MyCellRenderer extends DefaultTableCellRenderer
    {    final Icon icon = new ImageIcon("caley.gif");
         public MyCellRenderer ()
              super();
         public void setValue(Object value)
         if(value == null)
              {             setText("");
              setIcon(icon);
              else
                   setText(String.valueOf(value));
    public void actionPerformed(ActionEvent event)
         Object source=event.getSource();
         int a;
         if (source==bbnext)
         // button next pressed
         a=Integer.parseInt(curye.getText());
         curye.setText(Integer.toString(a+1));
         else
              if (source==bbpre)
                   // button previous pressed
                   a=Integer.parseInt(curye.getText());
                   curye.setText(Integer.toString(a-1));
    private int getindex(String astring)
         int index=-1;
         if(astring.toUpperCase().equals("ENGLISH"))
              index=0;
              else
              if (astring.toUpperCase().equals("ITALIAN"))
              index=1;
              else
              index=2;
              return index;
         public void valueChanged(ListSelectionEvent event)
              JList source=(JList)event.getSource();
              Object asel;
              int index;
              if (source==linlist)
                   asel=linlist.getSelectedValue();
                   index=getindex((String)asel);
                   if (index==0)
                        // set header in English;
                        else
                             if (index==1)
                             // set header in Italian;
                             else
                                  if (index==2)
                                  // set header in Spanish;
         public static void main(String args[])
              yearPlannerBean test = new yearPlannerBean();
              test.setVisible(true);
         }//End Main
    }//End class

  • How to resize data in JTable?

    Hi all,
    I wish to provide a resize button on an application which will resize the data in a table (in most cases just text) as well as the table containing it. Is it possible to directly resize the table or must I change the renderer to draw all of the data bigger? I'm also not sure how to increase the width of the table. Any help would be much appreciated.
    package gui;
    import java.awt.BorderLayout;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import javax.swing.JButton;
    import javax.swing.JFrame;
    import javax.swing.JPanel;
    import javax.swing.JScrollPane;
    import javax.swing.JTable;
    import javax.swing.SwingUtilities;
    import javax.swing.table.DefaultTableModel;
    public class Resizer extends JFrame
         * @see java.io.Serializable
        public static final long serialVersionUID = 0;
         * Table containing data
        private JTable table = null;
         * Scroll pane containing table
        private JScrollPane scroller = null;
         * Name of button to increase text size
        private static final String INCREASE = "Increase";
         * Name of button to decrease text size
        private static final String DECREASE = "Decrease";
         * An increment to use when resizing
        private static final int INCREMENT = 5;
        public Resizer()
            setTitle("Resizer");
            setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            setSize(300,200);
            getContentPane().setLayout(new BorderLayout());
            // Add the table and its contents
            table = createTable();
            scroller = new JScrollPane(table);
            getContentPane().add(scroller, BorderLayout.CENTER);
            // Add buttons to resize
            JButton increase = new JButton(INCREASE);
            increase.addActionListener(new ButtonListener());
            JButton decrease = new JButton(DECREASE);
            decrease.addActionListener(new ButtonListener());
            JPanel panel = new JPanel();
            panel.add(increase);
            panel.add(decrease);
            getContentPane().add(panel, BorderLayout.SOUTH);
            // Show this window
            setLocationRelativeTo(null);
            setVisible(true);
        private JTable createTable()
            JTable t = new JTable();
            t.setModel(new MyModel());
            // Row 1
            t.getModel().setValueAt("John", 0, 0);
            t.getModel().setValueAt(new Integer(1), 0, 1);
            // Row 2
            t.getModel().setValueAt("Chris", 1, 0);
            t.getModel().setValueAt(new Integer(2), 1, 1);
            // Row 3
            t.getModel().setValueAt("Susan", 2, 0);
            t.getModel().setValueAt(new Integer(3), 2, 1);
            return t;
        private class MyModel extends DefaultTableModel
            private static final long serialVersionUID = 2;
            public MyModel()
                this.setColumnCount(2);
                this.setRowCount(3);
            public String getColumnName(int col)
                switch(col)
                case 0:
                    return "Name";
                case 1:
                    return "Number";
                default:
                    return "Oops";
        private class ButtonListener implements ActionListener
            public void actionPerformed(ActionEvent ae)
                    if (((JButton)ae.getSource()).getText().equals(INCREASE))
                        increaseTable();  
                    else if (((JButton)ae.getSource()).getText().equals(DECREASE))
                        decreaseTable();
        private void increaseTable()
            this.setSize(this.getWidth()+INCREMENT, this.getHeight()+INCREMENT);
            table.setRowHeight(table.getRowHeight()+INCREMENT);
            table.setSize(table.getWidth()+INCREMENT, table.getHeight()+INCREMENT);
        private void decreaseTable()
            this.setSize(this.getWidth()-INCREMENT, this.getHeight()-INCREMENT);
            table.setRowHeight(table.getRowHeight()-INCREMENT);
            table.setSize(table.getWidth()-INCREMENT, table.getHeight()-INCREMENT);
        public static void main(String[] args)
            SwingUtilities.invokeLater(new Runnable()
                public void run()
                    new Resizer();
    }Using JDK 1.4.2

    Thanks all.
    The solution was to use setFont() on the table and its headers. Here's what I put in to increase and descrease the table size (for future reference).
         * Increases the size of everything in the table
        private void increaseTable()
            table.setRowHeight(table.getRowHeight() + INCREMENT);
            table.setSize(table.getWidth() + INCREMENT, table.getHeight() + INCREMENT);
            for (int i = 0; i < table.getColumnCount(); i++)
                TableColumn col = table.getColumnModel().getColumn(i);
                col.setWidth(col.getWidth() + INCREMENT / table.getColumnCount());
            Font headerFont = table.getTableHeader().getFont();
            table.getTableHeader().setFont(headerFont.deriveFont(headerFont.getSize2D()+INCREMENT));
            Font dataFont = table.getFont();
            table.setFont(dataFont.deriveFont(dataFont.getSize2D() + INCREMENT));
         * Decreases the size of everything in the table
        private void decreaseTable()
            if (table.getRowHeight() > INCREMENT)
                table.setRowHeight(table.getRowHeight() - INCREMENT);
                table.setSize(table.getWidth() - INCREMENT, table.getHeight() - INCREMENT);
                for (int i = 0; i < table.getColumnCount(); i++)
                    TableColumn col = table.getColumnModel().getColumn(i);
                    col.setWidth(col.getWidth() - INCREMENT / table.getColumnCount());
                Font headerFont = table.getTableHeader().getFont();
                table.getTableHeader().setFont(headerFont.deriveFont(headerFont.getSize2D()-INCREMENT));
                Font dataFont = table.getFont();
                table.setFont(dataFont.deriveFont(dataFont.getSize2D() - INCREMENT));
        }

  • Need help serializing an AbstractTableModel for a JTable with cell editing.

    Fun times are ahead. Here we go!
    I have a JTable that contains data I'd like to serialize out to a file to be restored and viewed later.
    So I tried saving the AbstractTableModel subclass out to a file. Whenever I do this, I get the following error message:
    java.io.NotSerializableException: javax.swing.JTable$CellEditorRemover
    Now I know for fact that serializing an AbstractTableModel that was installed in a JTable without cell editing works just fine (my old code did exactly that). As a result, I think that the code that handles events in the AbstractTableModel contains references back out to the JTable, which causes the JTable to be saved no matter what (even though I'm just interested in saving the TableModel only). It causes a bigger file than normal, but file size is not an issue. The only issue I have is that CellEditorRemover (an undocumented inner class of JTable), which is automatically installed for JTables with editable cells, is not serializable.
    This leads to the following questions:
    1. Is there a way to avoid serialization/deserialization of the CellEditorRemover inner class of JTable?
    2. Is there a way to save an AbstractTableModel without saving all of the event listeners associated with it?
    I think an answer to either of these questions would go a long way towards solving my problem. Otherwise, I'll resign myself to weeping silently in the corner of my office.
    Thanks!

    I would suggest that if you can you only save the
    data... but i would do this by using the
    externalizable interface.
    What you will need to do is have the
    writeExternal(ObjectOutputStream out) and
    readExternal(ObjectOutputStream out) methods in your
    class. These will be responsiable for saving the
    data.
    Here's an example of what you can do in these
    methods... this is just a little tidbit from a program
    i've written.public void writeExternal(ObjectOutput out) throws
    IOException {
              out.writeInt(size);
              out.writeObject(drawName);
              out.writeInt(playersLength);
    for(int i = 0; i < playersLength; i++)
    ) out.writeObject(players);
              out.writeInt(seedsLength);
    for(int i = 0; i < seedsLength; i++)
    ) out.writeObject(seeds[i]);
              out.writeInt(drawLength);
    for(int i = 0; i < drawLength; i++)
    ) out.writeObject(draw[i]);
    public void readExternal(ObjectInput in) throws
    IOException, ClassNotFoundException {
              size = in.readInt();
              drawName = (String)in.readObject();
              playersLength = in.readInt();
    for(int i = 0; i < playersLength; i++) players[i] =
    = (String)in.readObject();
              seedsLength = in.readInt();
    for(int i = 0; i < seedsLength; i++) seeds[i] =
    = (String)in.readObject();
              drawLength = in.readInt();
    for(int i = 0; i < drawLength; i++) draw[i] =
    = (String)in.readObject();
    You can now use your class as you would a Serializable
    class, but it will only save the data
    Hope this helped
    webaf409java
    I forgot to add some critical information in my original post. My apologies. :(
    I've thought about using Externalizable, but am hesitant to use it because the application would no longer be able to read in files using the old save format (ie, AbstractTableModels for JTables without CellEditorRemovers ).  I want to preserve the ability to read the old saved AbstractTableModel formats if possible. 
    Do you know of a way to revert to the default deserialization mechanism from readExternal?  This way, during deserialization, I could do a quick test on the object being read and have the ability to default to the regular deserialization mechanism if the object is of the old type or continue with the new Externalizable stuff if the object is one of the new type.  Maintaining file compatibility is key.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       

  • How to use setDragEnabled in a JTable with Textbox

    Hi all,
    I am new to swings and have a very urgent doubt.I want to select and drag the row of the JTable and place it in the text box.How do I do it.An Example program will solve my query.Please Its Very urgent.
    thanks in advance
    With kind Regards
    Satheesh.K

    Hey Lynx,
    The 'you are running this application for the first time' thing is normal as most applications will put a few plist files and settings in a couple of places in your home /library folders. I wonder though about having to re-serialize...Have you installed them in other places rather than your /Applications folder? If not, some applications will ask if you want to install for all users or not- but I'd say that user speciffic applications are about 20-30% of apps...-ish ^^
    Maybe running the installers and installing for allusers would save you a bit of a hassle going forward?
    hope it helps

  • JTable: scrollabel Cell

    Hi,
    I've already come up with this, but up to now I haven't received any answer.
    What do I have to do, to can I scroll a non editable cell within a JTable?
    Besides the CellRenderer, I have to implement the CellEditor. But I something is wrong, it just won't work.
    code snippet from celleditor:
    public class ScrollPaneCellEditor extends JScrollPane implements TableCellEditor, Serializable{
    JEditorPane pane;
    JScrollPane scrollpane;
    StringBuffer sb;
    /** Creates a new instance of IconTableCellRenderer */
    public ScrollPaneCellEditor() {      
    pane = new JEditorPane();
    sb = new StringBuffer(); }
    public boolean isCellEditable(java.util.EventObject anEvent) {
    return false;
    public java.awt.Component getTableCellEditorComponent(javax.swing.JTable table, Object value, boolean isSelected, int row, int column) {
    pane.setText(value.toString());
    super.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);
    JViewport vp = new JViewport();
    vp.setScrollMode(JViewport.BLIT_SCROLL_MODE);
    vp.setView(pane);
    super.setWheelScrollingEnabled(true);
    if (isSelected){           
    scrollpane.setViewport(vp);
    if(hasFocus()){
    scrollpane.setViewportView(vp);
    super.add(vp);
    return this;
    Best regards,
    Andi

    Hi bukibu79 ,
    In JTable cells are not a component
    it is a painting using graphics, when you edit a cell this time the editable cell only a component so you cann't edit two cells at a time.
    Another one is suppose you assume that cell are compoents then how can add a single component into two different cells. What actualy do on JTable is , JTable get the component form the renderer and paint this renderer component into the cell's rectangle area and move this component to some non visible area.
    If your table cell is non editable then the editor doesn't work because there are no need to get editor for JTable.

  • Jtable column sorting

    Hi all,
    I have jtable wirh setAutoCreateRowSorter(true); . The columns with Double object are sorting correctly. One column values are object of our class "Carat". But this column is not sorting like numbers. What are the changes I have to do to sort like number or Double.?
    my custom class Carat is
    import java.io.Serializable;
    import common.Common;
    public class Carat implements Serializable{
         private static final long serialVersionUID = 7876408747596231364L;
         Double carat;
         public Carat(double carat){
              this.carat = new Double(carat);
         public double doubleValue(){
              return carat.doubleValue();
         public void setCarat(Double carat){
              this.carat = carat;
         //here round to 3 decimal
         public String toString(){
              return Common.roundCarat(carat.doubleValue());
         public Double getDoubleValue(){
              return carat;
         public Carat getDifference(Carat cat){
              return new Carat(this.carat.doubleValue() - cat.doubleValue());
         public boolean equals(Carat cart){
              if(this.carat.doubleValue() == cart.doubleValue()){
                   return true;
              return true;
         public int compareTo(Carat anotherDouble) {
            return Double.compare(carat.doubleValue(), anotherDouble.doubleValue());
    }Ant suggestions ...plz help....

    You have to implement the Compareable-Interface.
    Also the compareTo-Implementation is wrong:
    use Object for the parameter type.
    public class Carat implements Serializable, Compareable {
    public int compareTo( Object that ){
    }Read the book Java "Effective Java" :)
    IMHO this post is not in the correct thread...

Maybe you are looking for