Inserir dados da Jtable no banco

50 respostas
L

Olá Pessoal,

Eu estou com uma dúvida na inserção de dados de Jtable no banco, ele exibe seguinte erro"java.lang.String cannot be cast to java.lang.Double"
Alguém pode-me ajudar ai?
Agradeço desde já pela atenção.

50 Respostas

L

Por favor alguém tem uma ideia desse erro, pois já procurei no net, mas não acho nada concreto.

M

Isso parece erro do insert e nao da JTable. Voce provavelmente pegou um campo String e esta tentando gravar um Double.

Posta o código do seu insert e onde voce chama com os dados da JTable.

A

O sr. deve estar trabalhando com o DefaultTableModel lá, uma zica só. Tente isso para adicionar, por exemplo:

public void adicionaNaTabela()
    {
       String a=txtProduto.getText();
       String b=txtValorUnitario.getText();
       String c=txtQuantidade.getText();

       double n1 = Double.parseDouble(b);
       double n2 = Double.parseDouble(c);

        DefaultTableModel modelo = (DefaultTableModel)tabela.getModel();
        modelo.addRow(new Object [] {a,c,b,(n1*n2)});
    }
L

Meus amigos muito obrigado pela ajuda, mas enfilizmente não funcionou ainda e continua com erro de "for input String: “2,00”, isso usando ideia do Andre para inclusão no Jtable.

L

Alguém poderia-me dar uma ideia melhor para resolver este problema?
Desde já agradeço.

M

Postar o método que adiciona no banco e seu TableModel. E se tiver usando o Default minha dica é PARAR IMEDIATAMENTE.

L

Este é o método:

