【问题标题】:Invoke prepareRenderer of JTable Swing调用 JTable Swing 的 prepareRenderer
【发布时间】:2014-05-31 05:45:36
【问题描述】:

通过修改 prepareRenderer 来实现 JTable

public class MyTable extends JTable {

    private List<Client> list;

    public MyTable(TableModel model){
        super(model);
        if (model instanceof ProfitAbilityTableModel){
            list=((ProfitAbilityTableModel)model).getClients();
        }       
    }
    @Override
    public Component prepareRenderer(TableCellRenderer renderer, int rowIndex, int vColIndex){
        Component rComp=super.prepareRenderer(renderer, rowIndex, vColIndex);
        if(list!=null){
            Client client=list.get(rowIndex);
            if(client.getExpected()==client.getReceived())
                rComp.setBackground(new Color(139, 255, 182));
            else
                rComp.setBackground(new Color(255,139,147));
        }

        return rComp;
    }
}

ProfitAbilityTableModel

public class ProfitAbilityTableModel  extends AbstractTableModel{

    private String []columnNames={"Имя учетной записи", "Ф.И.О. Клиента","Адрес",
            "Получено грн.", "Предпологалось грн."};
    private List<Client> clients;

    public ProfitAbilityTableModel(List<Client> clients){
        this.clients=clients;
    }

    public ProfitAbilityTableModel(){};

    @Override
    public int getColumnCount() {
        return 5;
    }

    @Override
    public int getRowCount() {
        return (clients!=null) ? clients.size(): 0;
    }

    @Override
    public Object getValueAt(int r, int c) {
        Client client=clients.get(r);
        switch (c) {
            case 0:
                return client.getUserName();
            case 1:
                return client.getName() +" " + client.getSurname() + " " + client.getPatronymic();
            case 2:
                return client.getAddress();
            case 3:
                return client.getReceived();
            case 4:
                return client.getExpected();    
            default:
                return null;
        }
    }

    @Override
    public String getColumnName(int c){
        return columnNames[c];
    }

    public List<Client> getClients() {
        return clients;
    }


}

在 mainFrame 中创建带有空 tableModel 的表 table = new MyTable(new ProfitAbilityTableModel());

当按下按钮时这样做

button_1.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent arg0) {
                table.setModel(new ProfitAbilityTableModel(ClientFactory.getClients(10)));
            }
        });

客户端工厂:

public class ClientFactory {
    public static List<Client> getClients(int amount){
        List<Client> result=new ArrayList<>();
        Client c;
        int received,expected;
        for(int i=0;i<amount;i++){
            c=new Client();
            c.setUserName("username " + i);
            c.setName("name "+ i);
            c.setSurname("surname " + i);
            c.setPatronymic("patronymic" + i);
            c.setAddress("address " + i);
            expected=(int)(Math.random()*100);
            received=(int)(Math.random()*100);
            if(received>expected)
                received=expected;
            c.setExpected(expected);
            c.setReceived(received);
            result.add(c);
        }
        return result;
    }
}

如果Client 的两个字段相等,则更改行的颜色。 创建MyTable 时可以正常工作,但是更改 tableModel 时所有行都具有默认背景颜色(白色)。更改表模型时如何调用此代码?

【问题讨论】:

  • 是的,当按下按钮程序使用新数据设置新表模型时。这很棘手。将来它会从数据库中获取数据
  • 也许我走错路了?所以告诉我,如何正确地实现它。
  • 1. set new table model with new data. It's tricky. - 看不出有任何优势,JTable 及其 XxxTableModel 被指定为可重用的,2. 必须查看@camickr XxxTableModel 的博客(最好的代码和简单、清晰的逻辑......)和prepareRenderer这里的大部分代码只是从这个博客复制粘贴,3。In future it's take data from DB这里也搜索数据库中的表
  • 1.将索引转换为模型,然后您从第 6 列测试模型中的值(if(client.getExpected()==client.getReceived()) 让我成为废话,此项目必须返回实际值 - StringIntegerBoolean),2. 删除递归测试if(list!=null){ 应该是model isn't mull,更好地测试模型中的行数是否大于0(必须默认为prepareRenderer)

标签: java swing colors jtable tablecellrenderer


【解决方案1】:

通过将此方法添加到 ProfitAbilityTableModel 解决的问题:

public void setData(List<Client> clients){
        this.clients=clients;
    }

    public Client getClient(int index){
        return clients.get(index);
    }

换我的桌子:

public class MyTable extends JTable {

    public MyTable(TableModel model){
        super(model);   
    }
    @Override
    public Component prepareRenderer(TableCellRenderer renderer, int rowIndex, int vColIndex){
        Component rComp=super.prepareRenderer(renderer, rowIndex, vColIndex);
        if(getModel()!=null){
            Client client=((ProfitAbilityTableModel)getModel()).getClient(rowIndex);
            if(client.getExpected()==client.getReceived())
                rComp.setBackground(new Color(139, 255, 182));
            else
                rComp.setBackground(new Color(255,139,147));
        }

        return rComp;
    }
}

在主框架中按如下按钮更新数据:

ProfitAbilityTableModel model=(ProfitAbilityTableModel)table.getModel();
model.setData(ClientFactory.getClients(10));
model.fireTableDataChanged();

【讨论】:

  • 发布一个 SSCCE / MCVE / MCTRE,简短、可运行、可编译,可使用存储在局部变量中的 JTable / XxxTableModel 硬编码值,永远不要从模型类中调用 model.fireXxxXxx,你的模型又是' t完成了,这样就麻烦了,JTable的代码,它的模型和渲染器是很简单的工作,不要把简单的事情复杂化了
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-08-19
  • 2012-02-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-10-31
相关资源
最近更新 更多