How to use a selection setBackground in custom Renderer?

Asked

Viewed 142 times

0

I’m trying to use a render Cell, so when it shows monetary data, it does the formatting. However, when I apply the render in a particular column, the focus in that column does not have the background of the rest of the row.

To solve this, I thought about doing the same thing I did in my Abstracttable, creating a method that changes the color of the selected line, so it ends up picking the whole line. However, being Default, I could not do the same. So if someone knows a way to apply render other than "bug" or knows how to set the color.

To illustrate the problem:
inserir a descrição da imagem aqui

On my Abstract, I do so:

private JTable tabela = new JTable(jtmCompra) 
{
    @Override
    public Component prepareRenderer(TableCellRenderer renderer, int linha, int coluna) 
    {
        Component componente = super.prepareRenderer(renderer, linha,                  coluna);  

        if (isRowSelected(linha))//Focu na linha.
            {         

                componente.setBackground(new Color(147, 200, 255, 255)); 

            }       
     }      
} 

Dai as "line paint" is right. inserir a descrição da imagem aqui


Simple example:

Tela Sistema:

package telas;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JDesktopPane;
import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;

public class TelaSistema extends JFrame implements ActionListener
{

    public static JDesktopPane jdp = new JDesktopPane();
    public JMenuBar jmb = new JMenuBar();
    public JMenu jmCadastros = new JMenu("Cadastros"); 
    public JMenuItem jmiE = new JMenuItem("Uma tela qualquer");

    public TelaSistema() 
    {     
        setExtendedState(MAXIMIZED_BOTH);
        setTitle("Sistema");
        getContentPane().add(jdp);
        setJMenuBar(jmb);
        jmb.add(jmCadastros);       
        adicionaJMenuItem(jmCadastros, jmiE);        
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setVisible(true);
    }

    private void adicionaJMenuItem(JMenu menu, JMenuItem item) 
    {    
        menu.add(item);
        item.addActionListener(this);
    }

    @Override
    public void actionPerformed(ActionEvent ae) 
    {
        if (ae.getSource() == jmiE)
        {
            TelaCadastroA a = new TelaCadastroA();
            jdp.add(a);
        }
    }

    public static void main(String args[]) 
    {
       TelaSistema telaSistema = new TelaSistema();
    }  
}

Screen: Registration

package telas;

import java.awt.Component;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.text.DecimalFormat;
import javax.swing.JButton;
import javax.swing.JInternalFrame;
import javax.swing.JPanel;
import javax.swing.JTable;
import javax.swing.SwingConstants;
import javax.swing.table.DefaultTableCellRenderer;

public class TelaCadastroA extends JInternalFrame implements ActionListener
{
      public JButton jbConsultar = new JButton("Consultar");
      public JPanel jpBotoes = new JPanel();

    public TelaCadastroA() 
    {
        super("");    
        adicionaBotao(jbConsultar);
        setSize(500, 500);  
        getContentPane().add("South", jpBotoes);
        jpBotoes.setLayout(new GridLayout(1, 1));
        Dimension tamanhoTela = Toolkit.getDefaultToolkit().getScreenSize();
        setLocation((tamanhoTela.width - getWidth()) / 2, ((tamanhoTela.height - getHeight())) / 2);
        setVisible(true);
    }

    private void adicionaBotao(JButton botao) {
        jpBotoes.add(botao);
        botao.addActionListener(this);
    }

      @Override
    public void actionPerformed(ActionEvent ae)
    {
        if (ae.getSource() == jbConsultar) 
        {
            consultar();
        }
    }

    public void consultar() 
    {       
        TelaConsultar.getTela("Consulta",  new String[]
        {
            "Código", "A", "B", "C"
        }, new DefaultTableCellRenderer[] {null, null,  new CellRenderMonetario(), null}, this);
    } 

    class CellRenderMonetario extends DefaultTableCellRenderer 
    {
        private DecimalFormat df = new DecimalFormat(",##0.00");

        @Override
        public Component getTableCellRendererComponent(JTable tabela, Object valor, boolean isSelected, boolean temFocu, int linha, int coluna)
        {
            if (valor == null)
            {
                valor = 0;
            }

            if (valor instanceof String)
            {
                setText(df.format(Double.parseDouble((String) valor)) + " ");
            } 

            else 
            {
                setText(df.format(valor) + " ");
            }
            setHorizontalAlignment(SwingConstants.RIGHT);
            return this;
        }
    }
}

Tela Coonsulta:

package telas;

import java.awt.Dimension;
import java.awt.Toolkit;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import javax.swing.JInternalFrame;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.event.InternalFrameEvent;
import javax.swing.event.InternalFrameListener;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumnModel;

public class TelaConsultar extends JInternalFrame implements InternalFrameListener, MouseListener {

    private static TelaConsultar telaConsultar = null;
    private String sql;
    private String[] titulos;
    private TelaCadastroA tela;
    private JTable tabela;
    private JScrollPane jsp;
    private DefaultTableModel dtm = new DefaultTableModel();
    private String proc;