public void inserirItemvenda() { try{ ItemVenda item = new ItemVenda(); ctrItem = new CTR_ManterItemVenda(); CTR_ManterProduto ctrProdutos = new CTR_ManterProduto(); Produto produto = new Produto(); String aux1=""; String aux2=""; String aux3=""; for (int i = 0 ; i < jtProdutos.getRowCount() ; i++) { //if (jtProdutos.getValueAt(i, 0).equals(true)) aux1=(String)jtProdutos.getValueAt(i,2); item.setValorUnitario(Double.parseDouble(aux1)); aux2=(String)jtProdutos.getValueAt(i, 3); item.setQuantidade(Double.parseDouble(aux2)); aux3=(String)jtProdutos.getValueAt(i, 4); item.setValorTotal(Double.parseDouble(aux3)); produto = (Produto) ctrProdutos.carregarProdutoCodigoProduto((Integer) jtProdutos.getValueAt(i, 0)); item.setIdProduto(produto); item.setIdVenda(venda); item.setTamanho(String.valueOf(JTxtTamanho)); item.setCor(String.valueOf(JTxtCor)); ctrItem.gravarItemVenda(item); //} } }

M

Coloca o código de gravarItemVenda()

L

Boa dia Mark,

Segue o código de GravarItemVenda e método gravar:

public boolean gravarItemVenda(ItemVenda item) { try { itemHibernateDAO.gravar(item); return true; } catch(HibernateException e) { e.printStackTrace(); Logger logAux = Logger.getLogger(CTR_ManterItemVenda.class); mensagemErro = "Erro gerado pelo sistema: "+e; log.gerarLog(logAux, mensagemErro); return false; } }

public void gravar(ItemVenda item) throws HibernateException { Session session = new HibernateFactory().getSession(); session.getTransaction().begin(); session.save(item); session.getTransaction().commit(); session.close(); }

R

"for input String: “2,00”

2,00 não é um número válido para ele!
Tente 2.00

L

Mudei, mas não resolveu nada. Já estou alguns dias tentando resolver isso, quem poder me ajudar agradeço muito.

L

Alguém pode-me dar uma ideia melhor?

V

Posta postar a linha do código onde a exception indica?

L

Vini segue o código de inclusão de item venda:

public void inserirItemvenda()
{
    try{
    ItemVenda item = new ItemVenda();
    ctrItem = new CTR_ManterItemVenda();
    CTR_ManterProduto ctrProdutos = new CTR_ManterProduto();
    Produto produto = new Produto();
    String aux1;
    String aux2;
    String aux3;
    for (int i = 0 ; i < jtProdutos.getRowCount() ; i++)
    {
          aux1=(String)jtProdutos.getValueAt(i,2);
          item.setValorUnitario(Double.parseDouble(aux1));
          aux2=(String)jtProdutos.getValueAt(i, 3);
          [b]item.setQuantidade(Double.parseDouble(aux2));[/b] 
         aux3=(String)jtProdutos.getValueAt(i, 4);
         [b] item.setValorTotal(Double.parseDouble(aux3));[/b]
          produto = (Produto) ctrProdutos.carregarProdutoCodigoProduto((Integer) jtProdutos.getValueAt(i, 0));
          item.setIdProduto(produto);
          item.setIdVenda(venda);
          item.setTamanho(String.valueOf(JTxtTamanho));
          item.setCor(String.valueOf(JTxtCor));
          ctrItem.gravarItemVenda(item);
    }
} 
    catch(Exception e){
        JOptionPane.showMessageDialog(null,"Erro ao persistir objeto item venda: "+e.getMessage());
    }
}

segue o código que calcula o preço total:

public Double CalculaprecoTotal(){
        String p= jftfPreco.getText();
        String q= jftfQuantidade.getText();
        Double preco = Double.parseDouble(jftfPreco.getText());
        Double quantidade = Double.parseDouble(jftfQuantidade.getText().replace(",", "."));
        Double valorTotal = preco * quantidade;
        return valorTotal;        
}

por último o código que adiciona dados na Jtabela:

private void jbtnAdicionarProdutoActionPerformed(java.awt.event.ActionEvent evt) {                                                     
   try{
    DefaultTableModel dtm = (DefaultTableModel) jtProdutos.getModel();

    DefaultComboBoxModel dcbm = (DefaultComboBoxModel) JCBoxCodigoProduto.getModel();
    dtm.addRow(new Object[] {JTxtNomeProduto.getText(), dcbm.getSelectedItem().toString(), jftfPreco.getText(), jftfQuantidade.getText(), CalculaprecoTotal()});
   }
   catch(Exception e){
       JOptionPane.showMessageDialog(null,"erro ao adicionar produto na tabela"+e.getMessage());
   }
}
V

Pode indicar nesse monte de código aí, qual é a linha que a exception aponta?

V

Ah claro, agora que vi, você engole informação importante da exception. Faça assim no seu catch:

JOptionPane.showMessageDialog(null,"erro ao adicionar produto na tabela"+e.getMessage()); e.printStackTrace();

E no console, após fechar a janela de erro, aparecerá uma descrição detalhada do problema, indicando exatamente em que linha o bug ocorreu, e em que método. Jamais engula informações de exceptions, pois elas são úteis. E sem elas, fica difícil mesmo saber onde procurar o problema.

Aí, vc pode só postar o trecho específico para a gente, destacando com algum comentário a linha que a exception indicou.

L

Obiragdo Vini, vou fazer isso e retorno já.

L

Este é o erro que ele exibie:

java.lang.NumberFormatException: For input string: "2,00" at sun.misc.FloatingDecimal.readJavaFormatString(FloatingDecimal.java:1224) at java.lang.Double.parseDouble(Double.java:510) at br.com.karinhaEstoque.view.formInclusaoVenda.inserirItemvenda(formInclusaoVenda.java:1487) at br.com.karinhaEstoque.view.formInclusaoVenda.insereVenda(formInclusaoVenda.java:1410) at br.com.karinhaEstoque.view.formInclusaoVenda.btnIncluirActionPerformed(formInclusaoVenda.java:1008) at br.com.karinhaEstoque.view.formInclusaoVenda.access$100(formInclusaoVenda.java:18) at br.com.karinhaEstoque.view.formInclusaoVenda$2.actionPerformed(formInclusaoVenda.java:219) at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:1995) at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2318) at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:387) at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:242) at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:236) at java.awt.Component.processMouseEvent(Component.java:6263) at javax.swing.JComponent.processMouseEvent(JComponent.java:3267) at java.awt.Component.processEvent(Component.java:6028) at java.awt.Container.processEvent(Container.java:2041) at java.awt.Component.dispatchEventImpl(Component.java:4630) at java.awt.Container.dispatchEventImpl(Container.java:2099) at java.awt.Component.dispatchEvent(Component.java:4460) at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4574) at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4238) at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4168) at java.awt.Container.dispatchEventImpl(Container.java:2085) at java.awt.Window.dispatchEventImpl(Window.java:2475) at java.awt.Component.dispatchEvent(Component.java:4460) at java.awt.EventQueue.dispatchEvent(EventQueue.java:599) at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:269) at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:184) at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:174) at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:169) at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:161) at java.awt.EventDispatchThread.run(EventDispatchThread.java:122)

V

Ok, agora veja o que sua mensagem de erro diz. Que não pode converter string para double pq o valor 2,00 não é válido. E na exceção, diz também exatamente em que conversão o java está falhando, veja:

at sun.misc.FloatingDecimal.readJavaFormatString(FloatingDecimal.java:1224)

at java.lang.Double.parseDouble(Double.java:510)

at br.com.karinhaEstoque.view.formInclusaoVenda.[b]inserirItemvenda<a>/b</a>

Ou seja, no Arquivo formInclusaoVenda.java, na linha 1487, no método inserirItemvenda, da classe formInclusaoVenda.

Tente alterar seu método para:

public void inserirItemvenda() { try{ ctrItem = new CTR_ManterItemVenda(); CTR_ManterProduto ctrProdutos = new CTR_ManterProduto(); Produto produto = new Produto(); for (int i = 0 ; i &lt; jtProdutos.getRowCount() ; i++) { NumberFormat format = NumberFormat.getInstance(); ItemVenda item = new ItemVenda(); String aux1=(String)jtProdutos.getValueAt(i,2); item.setValorUnitario(format.parse(aux1)); String aux2=(String)jtProdutos.getValueAt(i, 3); [b]item.setQuantidade(format.parse(aux2));[/b] String aux3=(String)jtProdutos.getValueAt(i, 4); [b] item.setValorTotal(format.parse(aux3));[/b] produto = (Produto) ctrProdutos.carregarProdutoCodigoProduto((Integer) jtProdutos.getValueAt(i, 0)); item.setIdProduto(produto); item.setIdVenda(venda); item.setTamanho(String.valueOf(JTxtTamanho)); item.setCor(String.valueOf(JTxtCor)); ctrItem.gravarItemVenda(item); } } catch(Exception e){ JOptionPane.showMessageDialog(null,&quot;Erro ao persistir objeto item venda: &quot;+e.getMessage()); e.printStackTrace(); } }

Ou pare de trabalhar com DefaultTableModel, evite esse monte de casts e conversões.

Outra coisa. Java não é C, nem Pascal. Você pode (e deve) declarar as variáveis no ponto mais próximo de onde for usa-las, não no início do método. Isso evita um monte de erros. Por exemplo, você deu vários "new" antes do for. Isso significa que o objeto usado para cada item do JTable será o mesmo. Isso certamente não é verdade para o ItemVenda, já que cada linha representa um item diferente. Aliás, se você estivesse usando o seu próprio model, você também não precisaria criar nenhum objeto novo.

Você também faz uma chamada ao carregarProduto ali no meio do seu for. Fique sabendo que essa é uma operação extremamente ineficiente, e que também poderia ser evitada se você seguisse o conselho que estamos repetindo para você umas 200 vezes, de parar de usar o DefaultTableModel. Se você quiser continuar dando murro em ponta de faca e usar esse modelo, me avise, pois estou muito propenso a não responder tópicos seus com JTable de agora em diante.

Finalmente, esse tópico aqui pertence ao fórum de interface gráfica, não off-topic. Por isso o movimentei.

L

Cara se eu soubesse usar Jtable sem DefaultTableModel, eu faria isso sim. Me dá um exemplo sem uso DefaultTableModel para que eu possa melhorar este problema. Outra coisa, eu estou apredendo java ainda, porém você consegue mesmo ver que o meu nível de conhecimento em java é muito inferior em relação a sua, por isso estou pedindo ajuda.
Se você poder me ajudar eu agradeço muito, senão poder também eu entendo.

V

Se você quer se livrar do Default, eu te ajudo sem problemas. Nem que gastemos uns 200 posts para isso, e eu tenha que elaborar um exemplo baseado nas suas próprias classes de negócio.

Agora, seu argumento não é lá muito válido. Quanto tempo você gastou aprendendo a usar o default? Quanto tempo você está gastando nesse for, para achar um problema que o default te gerou? Quanto tempo você vai gastar, fazendo casts, entendendo como driblar as limitações que o default te dá?

Se você tem tempo e capacidade para aprender a usar o default, terá também para aprender a não usa-lo.

Bem, aqui está um exemplo para um TableModel de livros:
http://www.guj.com.br/posts/list/132698.java#714736

Se quiser, poste a estrutura da classe que está sendo exibida na JTable, e diga que campos você quer exibir na tabela, que te ajudamos a montar um modelo similar para sua própria classe. Você vai ver que você está atualmente trabalhando jeito difícil, não do jeito fácil.

L

Eu quero aprender a não usar defaultTabeleModel, pois muita pesquisas que já fiz fala sobre isso, só que não sei fazer.
Vou postar código para você me ajudar.

vlw

L

Seguinte Vini, eu estou trazendo do banco da tabela produto para JComboBox(código) e JTxtField's(descrição,preço,tamanho,cor cada JTxtField corresponde a código selecionado no combo), quando informo a quantidade ele calcula valor total do produto. A cada produto calculado é adicionado na tabela(código,descrição,preço,quantidade e valor total) e depois de todo produto ser adicionado na Jatable queria incluir no banco. Daí que veio problema toda.

Segue código da classe produto:
@Entity
public class Produto {
   
    
    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    private int codigo;
    private int codigoProduto;
    private String nome;
    private String modelo;
    private String cor;
    private String sexo;
    private String tamanho;
    private float valorCusto;
    private double  valorVenda;
    private int quantidade;
    
    @ManyToOne
    @JoinColumn(name="codigo_for")
    private Fornecedor fornecedor;
    @ManyToOne
    @JoinColumn(name="codigoLoja")
    private Loja loja;

