为java JTable中的特定单元着色

时间:2013-08-07 14:00:06

标签: java swing jtable tablecellrenderer

我想通过输入行号和列号来为JTable上的特定单元着色。

例如,我有这个代码,意味着为第一个单元格着色= 0,列= 0,但它不起作用

package functions_classes;

import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.*;
import javax.swing.border.LineBorder;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import javax.swing.table.*;

public class RemoveAddRows extends JFrame {

     static DefaultTableCellRenderer stringRenderer;
     static Component c;
    private static final long serialVersionUID = 1L;
    private Object[] columnNames = {"Type", "Company", "Shares", "Price"};
    private Object[][] data = {
        {"Buy", "IBM", Integer.valueOf(1000), Double.valueOf(80.50)},
        {"Sell", "MicroSoft", Integer.valueOf(2000), Double.valueOf(6.25)},
        {"Sell", "Apple", Integer.valueOf(3000), Double.valueOf(7.35)},
        {"Buy", "Nortel", Integer.valueOf(4000), Double.valueOf(20.00)}
    };
    public static JTable table;

    private DefaultTableModel model;
    private javax.swing.Timer timer = null;

    public RemoveAddRows() {
        model = new DefaultTableModel(data, columnNames) {
            private static final long serialVersionUID = 1L;

            @Override
            public Class getColumnClass(int column) {
                return getValueAt(0, column).getClass();
            }
        };

        table = new JTable(model) {
            private static final long serialVersionUID = 1L;

            @Override
            public Component prepareRenderer(TableCellRenderer renderer, int row, int column) {
                 c = super.prepareRenderer(renderer, row, column);                     
                 System.out.println("la valeur de row egale "+row);                     
                 System.out.println("la valeur de column egale "+column);
                if (isRowSelected(0) && isColumnSelected(0)) {
                   // ((JComponent) c).setBorder(new LineBorder(Color.red));
                    ((JComponent) c).setBackground(Color.RED);
                    }                      
                return c;
            }
        };

        stringRenderer = (DefaultTableCellRenderer) table.getDefaultRenderer(String.class);
        stringRenderer.setHorizontalAlignment(SwingConstants.CENTER);
        ListSelectionModel rowSelMod = table.getSelectionModel();

        rowSelMod.addListSelectionListener(new ListSelectionListener() {
            @Override
            public void valueChanged(ListSelectionEvent e) {
                int row = table.getSelectedRow();
                int col = table.getSelectedColumn();
                String str = "Selected Row(s): ";
                int[] rows = table.getSelectedRows();
                for (int i = 0; i < rows.length; i++) {
                    str += rows[i] + " ";
                }
                str += "Selected Column(s): ";
                int[] cols = table.getSelectedColumns();
                for (int i = 0; i < cols.length; i++) {
                    str += cols[i] + " ";
                }
                str += "Selected Cell: " + table.getSelectedRow() + ", " + table.getSelectedColumn();
                System.out.println(str);
                Object value = table.getValueAt(row, col);
                System.out.println(String.valueOf(value));
            }
        });
        table.setPreferredScrollableViewportSize(table.getPreferredSize());
        JScrollPane scrollPane = new JScrollPane(table);
        add(scrollPane);
        JButton button1 = new JButton("Remove all rows");
        button1.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                if (model.getRowCount() > 0) {
                    for (int i = model.getRowCount() - 1; i > -1; i--) {
                        model.removeRow(i);
                    }
                }
                System.out.println("model.getRowCount() --->" + model.getRowCount());
            }
        });
        JButton button2 = new JButton("Add new rows");
        button2.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                start();
            }
        });
        JPanel southPanel = new JPanel();
        southPanel.add(button1);
        southPanel.add(button2);
        add(southPanel, BorderLayout.SOUTH);
    }

    private void start() {
        timer = new javax.swing.Timer(2500, updateCol());
        timer.start();
    }

    public Action updateCol() {
        return new AbstractAction("text load action") {
            private static final long serialVersionUID = 1L;

            @Override
            public void actionPerformed(ActionEvent e) {
                DefaultTableModel model = (DefaultTableModel) table.getModel();
                Object[] data0 = {"Buy", "IBM", Integer.valueOf(1000), Double.valueOf(80.50)};
                model.addRow(data0);
                Object[] data1 = {"Sell", "MicroSoft", Integer.valueOf(2000), Double.valueOf(6.25)};
                model.addRow(data1);
                Object[] data2 = {"Sell", "Apple", Integer.valueOf(3000), Double.valueOf(7.35)};
                model.addRow(data2);
                Object[] data3 = {"Buy", "Nortel", Integer.valueOf(4000), Double.valueOf(20.00)};
                model.addRow(data3);
                System.out.println("model.getRowCount() --->" + model.getRowCount());
                timer.stop();
                int rowIndex = table.getRowCount() - 1;
                table.changeSelection(rowIndex, 0, false, false);
            }
        };
    }

    public static void main(String[] args) {
        javax.swing.SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                RemoveAddRows frame = new RemoveAddRows();
                frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);                    

             //   table.prepareRenderer(stringRenderer, 1, 2);
                //Component c1=table.prepareRenderer((DefaultTableCellRenderer) table.getDefaultRenderer(String.class), 1,1);

               // stringRenderer = (DefaultTableCellRenderer) table.getDefaultRenderer(String.class);
               // JComponent c1=(JComponent) table.prepareRenderer(stringRenderer, 0,0);
                // c1.setBackground(Color.cyan);
            }
        });
    }
}

