This discussion is archived
0 Replies Latest reply: Sep 28, 2012 7:55 AM by 965090 RSS

Mapping of JTable Rows and columns and paint it to the JPanel

965090 Newbie
Currently Being Moderated
Hi,

I am using JTable and graphics object to draw the JTable on JPanel. But due to some lack of measurement I am not able to draw table cells correctly.

Apart from this on changing the fontSize I have to redraw it according to the requirement. But when the data size increases it draws absurdly.

I am using jTable.getCellRect() api to get the row width and height. Please help to redraw a JTable cell row and height on JPanel.

I am also attaching a sample code with this mail.

Thanks,
Ajay
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.*;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import javax.swing.table.*;
import java.util.*;
import java.awt.*;

public class SimpleTableDemo extends JPanel {
    private boolean DEBUG = false;
       private int spacing = 6;
       private Map columnSizes = new HashMap();
       String[] columnNames = {"First Name",
                                "Last Name",
                                "Sport",
                                "# of Years",
                                "Vegetarian"};

        Object[][] data = {
         {"Kathy", "Smith",
          "SnowboardingXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX", new Integer(5), new Boolean(false)},
         {"John", "Doe",
          "Rowing", new Integer(3), new Boolean(true)},
         {"Sue", "Black",
          "Knitting", new Integer(2), new Boolean(false)},
         {"Jane", "White",
          "Speed reading", new Integer(20), new Boolean(true)},
         {"Joe", "Brown",
          "Pool", new Integer(10), new Boolean(false)}
        };

        final JTable table = new JTable(data, columnNames);
          Panel1 panel;