    public int getCodigo() {
        return codigo;
    }
    
    public void setCodigo(int codigo) {
        this.codigo = codigo;
    }
    
    public String getNome() {
        return nome;
    }
    
    public void setNome(String nome) {
        this.nome = nome;
    }
    
    public String getModelo() {
        return modelo;
    }
    
    public void setModelo(String modelo) {
        this.modelo = modelo;
    }
    
    public String getSexo() {
        return sexo;
    }
    
    public void setSexo(String sexo) {
        this.sexo = sexo;
    }
    
    public String getTamanho() {
        return tamanho;
    }
    
    public void setTamanho(String tamanho) {
        this.tamanho = tamanho;
    }
    
   

    public String getCor() {
        return cor;
    }

    public void setCor(String cor) {
        this.cor = cor;
    }

    public float getValorCusto() {
        return valorCusto;
    }

    public void setValorCusto(float valorCusto) {
        this.valorCusto = valorCusto;
    }

    public int getCodigoProduto() {
        return codigoProduto;
    }

    public void setCodigoProduto(int codigoProduto) {
        this.codigoProduto = codigoProduto;
    }
   public String  toString(){
        return"" +codigoProduto;

    }
    /**
     * @return the fornecedor
     */
    public Fornecedor getFornecedor() {
        return fornecedor;
    }

    /**
     * @param fornecedor the fornecedor to set
     */
    public void setFornecedor(Fornecedor fornecedor) {
        this.fornecedor = fornecedor;
    }

    /**
     * @return the valorVenda
     */
    public double getValorVenda() {
        return valorVenda;
    }

    /**
     * @param valorVenda the valorVenda to set
     */
    public void setValorVenda(double valorVenda) {
        this.valorVenda = valorVenda;
    }

    /**
     * @return the loja
     */
    public Loja getLoja() {
        return loja;
    }

    /**
     * @param loja the loja to set
     */
    public void setLoja(Loja loja) {
        this.loja = loja;
    }

    /**
     * @return the quantidade
     */
    public int getQuantidade() {
        return quantidade;
    }

    /**
     * @param quantidade the quantidade to set
     */
    public void setQuantidade(int quantidade) {
        this.quantidade = quantidade;
    }

    /**
     * @return the numeroNotaFiscal
     */
   
    /**
     * @return the dataEntrada
     */
  
}

método que calcula preço total