3 个答案:

答案 0 :(得分:4)

您需要实现自定义单元格渲染器才能执行此操作,我已经修改了一些旧代码。希望这应该有效,我已经检查过它编译,但我没有测试过它;

import javax.swing.JTable; 
import javax.swing.table.DefaultTableCellRenderer; 
import java.awt.Component;  
import java.awt.Color;
import java.util.HashMap;

public class ColorCellRenderer extends DefaultTableCellRenderer {
    class Coordinate
    {
        public int row, col;
        public Coordinate(int row, int col)
        {
            this.row=row;this.col=col;
        }
        @Override
        public boolean equals(Object o)
        {
            if(o instanceof Coordinate)
            {
                return (((Coordinate)o).row==this.row)&&(((Coordinate)o).col==this.col);
            }
            return false;
        }
        @Override
        public int hashCode()
        {//Unique until col 10000
            return col + row*10000;
        }
    }
    private HashMap<Coordinate, Color> colorMap;
    public ColorCellRenderer() { 
        super();
        colorMap = new HashMap<Coordinate, Color>();
    } 
    public Color setColor(int row, int col, Color c)
    {
        return colorMap.put(new Coordinate(row, col), c);
    }
    /** 
     * Returns the component used for drawing the cell.  This method is 
     * used to configure the renderer appropriately before drawing. 
     * 
     * @param table      - JTable object 
     * @param value      - the value of the cell to be rendered. 
     * @param isSelected - isSelected   true if the cell is to be rendered with the selection highlighted; 
     *                   otherwise false. 
     * @param hasFocus   - if true, render cell appropriately. 
     * @param row        - The row index of the cell being drawn. 
     * @param column     - The column index of the cell being drawn. 
     * @return - Returns the component used for drawing the cell. 
     */ 

    public Component getTableCellRendererComponent
    (
        JTable table,
        Object value, 
        boolean isSelected, 
        boolean hasFocus, 
        int row, 
        int column
    ) 
        {
            Component c = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
            //Get color from nested hashmap
            //We allow it to setBackground(null) as DefaultRenderer doesn't resetBackground when called again.
                if(isSelected){
                    c.setBackgroun(table.getSelectionBackground());
                }else{
                    c.setBackground(colorMap.get(new Coordinate(row, column)));
            }
                return c; 
        } 
}

答案 1 :(得分:2)

而不是:

if (isRowSelected(0) && isColumnSelected(0)) {
   // ((JComponent) c).setBorder(new LineBorder(Color.red));
   ((JComponent) c).setBackground(Color.RED);
}

使用这段代码:

c.setBackground((row == 0) && (column == 0) ? Color.RED : Color.WHITE);

答案 2 :(得分:-1)

JComponent不知道如何设置背景。 相反,您应该手动在组件上绘制颜色。

我建议您创建自己的组件:

private class CustomComponent extends JComponent{
    CustomComponent() {
            setBackground(Color.BLACK);
    }
    public void paintComponent(Graphics g) {
            g.setColor(getBackground());
            g.fillRect(0, 0, getWidth(), getHeight());
    }

}

您可以在自定义组件中进行isSelected验证,并相应地设置颜色。