    public SimpleTableDemo() {
        super(new GridLayout(3,0));

      
        table.setPreferredScrollableViewportSize(new Dimension(500, 70));
        //table.setFillsViewportHeight(true);

        if (DEBUG) {
            table.addMouseListener(new MouseAdapter() {
                public void mouseClicked(MouseEvent e) {
                    printDebugData(table);
                }
            });
        }

        //Create the scroll pane and add the table to it.
        JScrollPane scrollPane = new JScrollPane(table);

        //Add the scroll pane to this panel.
        add(scrollPane);

        panel = new Panel1();
        Rectangle rect = table.getCellRect(0,0,true);

          panel.setX(table.getWidth());
          panel.setY(0);
        panel.setWidth(rect.width);
          panel.setHeight(rect.height);
        panel.setStr(table.getModel().getValueAt(0,0).toString());
          panel.setModel(table);

          add(panel);

        final JComboBox jNumberComboBoxSize = new JComboBox();
          jNumberComboBoxSize.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "11", "12", "14", "16", "18", "20", "24", "30", "36", "48", "72" }));
        jNumberComboBoxSize.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
               jNumberComboBoxSizeActionPerformed(jNumberComboBoxSize);
            }
        });

          JPanel panel2 = new JPanel();
          panel2.add(jNumberComboBoxSize);
          
          add(panel2);
          adjustColumns();

    }

     private void jNumberComboBoxSizeActionPerformed(JComboBox jNumberComboBoxSize)
     {
        int fontSize = Integer.parseInt(jNumberComboBoxSize.getSelectedItem().toString());
          table.setRowHeight(fontSize);
          table.setFont(new Font("Serif", Font.BOLD, fontSize));
          Rectangle rect = table.getCellRect(0,0,true);
          panel.setX(0);
          panel.setY(0);
       // panel.setWidth(rect.width);
          panel.setHeight(rect.height);
        panel.setStr(table.getModel().getValueAt(0,0).toString());
          panel.setModel(table);
          panel.repaint();
          table.revalidate();
     }

    private void printDebugData(JTable table) {
        int numRows = table.getRowCount();
        int numCols = table.getColumnCount();
        javax.swing.table.TableModel model = table.getModel();

        System.out.println("Value of data: ");
        for (int i=0; i < numRows; i++) {
            System.out.print("    row " + i + ":");
            for (int j=0; j < numCols; j++) {
                System.out.print("  " + model.getValueAt(i, j));
            }
            System.out.println();
        }
        System.out.println("--------------------------");
    }
    
      /*
      *  Adjust the widths of all the columns in the table
      */
     public void adjustColumns()
     {
          TableColumnModel tcm = table.getColumnModel();

          for (int i = 0; i < tcm.getColumnCount(); i++)
          {
               adjustColumn(i);
          }
     }
    
     /*
      *  Adjust the width of the specified column in the table
      */
     public void adjustColumn(final int column)
     {
          TableColumn tableColumn = table.getColumnModel().getColumn(column);

          if (! tableColumn.getResizable()) return;

          int columnHeaderWidth = getColumnHeaderWidth( column );
          int columnDataWidth   = getColumnDataWidth( column );
          int preferredWidth    = Math.max(columnHeaderWidth, columnDataWidth);
        panel.setWidth(preferredWidth);
          updateTableColumn(column, preferredWidth);
     }
    
     /*
      *  Calculated the width based on the column name
      */
     private int getColumnHeaderWidth(int column)
     {
          TableColumn tableColumn = table.getColumnModel().getColumn(column);
          Object value = tableColumn.getHeaderValue();
          TableCellRenderer renderer = tableColumn.getHeaderRenderer();

          if (renderer == null)
          {
               renderer = table.getTableHeader().getDefaultRenderer();
          }

          Component c = renderer.getTableCellRendererComponent(table, value, false, false, -1, column);
          return c.getPreferredSize().width;
     }
    
     /*
      *  Calculate the width based on the widest cell renderer for the
      *  given column.
      */
     private int getColumnDataWidth(int column)
     {
          int preferredWidth = 0;
          int maxWidth = table.getColumnModel().getColumn(column).getMaxWidth();

          for (int row = 0; row < table.getRowCount(); row++)
          {
              preferredWidth = Math.max(preferredWidth, getCellDataWidth(row, column));

               //  We've exceeded the maximum width, no need to check other rows

               if (preferredWidth >= maxWidth)
                   break;
          }

          return preferredWidth;
     }
    
     /*
      *  Get the preferred width for the specified cell
      */
     private int getCellDataWidth(int row, int column)
     {
          //  Inovke the renderer for the cell to calculate the preferred width

          TableCellRenderer cellRenderer = table.getCellRenderer(row, column);
          Component c = table.prepareRenderer(cellRenderer, row, column);
          int width = c.getPreferredSize().width + table.getIntercellSpacing().width;

          return width;
     }
     
     /*
      *  Update the TableColumn with the newly calculated width
      */
     private void updateTableColumn(int column, int width)
     {
          final TableColumn tableColumn = table.getColumnModel().getColumn(column);
           
          if (! tableColumn.getResizable()) return;

          width += spacing;

          //  Don't shrink the column width

          width = Math.max(width, tableColumn.getPreferredWidth());
          

          columnSizes.put(tableColumn, new Integer(tableColumn.getWidth()));
          table.getTableHeader().setResizingColumn(tableColumn);
          tableColumn.setWidth(width);
     }

    /**
     * Create the GUI and show it.  For thread safety,
     * this method should be invoked from the
     * event-dispatching thread.
     */
    private static void createAndShowGUI() {
        //Create and set up the window.
        JFrame frame = new JFrame("SimpleTableDemo");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        //Create and set up the content pane.
        SimpleTableDemo newContentPane = new SimpleTableDemo();
        newContentPane.setOpaque(true); //content panes must be opaque
        frame.setContentPane(newContentPane);

        //Display the window.
        frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        //Schedule a job for the event-dispatching thread:
        //creating and showing this application's GUI.
        javax.swing.SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                createAndShowGUI();
            }
        });
    }
}

class Panel1 extends JPanel
{
    int x;
     int y;
     int width;
     int height;
     String str;
     JTable model;

    public void setModel(JTable model)
     {
       this.model = model;
     }

     public void setX(int x)
     {
          this.x = x;
     }
   
    public void setY(int y)
     {
          this.y = y;
     }

     public void setWidth(int w)
     {
          this.width = w;
     }
     
    public void setHeight(int h)
     {
          this.height = h;
     }

     public void setStr(String s)
     {
          this.str = s;
     }

    public void paint(Graphics g)
     {
         super.paint(g);
          int initX= 0;
          for(int row=0;row < 5; ++row)
          {
               initX = x;
               for (int col=0;col < 5;++col)
               {
                    g.drawRect(x,y,width,height);
                    g.drawString(model.getModel().getValueAt(row,col).toString(),x + 10,y + 10);
                    x = x + width;
               }
            x = initX;
               y = y + height;

          }
          
     }
};

Legend

  • Correct Answers - 10 points
  • Helpful Answers - 5 points