Retorno de Registro Duplicado na jTable

14 respostas
rolipam

Bom dia DEVs. Estou com o código abaixo que preenche uma jTabel a partir de uma consulta ao banco de dados de acordo com a solicitação do cliente.

private void btFiltrarActionPerformed(java.awt.event.ActionEvent evt) {                                          
        String sql = "";
        String mes = tfMesAnoPesquisa.getText().substring(0, 2); 
        String ano = tfMesAnoPesquisa.getText().substring(3, 7);
        
        if(rbMesAnoPesquisa.isSelected() && cbSubalmoxarifadoPesquisa.getSelectedItem().equals("TODOS")){
            // Pesquisa Validades por Mês e Ano em TODOS os Subalmoxarifados
            sql = "select v.id as vid, v.status as status, v.codproduto as codproduto, p.id as pid, p.tipo as tipo, p.apresentacao as apresentacao, "
                    + "p.descricao as descricao, v.origem as origem, v.detalhe_origem as detalhe_origem, v.subalmoxarifado as subalmoxarifado, "
                    + "s.id as sid, s.nome as nome, v.local as local, v.lote as lote, v.validade as validade, v.quantidade as qtde, v.cmm as cmm "
                    + "from validades v, produtos p, subalmoxarifados s where month(validade) = " + mes + " and year(validade) = " + ano + " "
                    + "and v.codproduto = p.id and v.subalmoxarifado = s.id order by validade" ;
        }else if(rbAnoPesquisa.isSelected() && cbSubalmoxarifadoPesquisa.getSelectedItem().equals("TODOS")){
            // Pesquisa Validades por Ano em TODOS os Subalmoxarifados
            sql = "select v.id as vid, v.status as status, v.codproduto as codproduto, p.id as pid, p.tipo as tipo, p.apresentacao as apresentacao, "
                    + "p.descricao as descricao, v.origem as origem, v.detalhe_origem as detalhe_origem, v.subalmoxarifado as subalmoxarifado, "
                    + "s.id as sid, s.nome as nome, v.local as local, v.lote as lote, v.validade as validade, v.quantidade as qtde, v.cmm as cmm "
                    + "from validades v, produtos p, subalmoxarifados s where year(validade) = " + tfAnoPesquisa.getText() + " "
                    + "and v.codproduto = p.id and v.subalmoxarifado = s.id order by validade";
        }else if(rbMesAnoPesquisa.isSelected() && !cbSubalmoxarifadoPesquisa.getSelectedItem().equals("TODOS")){
            // Pesquisa Validades por Mês e Ano para o Subalmoxarifado Selecionado no ComboBox
            sql = "select v.id as vid, v.status as status, v.codproduto as codproduto, p.id as pid, p.tipo as tipo, p.apresentacao as apresentacao, "
                    + "p.descricao as descricao, v.origem as origem, v.detalhe_origem as detalhe_origem, v.subalmoxarifado as subalmoxarifado, "
                    + "s.id as sid, s.nome as nome, v.local as local, v.lote as lote, v.validade as validade, v.quantidade as qtde, v.cmm as cmm "
                    + "from validades v, produtos p, subalmoxarifados s "
                    + "where month(validade) = " + mes + " and year(validade) = " + ano + " and subalmoxarifado = "+ codsubalmoxarifadosearch + " "
                    + "and v.codproduto = p.id and v.subalmoxarifado = s.id order by validade";
        }else if(rbAnoPesquisa.isSelected() && !cbSubalmoxarifadoPesquisa.getSelectedItem().equals("TODOS")){
            // Pesquisa Validades por Ano para o Subalmoxarifado Selecionado no ComboBox
            sql = "select v.id as vid, v.status as status, v.codproduto as codproduto, p.id as pid, p.tipo as tipo, p.apresentacao as apresentacao, "
                    + "p.descricao as descricao, v.origem as origem, v.detalhe_origem as detalhe_origem, v.subalmoxarifado as subalmoxarifado, "
                    + "s.id as sid, s.nome as nome, v.local as local, v.lote as lote, v.validade as validade, v.quantidade as qtde, v.cmm as cmm "
                    + "from validades v, produtos p, subalmoxarifados s "
                    + "where year(validade) = " + tfAnoPesquisa.getText() + " and subalmoxarifado = "+ codsubalmoxarifadosearch + " "
                    + "and v.codproduto = p.id and v.subalmoxarifado = s.id order by validade";
        }
        
        con.conecta();
        tbDados.getColumnModel().getColumn(0).setPreferredWidth(10);
        tbDados.getColumnModel().getColumn(1).setPreferredWidth(100);
        
        while(tmValidades.getRowCount() > 0){
            tmValidades.removeRow(0);
        }
        JOptionPane.showMessageDialog(null, sql);
        con.executeSQL(sql);
        validades = new ArrayList<>();
        produtos = new ArrayList<>();
        subalmoxarifados = new ArrayList<>();
        try{
            while(con.rs.next()){
                vb = new ValidadesBean();
                pb = new ProdutosBean();
                sb = new SubalmoxarifadoBean();
                vb.setId(con.rs.getInt("vid"));
                vb.setStatus(con.rs.getString("status"));
                vb.setCodproduto(con.rs.getInt("codproduto")); // Buscar na Tabela Produtos o TIPO a APRESENTAÇÃO e a DESCRIÇÃO do PRODUTO
                vb.setLote(con.rs.getString("lote"));
                vb.setValidade(con.rs.getDate("validade"));
                vb.setQuantidade(con.rs.getInt("qtde"));
                vb.setCmm(con.rs.getInt("cmm"));
                vb.setSubalmoxarifado(con.rs.getShort("subalmoxarifado")); // Buscar na Tabela Subalmoxarifados o NOME do SUBALMOXARIFADO
                vb.setLocal(con.rs.getString("local"));
                vb.setOrigem(con.rs.getString("origem"));
                vb.setDetalhe_origem(con.rs.getString("detalhe_origem"));
                validades.add(vb);
                pb.setId(con.rs.getInt("pid"));
                pb.setTipo(con.rs.getString("tipo"));
                pb.setApresentacao(con.rs.getString("apresentacao"));
                pb.setDescricao(con.rs.getString("descricao"));
                produtos.add(pb);
                sb.setId(con.rs.getInt("sid"));
                sb.setNome(con.rs.getString("nome"));
                subalmoxarifados.add(sb);
            }
            
            if(validades.size() == 0){
                
            }else{
                for(int i = 0; i < validades.size(); i++){
                    for(int j = 0; j < produtos.size(); j++){
                        tmValidades.addRow(new String[] {
                            sdf.format(validades.get(i).getValidade()),
                            produtos.get(i).getDescricao()
                        });
                    }
                }
            }
            
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            con.desconecta();
        }
        
    }