public Double CalculaprecoTotal(){
        String p= JLbPreco.getText();
        String q= JTxtQuantidade.getText();
        Double preco = Double.parseDouble(JLbPreco.getText());
        Integer quantidade = Integer.parseInt(JTxtQuantidade.getText());//.replace(",", "."));
        Double valorTotal = preco * quantidade;
        return valorTotal;
}
Método que adiciona dados para Jtable
try{
        if(!JTxtQuantidade.getText().trim().isEmpty()){
    DefaultTableModel dtm = (DefaultTableModel) jtProdutos.getModel();

    DefaultComboBoxModel dcbm = (DefaultComboBoxModel) JCBoxCodigoProduto.getModel();
    dtm.addRow(new Object[] {JTxtNomeProduto.getText(), dcbm.getSelectedItem().toString(), Double.parseDouble(JTxtPreco.getText()), Double.parseDouble(JTxtQuantidade.getText()), CalculaprecoTotal()});
   }
   else{
            JOptionPane.showMessageDialog(null,"Informe a quantidade para que possa ser adicionado na tabela");
   }
   }
   catch(Exception e){
       JOptionPane.showMessageDialog(null,"erro ao adicionar produto na tabela"+e.getMessage());
       e.printStackTrace();
   }
}
Método que remove
DefaultTableModel dtm = (DefaultTableModel) jtProdutos.getModel();
   int[] x = jtProdutos.getSelectedRows();//captura as linhas selecionadas
   for(int i =(x.length-1);i>=0;--i){
       dtm.removeRow(x[i]);//remove todas as linhas selecionadas
Método para inserir na tabelam Item
public void inserirItemvenda()
{
    try{
    
    for (int i = 0 ; i < jtProdutos.getRowCount() ; i++)
    {
        //if (jtProdutos.getValueAt(i, 0).equals(true))
          ctrItem = new CTR_ManterItemVenda();
          CTR_ManterProduto ctrProdutos = new CTR_ManterProduto();
          Produto produto = new Produto();
          NumberFormat format =NumberFormat.getInstance();
          ItemVenda item = new ItemVenda();
          String aux1=(String)jtProdutos.getValueAt(i,2);
          item.setValorUnitario((Double)format.parse(aux1));
          String aux2=(String)jtProdutos.getValueAt(i, 3);
          item.setQuantidade((Integer) format.parse(aux2));
          String aux3=(String)jtProdutos.getValueAt(i, 4);
          item.setValorTotal((Double)format.parse(aux3));
          item.setTamanho(String.valueOf(JTxtTamanho));
          item.setCor(String.valueOf(JTxtCor));
          produto = (Produto) ctrProdutos.carregarProdutoCodigoProduto((Integer) jtProdutos.getValueAt(i, 1));
          item.setIdProduto(produto);
          item.setIdVenda(venda);
          ctrItem.gravarItemVenda(item);
    }
} 
    catch(Exception e){
        JOptionPane.showMessageDialog(null,"Erro ao persistir objeto item venda: "+e.getMessage());
        e.printStackTrace();
    }
}
classe intem venda
@Entity
public class ItemVenda
{
    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    private Integer idItemVenda;
    
    @ManyToOne
    private Produto idProduto;
    @ManyToOne
    private Venda idVenda;
    private Integer quantidade;
    private String cor;
    private String tamanho;
    private double  valorUnitario;
    private double valorTotal;
    private double valorVencimento;
    private String dataVencimento;

    public Integer getIdItemVenda() {
        return idItemVenda;
    }

    public void setIdItemVenda(Integer idItemVenda) {
        this.idItemVenda = idItemVenda;
    }

    public Produto getIdProduto() {
        return idProduto;
    }

    public void setIdProduto(Produto idProduto) {
        this.idProduto = idProduto;
    }

    public Venda getIdVenda() {
        return idVenda;
    }

    public void setIdVenda(Venda idVenda) {
        this.idVenda = idVenda;
    }

    public double  getValorUnitario() {
        return valorUnitario;
    }

    public void setValorUnitario(double  valorUnitario) {
        this.valorUnitario = valorUnitario;
    }

    /**
     * @return the tamanho
     */
    public String getTamanho() {
        return tamanho;
    }

    /**
     * @param tamanho the tamanho to set
     */
    public void setTamanho(String tamanho) {
        this.tamanho = tamanho;
    }

    /**
     * @return the cor
     */
    public String getCor() {
        return cor;
    }

    /**
     * @param cor the cor to set
     */
    public void setCor(String cor) {
        this.cor = cor;
    }

    /**
     * @return the valorVencimento
     */
    public double getValorVencimento() {
        return valorVencimento;
    }

    /**
     * @param valorVencimento the valorVencimento to set
     */
    public void setValorVencimento(double valorVencimento) {
        this.valorVencimento = valorVencimento;
    }

    /**
     * @return the dataVencimento
     */
    public String getDataVencimento() {
        return dataVencimento;
    }

    /**
     * @param dataVencimento the dataVencimento to set
     */
    public void setDataVencimento(String dataVencimento) {
        this.dataVencimento = dataVencimento;
    }

    /**
     * @return the valorTotal
     */
    public double getValorTotal() {
        return valorTotal;
    }

    /**
     * @param valorTotal the valorTotal to set
     */
    public void setValorTotal(double valorTotal) {
        this.valorTotal = valorTotal;
    }

    /**
     * @return the quantidade
     */
    public Integer getQuantidade() {
        return quantidade;
    }

    /**
     * @param quantidade the quantidade to set
     */
    public void setQuantidade(Integer quantidade) {
        this.quantidade = quantidade;
    }
}

Qualquer coisa é só falar.

V

Ok, e que informações tem nas colunas da sua JTable? O que você quer listar na tabela?

V

Ah, agora que eu vi ali.

V

Ok, você então tem uma lista de produtos, e deseja listar os campos: código,descrição,preço,quantidade e valor total

Essas são as colunas do seu JTable, Certo?

Outra coisa. Como é calculado o valor total? Ele é o obtido pelo preço de venda vezes a quantidade?
Crie um método na classe Produto, para que ele mesmo saiba calcular o valor total.

N

"

V

Tenho outras dúvidas. A Tabela listará produtos ou ItemVenda?
Por que o itemVenda tem preço e quantidades, e o produto também?

L

código,descrição,preço,quantidade e valor total. São as colunas da Jtable!
O valor total é obtido pelo preço de venda vezes a quantidade!
Para criar este método eu precisaria de dados da JTxtField preço vindo do banco e quantidade informada pelo usário no fomrulário de venda, como capturo isso? Se eu tiver errado poder-me corrigir.

V

Sim. Que são colunas da JTable eu entendi. Mas essas colunas mostram dados de que objeto? Ou seja, se eu olhar para uma linha da sua JTable, estarei enxergando informações a respeito de que classe?

Veja bem. A JTable não existe “por si só”. Ela exibe alguma informação de suas classes. No caso do exemplo que eu passei ali em cima, a JTable lista livros. A sua JTable pode listar informações do produto, ou do ItemDeVenda, que aparentemente tem as informações que você colocou.

O ideal é sempre trabalhar com os objetos, nunca só com os valores soltos. Aparentemente, sua JTable lida com produtos, já que você está sendo obrigado a converter dados dela para um objeto da classe Produto, e provavelmente está fazendo o contrário também.

Você pode colocar um screenshot da sua tela atualmente? Aí fica mais fácil da gente se comunicar.

L

Tenho outras dúvidas. A Tabela listará produtos ou ItemVenda?
Reposta: a tabela listara dados do produto(codigo selecionado no combo,descriçao e preço correspondente a este código,valor total de cada produto, mais a quantidade informada.

Por que o itemVenda tem preço e quantidades, e o produto também?
Resposta: o item venda tem preço, quantidade e o produto, pois vou precisar de exibir o relatório de produto que foi mais vendido no mês, de que cor e quantidade, e qual foi o seu preço total com desconto.

Será que fui claro na explicação? Senão eu tento explicar da outra forma.

L

Sim. Que são colunas da JTable eu entendi. Mas essas colunas mostram dados de que objeto? Ou seja, se eu olhar para uma linha da sua JTable, estarei enxergando informações a respeito de que classe?

Veja bem. A JTable não existe “por si só”. Ela exibe alguma informação de suas classes. No caso do exemplo que eu passei ali em cima, a JTable lista livros. A sua JTable pode listar informações do produto, ou do ItemDeVenda, que aparentemente tem as informações que você colocou.

O ideal é sempre trabalhar com os objetos, nunca só com os valores soltos. Aparentemente, sua JTable lida com produtos, já que você está sendo obrigado a converter dados dela para um objeto da classe Produto, e provavelmente está fazendo o contrário também.

Você pode colocar um screenshot da sua tela atualmente? Aí fica mais fácil da gente se comunicar.

A minha Jtable exibe dados da classe produto que são:código,nome e preço.
Já quatidade jogo o que foi informada na JTxtField e o preço total, vem do calculo do preço total(preço x quantidade);

V

Ok, então vamos pensar num TableModel que, dada uma lista de objetos da classe Produto a exiba. É com a classe produto que iremos trabalhar, então, é ela que será representada no TableModel.

Antes de tudo, você tem que entender que quem chama os métodos padrão do TableModel (getColumnName(), getValueAt, etc) é o JTable. Não é você. Você irá chamar métodos que você vai adicionar no model, para inserir produtos, ou remover produtos da tabela. Os demais, é a tabela que irá usar, para perguntar para você que informações ela deve listar, na hora de construir a interface gráfica.

Pense assim. O Swing começa a desenhar a tabela. Mas ele ainda nem sabe quantas linhas ou quantas colunas sua tabela terá. O que ele faz? Ele pergunta para o model. Então, sempre encare os métodos padrão do model como respondendo a perguntas do Swing. Ok?

public class ProdutosTableModel extends AbstractTableModel {

    //Primeiro criamos constantes, para nossas colunas
    private static final int COL_CODIGO = 0; 
    private static final int COL_DESCRICAO = 1;
    private static final int COL_PRECO = 2;
    private static final int COL_QUANTIDADE = 3;    
    private static final int COL_TOTAL = 4;

    private List&lt;Produto&gt; valores;   //A lista de produtos que pretendemos exibir

    //Esse é um construtor, que recebe a nossa lista de produtos
    public ProdutosTableModel(Collection&lt;Produto&gt; valores) {
          this.valores = new ArrayList&lt;Produto&gt;(valores);
    }

    public int getRowCount() {
        //Quantas linhas tem sua tabela? Uma para cada item da lista.
        return valores.size();
    }

    public int getColumnCount() {
        //Quantas colunas tem a tabela? Na sua tabela, 5.
        return 5;
    }

    public String getColumnName(int columnIndex) {
        //Qual é o nome das nossas colunas? Isso aparecerá no cabeçalho
        if (columnIndex == COL_CODIGO) return "Código";
        if (columnIndex == COL_DESCRICAO) return "Descrição";
        if (columnIndex == COL_PRECO) return "Preço";
        if (columnIndex == COL_QUANTIDADE) return "Quantidade";
        if (columnIndex == COL_TOTAL) return "Total";
    }

    public Object getValueAt(int row, int column) {
        //Precisamos retornar o valor da coluna column e da linha row.
        //O JTable chama esse método quando precisa desenhar uma célula. E só ele deve chama-lo.
        //Você usará um método muito mais conveniente, chamado getProduto()
        Produto prod = valores.get(row);
        if (column == COL_CODIGO) prod.getCodigo();
        if (column == COL_DESCRICAO) prod.getNome(); //A descrição é só o nome mesmo?
        if (column == COL_PRECO) return prod.getPreco(); 
        if (column == COL_QUANTIDADE) return prod.getQuantidade();
        if (column == COL_TOTAL) return prod.getTotal(); //Esse método é o que eu disse que seria legal criar.
    }

    //Você deve implementar o setValueAt se sua tabela for editável.
    //Nesse exemplo, vou deixar alterar só a quantidade.
    public  void setValueAt(Object aValue, int rowIndex, int columnIndex) {
        try {
           if (columnIndex == COL_QUANTIDADE) valores.get(rowIndex).setQuantidade(Integer.parseInt(aValue.toString()));
        } catch (Exception e) {
           //Em caso de exceção, deixo o produto inalterado. Isso fará com que os valores antigos sejam desenhados.
           //Pode ocorrer caso o usuário digite uma letra na quantidade, por exemplo.
        }
    }

    public  Class getColumnClass(int columnIndex) {
        //Qual a classe das nossas colunas? 
        if (columnIndex == COL_CODIGO) return Integer.class;
        if (columnIndex == COL_DESCRICAO) return String.class;
        //As demais são double
        return Double.class;
    }
    
    boolean isCellEditable(int rowIndex, int columnIndex) {
        //Indicamos se a célula da rowIndex e da columnIndex é editável. Somente a quantidade é editavel nesse exemplo
        return columnIndex == COL_QUANTIDADE;
    }
    //Já que esse tableModel é de produtos, vamos fazer um get que retorne um produto inteiro.
    //Isso elimina a necessidade de chamar o getValueAt() nas telas. 
    public Produto get(int row) {
        return valores.get(row);
    }

    // --- Já respondemos ao Swing o que ele queria saber. Agora é hora de adicionar métodos para nós mesmo. :) 
    //Esse método permite adicionar um produto na JTable
    public void add(Produto produto) {
        //Adicionamos o produto
        valores.add(produto);
        //Avisamos a table, para que redesenhe a linha
        fireTablesRowInserted(valores.size()-1, valores.size()-1);
    }

    public List&lt;Produto&gt; getProdutos() {
       return Collections.unmodifiableList(valores);
    }
}

Tente substituir seu DefaultTableModel por esse. Ok, você vai ter que modificar sua tela quase inteira, mas veja que agora você tem um método “get” que retorna um produto inteiro e o método “add”, que adiciona um produto inteiro.

O usuário então preencherá a tela, com os dados do produto que quer adicionar. Quando ele clicar em “Adicionar”, você irá gerar um novo objeto da classe produto, e adiciona-lo diretamente no JTable.

Sua JTable pode ser preenchida inicialmente com os dados vindos do banco. Provavelmente o Hibernate já te retornará um List<Produto>. Caso queira a tabela vazia, é só passar um List em branco.

O model também te fornece o método getProdutos(), que permite listar todos os produtos dentro do JTable. Note que, usando esses métodos (add, get, e getProdutos()), não será necessário usar nem o getValueAt() nem o setValueAt(), e também não será necessário fazer casts, nem será necessário dar new na classe produto.

L

Vou fazer isso agora, qualquer coisa retorno.

Só uma pergunta, estou usando IDE NetBeans, então tenho que eliminar o componente Jtable que eu peguei da paleta?

V

Não, não. Você só vai alterar o model dele. O JTable continua o mesmo.

Não sei exatamente onde define o model no Netbeans, mas em algum lugar você vai fazer algo como:

List&lt;Produto&gt; produtos = ProdutosDao.carregarProduto(); seuTable.setModel(new ProdutosTableModel(produtos));

Ou, caso queira uma tabela vazia:

L

Neste método aparece erro sublinhado de vermelho no ProdutosTableModel

Erro:

java:1273: br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel is not abstract and does not override abstract method getValueAt(int,int) in javax.swing.table.TableModel public class ProdutosTableModel extends AbstractTableModel{

V

Posta seu model aí.

N

O Vini, é esse método mesmo?

fireTablesRowAdded(int,int)???

Deve ser sobre isso que o rapaz ta falando…

Não seria esse?

fireTablesRowsInserted(int,int)

[]'s

V

É verdade, é fireTableRowsInserted

L

Boa dia Vini,

Consegue mudar o Model, no NetBeans ele fica na propriedade da Jtabele!

Ele esta recusando column, será que tenho que declarar ele?

segue o erro:

C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1277: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_CODIGO)return "Código"; C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1279: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_DESCRICAO)return "Descrição"; C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1281: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_PRECO)return "Preço"; C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1283: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_QUANTIDADE)return "Quantidade"; C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1285: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_TOTAL)return "Total"; C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1302: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_QUANTIDADE) valores.get(rowIndex).setQuantidade(Integer.parseInt(aValue.toString())); C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1311: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_CODIGO) return Integer.class; C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1312: cannot find symbol symbol : variable column location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel if (column == COL_DESCRICAO) return String.class; C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1333: cannot find symbol symbol : method fireTablesRowsInserted(int,int) location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel fireTablesRowsInserted(valores.size()-1, valores.size()-1); C:\Documents and Settings\lagsilva\Desktop\KarinhaEstoque_Modficado\Karen Estoque\src\br\com\karinhaEstoque\view\formInclusaoVenda.java:1337: cannot find symbol symbol : variable Collections location: class br.com.karinhaEstoque.view.formInclusaoVenda.ProdutosTableModel return Collections.unmodifiableList(valores); Note: Some input files use unchecked or unsafe operations. Note: Recompile with -Xlint:unchecked for details. 10 errors FALHA NA CONSTRUÇÃO (tempo total: 3 segundos)