    public TelaConsultar(String tituloJanela, String[] titulos, DefaultTableCellRenderer[] renderizadores, TelaCadastroA tela) 
    {
        super(tituloJanela, true, true, false, false);
        this.sql = sql;
        this.titulos = titulos;
        this.tela = tela;
        tabela = new JTable() 
        {
            @Override
            public boolean isCellEditable(int linha, int coluna)
            {
                return false;//Esta tabela não pode ser editada pois é uma consulta         
            }
        };
        tabela.setModel(dtm); //Define o modelo da tabela
        tabela.getTableHeader().setReorderingAllowed(false);
        for (int i = 0; i < titulos.length; i++) 
        {
            dtm.addColumn(titulos[i]);
        }
        jsp = new JScrollPane(tabela);
        getContentPane().add(jsp);
        preencher();
        //pack();
        setSize(650, 400);
        setMinimumSize(new Dimension(getWidth(), getHeight()));
        centralizaTelaConsulta();
        setVisible(true);
        tabela.addMouseListener(this);
        addInternalFrameListener(this);

        TableColumnModel tableModel = tabela.getColumnModel();
        for (int i = 0; i < titulos.length; i++)
        {
            tableModel.getColumn(i).setMinWidth(70);                    
        }

        for (int i = 0; i < tableModel.getColumnCount(); i++) 
        {
            if (renderizadores[i] != null) 
            {
                tableModel.getColumn(i).setCellRenderer(renderizadores[i]);
                /* if (isRowSelected(i))//Focu na linha.
                {

                }*/
            }

        }
    }

    public static void getTela(String tituloJanela, String[] titulos, DefaultTableCellRenderer[] renderizadores, TelaCadastroA tela) 
    {
        if (telaConsultar == null) 
        {
            telaConsultar = new TelaConsultar(tituloJanela, titulos, renderizadores, tela);
            TelaSistema.jdp.add(telaConsultar);
        }
        TelaSistema.jdp.setSelectedFrame(telaConsultar);
        TelaSistema.jdp.moveToFront(telaConsultar);
    }

    private void preencher() 
    {
        for (int i = 0; i < 10; i++) 
        {
            dtm.addRow(new Object[]{"" + i, "Brasil - " + i});
        }

    }

    public void centralizaTelaConsulta() 
    {
        Dimension tamanhoTela = Toolkit.getDefaultToolkit().getScreenSize();
        setLocation((tamanhoTela.width - getWidth()) / 2, ((tamanhoTela.height - getHeight())) / 2);
    }

    @Override
    public void mousePressed(MouseEvent e) {
    }

    @Override
    public void mouseReleased(MouseEvent e) {
    }

    @Override
    public void mouseEntered(MouseEvent e) {
    }

    @Override
    public void mouseExited(MouseEvent e) {
    }

    @Override
    public void internalFrameOpened(InternalFrameEvent e) {
    }

    @Override
    public void internalFrameClosing(InternalFrameEvent e) {
    }

    @Override
    public void internalFrameClosed(InternalFrameEvent e) {
        TelaSistema.jdp.remove(telaConsultar);
        telaConsultar = null;
    }

    @Override
    public void internalFrameIconified(InternalFrameEvent e) {
    }

    @Override
    public void internalFrameDeiconified(InternalFrameEvent e) {
    }

    @Override
    public void internalFrameActivated(InternalFrameEvent e) {

    }

    @Override
    public void internalFrameDeactivated(InternalFrameEvent e) {
    }

    @Override
    public void mouseClicked(MouseEvent me) {

    }
}
  • 1

    Who renders are the Cellrenders, defaulttablemodel in no way influences it. If possible, add your Renderer and a [mcve] for the code to be testable.

  • 2

    Even the most basic example, I think I’ll have to post a link to download a . rar, is that a problem? I’ll try to put "as little as possible" of things.

  • 1

    Complicates a bit. Make an example with some sample data (no database connection).

1 answer

2


As you are modifying the way this column renders, the default table definitions are not applied, so the method getTableCellRendererComponent has a parameter isSelected, for you to define yourself. In the case of your code, the solution I found was to check if the field was selected, and copy the default selection settings from the table:

class CellRenderMonetario extends DefaultTableCellRenderer {

    private DecimalFormat df = new DecimalFormat(",##0.00");

    @Override
    public Component getTableCellRendererComponent(JTable tabela, Object valor, boolean isSelected, boolean temFocu, int linha, int coluna) {
        if (valor == null) {
            valor = 0;
        }
        if (isSelected) {
            setBackground(tabela.getSelectionBackground());
            setForeground(tabela.getSelectionForeground());
        } else {
            setBackground(tabela.getBackground());
            setForeground(tabela.getForeground());
        }

        if (valor instanceof String) {
            setText(df.format(Double.parseDouble((String) valor)) + " ");
        } else {
            setText(df.format(valor) + " ");
        }
        setHorizontalAlignment(SwingConstants.RIGHT);

        return this;
    }
}

With this, the field will follow the same color selection pattern as the rest of the table.

There are several things that could be improved in this code, especially the question of organization and responsibilities of classes and methods, but this would escape the scope of the question.

  • 2

    Wow, gave it right. I had not thought of mecher in the render. Thank you very much.

  • @Gustavosantos Dispo :)

  • 1

    I have a question, very close to the topic, but I should open a new, or post post post in the comments ? It’s just that I made a yield for date, which is not quite right.

  • @Gustavosantos answered you there in chat.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.