O interessante é que quando eu faço a busca por mês e ano os registros na tabela são mostrados corretamente, um de cada, e quando eu faço a busca por ano a tabela mostra os registros duplicados.
Alguém aí identifica qual o meu problema?
Agradecido!

14 Respostas

rolipam

Problema da duplicação resolvido! O problema agora é outro. Qdo seleciono um registro na tabela os campos referentes aos produtos não atualiza para todos os produtos e às vezes dá o erro Java.lang.ArrayOutOfBoundsException

RoinujNosde

Mostra o erro e o código relacionado

rolipam

Problema Resolvido! Porém agora estou com um novo problema!!! KKKKK… Essa Vida de Dev é “Phood@” (Isso mesmo, com PH de pharmacia (afinal de contas sou farmacêutico também) , dois “O” de Zoológico (aqui em casa tenho 3 cachorros, 5 gatos e 1 passarinho) e terminando com Arroba)! Mas o que seria de nós se não fossem os BUGs, neles nosso aprendizado só cresce! E quando conseguimos resolver com nossos próprios meios a satisfação é imensa! Mas vamos ao que interessa. Agora está tudo correndo perfeitamente, se não fosse um pequeno e incômodo problema. O produto listado no jComboBox não é “setado”. Segue o código abaixo. A linha que está dando erro está comentada.