V

É pq no método o nome do parâmetro é columnIndex, não column.

Eu já avisei que estou sem netbeans aqui, e faço as coisas de cabeça. Você pode tentar corrigir errinhos bobos como esse? A exception já descrevia qual era o problema, tente entender o código ao invés de só copiar e colar.

Já corrigi ali em cima.

L

Estou achando que ele deve retornar ColumnIndex invés de column.

V

Sim, ali em cima eu corrigi.

Veja que o método getColumnName foi declarado assim:
public String getColumnName(int columnIndex) {

Mas internamente estou usando a variável com o nome só de column

Você pode corrigir o problema declarando assim:
public String getColumnName(int column) {

Ou, alterando o uso interno para columnIndex. Eu editei o código ali em cima e fiz as correções, onde necessário.

L

Eu digitei tudo na mão e tentei enteder pelo comentário.
Eu tentei ver o erro que aparece no método public String getColumnName(int columnIndex)//que exibie nome das colunas no cabeçalho da Jatable, procurei no net, não achei nada específico.
aparece este erro:missing return statement

V

Ah sim, é pq todos os returns estão dentro de ifs. Você precisa ter um return fora.
Corrigir isso é simples. Antes da última linha do método faça:

Ou simplesmente faça:

Isso vale tanto para o getColumnName() quanto para o getValueAt.

No fundo, esse código nunca executará, pois o JTable jamais irá passar para você um número de coluna que não existe.

N

Vini eu to com um problema, se poder me ajudar…

Meus dados estão vindo de uma planilha do Excel. Minha “filha” da TableModel é um pouco diferente da que vc apresentou. Mas o fato é que preciso que os dados sejam obtidos apartir da linha 6 da planilha (index 5 no meu código) e quando coloco:

public int getRowCount() {
            return sheet.getRows()+5;//testei com 100 tb, por via das dúvidas.
        }

   public Object getValueAt(int rowIndex, int columnIndex) {
                 rowIndex = linhaInicial++;//Variável global iniciada com o valor 5.
                 Cell cell = sheet.getCell(columnIndex, rowIndex);//Essa é minha linda 51 do erro abaixo
                return cell.getContents();           

        }

   /**          SEGUINTE ERRO APRESENTADO       **/

  java.lang.ArrayIndexOutOfBoundsException: 30
  at jxl.read.biff.SheetImpl.getCell(SheetImpl.java:356)
  at utilidades.SheetTableModel.getValueAt(SheetTableModel.java:51)
  at javax.swing.JTable.getValueAt(JTable.java:2695)

Na minha planilha existem apenas 30 linhas e por causa dessa exception adicionei mais 5 no getRows para verificar.
E ela continua …

O que pode ser hein??

Se achar necessário o código me avise.

[]'s

M

Acho que seu unico problema é:

public int getRowCount() {  
           return sheet.getRows()+5;
       }

Pois RowCount retorna o numero de linhas e sua planilha provavelmente nao tem o total+5… mesmo lendo a aprtir da quinta linha acho que voce devia tirar o +5 para ler apenas até o final.

N

Mark_Ameba:
Acho que seu unico problema é:

Pois RowCount retorna o numero de linhas e sua planilha provavelmente nao tem o total+5… mesmo lendo a aprtir da quinta linha acho que voce devia tirar o +5 para ler apenas até o final.

Então Mark eu havia feito isso que vc sugeriu, mas não deu certo tb cara. Tentei bolar uma lógica dentro desse método mais até agora não deu certo.
Na verdade, estou começando a enteder agora como funciona a TableModel…

Muito grato desde já!

[]'s

N

Alguém mais disposto a ajudar um pobre iniciante? Só lembrando que após a importação vou “Inserir dados da Jtable no banco” :smiley:

[]'s

V

neeryck:
Então Mark eu havia feito isso que vc sugeriu, mas não deu certo tb cara. Tentei bolar uma lógica dentro desse método mais até agora não deu certo.
Na verdade, estou começando a enteder agora como funciona a TableModel…

Todos nós estamos. Mas seria bastante útil se postasse o que você fez, a lógica que você quis bolar, o que não deu certo e, se deu erro, que erro deu e aonde. Senão fica impossível te ajudar.

Criado 16 de dezembro de 2009
Ultima resposta 2 de jan. de 2010
Respostas 50
Participantes 6