private void tbDadosLinhaSelecionada(JTable tb){

    if (tb.getSelectedRow() != -1) {
	...
    if(todos.get(tb.getSelectedRow()).getTipo().equals("Medicamento")){
       cbTipo.setSelectedItem("Medicamento");
       tfTipo.setText("");
    }else if(todos.get(tb.getSelectedRow()).getTipo().equals("Manipulado")){
       cbTipo.setSelectedItem("Manipulado");
       tfTipo.setText("");
    }else if(todos.get(tb.getSelectedRow()).getTipo().equals("Substância")){
       cbTipo.setSelectedItem("Substância");
       tfTipo.setText("");
    }else{
       cbTipo.setSelectedItem("Outros");
       tfTipo.setText(todos.get(tb.getSelectedRow()).getTipo());
    }
	...
	AtualizarCBDescricao(); 
    cbDescricao.requestFocus();
    cbDescricao.setSelectedItem(todos.get(tb.getSelectedRow()).getDescricao()); // Não está "Setando" o Produto no CombBox
    ...
}

private void AtualizarCBDescricao(){
    pb = new ProdutosBean();
    produtos = new ArrayList<>();
    if(cbTipo.getSelectedItem().equals("Selecione")){
        
    }else if(cbTipo.getSelectedItem().equals("Outros")){
        tipo = tfTipo.getText();
    }else{
        tipo = String.valueOf(cbTipo.getSelectedItem());
    }
    String sql = "select * from produtos where tipo like '" + tipo + "' order by descricao";
    cbDescricao.removeAllItems();
    cbDescricao.addItem("Selecione");
    try{
        con.conecta();
        con.executeSQL(sql);
        while(con.rs.next()){
            cbDescricao.addItem(con.rs.getString("descricao"));
            pb.setId(con.rs.getInt("id"));
            pb.setDescricao(con.rs.getString("descricao"));
            pb.setTipo(con.rs.getString("tipo"));
            pb.setApresentacao(con.rs.getString("apresentacao"));
            produtos.add(pb);
        }

    }catch(Exception e){
        e.printStackTrace();
    }finally{
        con.desconecta();
    }
}
RoinujNosde

getDescricao() deve estar retornando null ou “”

rolipam

Não está retornando null nem “” pois quando retorna outro tipo como medicamento, manipulado ou substância (que estão pré carregados no jComBox TIPO) o jComboBox DESCRIÇÃO consegue carregar todos os produtos para aquele tipo e “SETA” o produto correto.

RoinujNosde

Coloca pra printar o valor que está setando no combobox.

rolipam

Eu fiz o que vc sugeriu:

AtualizarCBDescricao();
          cbDescricao.requestFocus();
          cbDescricao.setSelectedItem(todos.get(tb.getSelectedRow()).getDescricao());
          System.out.println(todos.get(tb.getSelectedRow()).getDescricao());

E apesar de continuar não setando a descrição do produto no comboBox (apenas para os tipos que não são pré-cadastrados no ComboBox, para os demais tipos pré-carregados, mostra normalmente), o System.out.println está imprimindo a descrição do produto corretamente.
O engraçado é que quando clico na linha da tabela para exibir os dados, dá pra perceber que o comboBox mostra a descrição e muda rapidamente para “Selecione”. É como se tivesse alguma coisa atualizando o comboBox de novo e setando “Selecione”, o que não está acontecendo em nenhuma linha de código.

RoinujNosde

Tem mais alguma coisa abaixo da linha cbDescricao.setSelectedItem?

rolipam

tem os demais campos que tem que mostrar os dados.

RoinujNosde

nenhum deles modifica o cbDescricao?

rolipam

Não. Segue código completo.
private void tbDadosLinhaSelecionada(JTable tb){

if (tb.getSelectedRow() != -1) {
          tfId.setText(""+todos.get(tb.getSelectedRow()).getVid());
          if(todos.get(tb.getSelectedRow()).getStatus().equals("L")){
            cbStatus.setSelectedItem("L - Longe da Validade (1+ ano)");
          }else if(todos.get(tb.getSelectedRow()).getStatus().equals("D")){
              cbStatus.setSelectedItem("D - Dentro da Validade (6m a 1a)");
          }else if(todos.get(tb.getSelectedRow()).getStatus().equals("P")){
              cbStatus.setSelectedItem("P - Perto da Validade (2m a 6m)");
          }else if(todos.get(tb.getSelectedRow()).getStatus().equals("V")){
              cbStatus.setSelectedItem("V - Vencendo no Mês");
          }else if(todos.get(tb.getSelectedRow()).getStatus().equals("E")){
              cbStatus.setSelectedItem("E - Vencido em Estoque");
          }else if(todos.get(tb.getSelectedRow()).getStatus().equals("R")){
              cbStatus.setSelectedItem("R - Vencido Retirado do Estoque");
          }else if(todos.get(tb.getSelectedRow()).getStatus().equals("F")){
              cbStatus.setSelectedItem("F - Troca com Fornecedor");
          }else if(todos.get(tb.getSelectedRow()).getStatus().equals("T")){
              cbStatus.setSelectedItem("T - Troca com Outra Instituição");
          }else{
              cbStatus.setSelectedItem("SELECIONE");
          }
          if(todos.get(tb.getSelectedRow()).getTipo().equals("MEDICAMENTO")){
              cbTipo.setSelectedItem("MEDICAMENTO");
              tfTipo.setText("");
          }else if(todos.get(tb.getSelectedRow()).getTipo().equals("MANIPULADO")){
              cbTipo.setSelectedItem("MANIPULADO");
              tfTipo.setText("");
          }else if(todos.get(tb.getSelectedRow()).getTipo().equals("SUBSTÂNCIA")){
              cbTipo.setSelectedItem("SUBSTÂNCIA");
              tfTipo.setText("");
          }else{
              cbTipo.setSelectedItem("OUTROS");
              tfTipo.setText(todos.get(tb.getSelectedRow()).getTipo());
          }
          if(todos.get(tb.getSelectedRow()).getApresentacao().equals("COMPRIMIDO")){
              cbApresentacao.setSelectedItem("COMPRIMIDO");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("CÁPSULA")){
              cbApresentacao.setSelectedItem("CÁPSULA");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("DRÁGEA")){
              cbApresentacao.setSelectedItem("DRÁGEA");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("AMPOLA")){
              cbApresentacao.setSelectedItem("AMPOLA");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("FRASCO")){
              cbApresentacao.setSelectedItem("FRASCO");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("FRASCO-AMPOLA")){
              cbApresentacao.setSelectedItem("FRASCO-AMPOLA");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("BOLSA")){
              cbApresentacao.setSelectedItem("BOLSA");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("SACHÊ")){
              cbApresentacao.setSelectedItem("SACHÊ");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("BISNAGA")){
              cbApresentacao.setSelectedItem("BISNAGA");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("POTE")){
              cbApresentacao.setSelectedItem("POTE");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("ADESIVO")){
              cbApresentacao.setSelectedItem("ADESIVO");
              tfApresentacao.setText("");
          }else if(todos.get(tb.getSelectedRow()).getApresentacao().equals("UNIDADE")){
              cbApresentacao.setSelectedItem("UNIDADE");
              tfApresentacao.setText("");
          }else{
              cbApresentacao.setSelectedItem("OUTROS");
              tfApresentacao.setText(todos.get(tb.getSelectedRow()).getApresentacao());
          }
          AtualizarCBDescricao();
          cbDescricao.requestFocus();
          cbDescricao.setSelectedItem(todos.get(tb.getSelectedRow()).getDescricao());
          System.out.println(todos.get(tb.getSelectedRow()).getDescricao());
          
          if(todos.get(tb.getSelectedRow()).getOrigem().equals("C")){
              cbOrigem.setSelectedItem("C - Compra");
          }else if(todos.get(tb.getSelectedRow()).getOrigem().equals("D")){
              cbOrigem.setSelectedItem("D - Doação");
          }else if(todos.get(tb.getSelectedRow()).getOrigem().equals("E")){
              cbOrigem.setSelectedItem("E - Empréstimo");
          }else if(todos.get(tb.getSelectedRow()).getOrigem().equals("T")){
              cbOrigem.setSelectedItem("Troca");
          }else if(todos.get(tb.getSelectedRow()).getOrigem().equals("I")){
              cbOrigem.setSelectedItem("I - Transferência Interna");
          }else{
              cbOrigem.setSelectedItem("SELECIONE");
          }
          cbSubalmoxarifado.setSelectedItem(todos.get(tb.getSelectedRow()).getNome());
          tfLocal.setText(todos.get(tb.getSelectedRow()).getLocal());
          tfLote.setText(todos.get(tb.getSelectedRow()).getLote());
          tfValidade.setText(sdf.format(todos.get(tb.getSelectedRow()).getValidade()));
          tfQuantidade.setText(String.valueOf(todos.get(tb.getSelectedRow()).getQuantidade()));
          tfCmm.setText(String.valueOf(todos.get(tb.getSelectedRow()).getCmm()));
    }
}
Outros Métodos que Alteram o cbDescrição são:

private void cbTipoActionPerformed(java.awt.event.ActionEvent evt) {

if(cbTipo.getSelectedItem().equals(SELECIONE)){
}else if(cbTipo.getSelectedItem().equals("OUTROS")){
        tfTipo.setEditable(true);
        tfTipo.requestFocus();
        tipo = tfTipo.getText();
        AtualizarCBDescricao();
    }else{
        tipo = String.valueOf(cbTipo.getSelectedItem());
        AtualizarCBDescricao();
    }
}

private void AtualizarCBDescricao(){
    pb = new ProdutosBean();
    produtos = new ArrayList<>();
    if(cbTipo.getSelectedItem().equals("SELECIONE")){
        
    }else if(cbTipo.getSelectedItem().equals("OUTROS")){
        tipo = tfTipo.getText();
    }else{
        tipo = String.valueOf(cbTipo.getSelectedItem());
    }
    String sql = "select * from produtos where tipo like '" + tipo + "' order by descricao";
    cbDescricao.removeAllItems();
    cbDescricao.addItem("SELECIONE");
    try{
        con.conecta();
        con.executeSQL(sql);
        while(con.rs.next()){
            cbDescricao.addItem(con.rs.getString("descricao"));
            pb.setId(con.rs.getInt("id"));
            pb.setDescricao(con.rs.getString("descricao"));
            pb.setTipo(con.rs.getString("tipo"));
            pb.setApresentacao(con.rs.getString("apresentacao"));
            produtos.add(pb);
        }

    }catch(Exception e){
        e.printStackTrace();
    }finally{
        con.desconecta();
    }
}

private void cbDescricaoActionPerformed(java.awt.event.ActionEvent evt) {                                            

    String sql = "select id from produtos where descricao like '" + String.valueOf(cbDescricao.getSelectedItem()) + "'";
    try{
        con.conecta();
        con.executeSQL(sql);
        if(con.rs.first()){
            codproduto = con.rs.getInt("id");
        }

    }catch(Exception e){
        e.printStackTrace();
    }finally{
        con.desconecta();
    }   
}

Mais nenhum. E é como eu falei antes, qdo o Tipo é “Medicamento”, “Manipulado” ou “Substância” que já são pre-carregados no cbTipo, a descrição do produto é mostrada corretamente no cbDescricao. O erro só ocorre qdo o Tipo setado no cbTipo é “Outros” e nesse caso um jTextField ao lado do cbTipo é que mostra o Tipo salvo no BD. O cbDescricao até mostra os produtos salvos com aquele tipo, mas não seta o produto, e tem mais, dá pra perceber que o cbDescricao até tenta setar a descrição, mas retorna rapidamente para “Selecione”.

RoinujNosde

Coloca um print no topo desse método “cb tipo chamado”, só pra debugar.
Acho que ele tá sendo chamado após selecionar a linha e resetando o cb descrição.

rolipam

Se fosse isso, não “setaria” corretamente a descrição para os tipos pré-carregados no cbTipo. O cbDescrição resetaria em todas as situações. Mas o que está ocorrendo é que ele só está resetando para o Tipo “Outros”. Mas vou testar esse DEBUG.

rolipam

Resolvido! O problema estava quando o tfTipo perdia o foco (FocusLost) para preencher o cbDescrição quando o cbTipo estava setado com “Outros”. Mas como eu preciso dessa funcionalidade para pesquisar pelos produtos cadastrados para o tipo descrito no jTextField, coloquei o método para atualizar o cbDescrição apenas quando estou criando um novo registro, ou seja, quando clico no botão novo (tipoRegistro = "novo") e depois que o registro é salvo, alterado ou excluído, ou clica no botão limpar campos, o tipoRegistro = "".

Criado 25 de abril de 2021
Ultima resposta 28 de abr. de 2021
Respostas 14
Participantes 2