imarquez
asked on
I can't refresh the contents of a JTable
Hello:
I'm working on a little database aplication in Java, I have a JTable that gets the data from a MySQL database, the table loads the data OK, but when I try to refresh it if a row is inserted or updated the results are not updated
Here is the code I made:
The method refrescarGrilla is the method that fills the data when the table is displayed, the secon method is used to refresh the data
What am I doing wrong?
I'm working on a little database aplication in Java, I have a JTable that gets the data from a MySQL database, the table loads the data OK, but when I try to refresh it if a row is inserted or updated the results are not updated
Here is the code I made:
The method refrescarGrilla is the method that fills the data when the table is displayed, the secon method is used to refresh the data
What am I doing wrong?
It will help if you actually post the code... :)
where is the code?
btw, you will need to call fireTableDataChanged() or fireTableRowsInserted(int, int) after updating the data in the model!
btw, you will need to call fireTableDataChanged() or fireTableRowsInserted(int,
ASKER
I attached a code snippet but didn't show
Here it is:
public void refrescarGrilla(){
headVector.addElement("Nro Ped");
headVector.addElement("Fec ha Pedido");
headVector.addElement("Cli ente");
headVector.addElement("Dir eccion");
headVector.addElement("Art iculo");
headVector.addElement("Mov il");
headVector.addElement("Mov il prox");
headVector.addElement("Can tidad");
headVector.addElement("Fle te");
headVector.addElement("Tot al");
List lista;
lista = Persistir.getInstancia().l istarPedid os();
DefaultTableModel modelo = new DefaultTableModel();
modelo.setDataVector((Vect or) lista, headVector);
jTable1.setModel(modelo);
modelo.addTableModelListen er(jTable1 );
jTable1 = tblRes.autoResizeColWidth( jTable1, modelo);
modelo.fireTableDataChange d();
}
public void actualizarGrilla(){
List lista;
lista = Persistir.getInstancia().l istarPedid os();
DefaultTableModel modelo = new DefaultTableModel();
modelo.addTableModelListen er(jTable1 );
modelo.setDataVector((Vect or) lista, headVector);
jTable1 = tblRes.autoResizeColWidth( jTable1, modelo);
modelo.fireTableDataChange d();
}
Here it is:
public void refrescarGrilla(){
headVector.addElement("Nro
headVector.addElement("Fec
headVector.addElement("Cli
headVector.addElement("Dir
headVector.addElement("Art
headVector.addElement("Mov
headVector.addElement("Mov
headVector.addElement("Can
headVector.addElement("Fle
headVector.addElement("Tot
List lista;
lista = Persistir.getInstancia().l
DefaultTableModel modelo = new DefaultTableModel();
modelo.setDataVector((Vect
jTable1.setModel(modelo);
modelo.addTableModelListen
jTable1 = tblRes.autoResizeColWidth(
modelo.fireTableDataChange
}
public void actualizarGrilla(){
List lista;
lista = Persistir.getInstancia().l
DefaultTableModel modelo = new DefaultTableModel();
modelo.addTableModelListen
modelo.setDataVector((Vect
jTable1 = tblRes.autoResizeColWidth(
modelo.fireTableDataChange
}
refrescarGrilla should be called in the EventDispatchThread. Run the update in another thread.
Use the (execellently documented) SwingWorker to do this
Use the (execellently documented) SwingWorker to do this
ASKER
could you provide an example? I never used it before
There are examples in the docs
ASKER
Do I need to create another class that extends SwingWorker or I should make the JTable extend it so I can call the method to refresh the table?
Create a subclass of SwingWorker. Call it TableRefresher of something
try this and let me know,
public void refrescarGrilla(){
headVector.addElement("Nro Ped");
headVector.addElement("Fec ha Pedido");
headVector.addElement("Cli ente");
headVector.addElement("Dir eccion");
headVector.addElement("Art iculo");
headVector.addElement("Mov il");
headVector.addElement("Mov il prox");
headVector.addElement("Can tidad");
headVector.addElement("Fle te");
headVector.addElement("Tot al");
List lista;
lista = Persistir.getInstancia().l istarPedid os();
DefaultTableModel modelo = ( DefaultTableModel )jTable1.getModel();
modelo.setDataVector((Vect or) lista, headVector);
}
SwingWorker is needed if you want to do the operations in separate threads!
public void refrescarGrilla(){
headVector.addElement("Nro
headVector.addElement("Fec
headVector.addElement("Cli
headVector.addElement("Dir
headVector.addElement("Art
headVector.addElement("Mov
headVector.addElement("Mov
headVector.addElement("Can
headVector.addElement("Fle
headVector.addElement("Tot
List lista;
lista = Persistir.getInstancia().l
DefaultTableModel modelo = ( DefaultTableModel )jTable1.getModel();
modelo.setDataVector((Vect
}
SwingWorker is needed if you want to do the operations in separate threads!
ASKER
ksivananth, it didn't work, the table still doesn't show the update, I'll try using SwingWorker, but i still have no clue of how to do it, how can I run these methos in the eventDispatcher Thread using SwingWorker?
>>it didn't work, the table still doesn't show the update
it should work, are you sure the reference of jTable1 is same?
it should work, are you sure the reference of jTable1 is same?
this simple example works,
class TableGUI extends JFrame implements ActionListener
{
JTable tb;
JButton bt;
public TableGUI()
{
setTitle("This is a table GUI");
setSize(300,300);
setLayout(new BorderLayout());
Object[][] studentDetails = {{new String("Mary"), new String("A101"), new Double(22.1)},{new String("John"), new String("A102"), new Double(25.1)}};
String[] title = {"Name", "ID", "Score"};
DefaultTableModel model = new DefaultTableModel( studentDetails, title ) ;
tb = new JTable( model );
bt = new JButton("Score");
bt.addActionListener(this) ;
add(new JScrollPane(tb), BorderLayout.CENTER);
add(bt, BorderLayout.SOUTH);
}
public void actionPerformed(ActionEven t ae)
{
int[] row = tb.getSelectedRows();
if(row.length == 0)
{
Object[][] studentDetails = {{new String("Mary - 1"), new String("A101"), new Double(22.1)},{new String("John - 1"), new String("A102"), new Double(25.1)}};
String[] title = {"Name", "ID", "Score"};
DefaultTableModel model = ( DefaultTableModel )tb.getModel() ;
model.setDataVector( studentDetails, title ) ;
}
}
public static void main(String[] args)
{
JFrame f = new TableGUI();
f.setVisible(true);
}
}
class TableGUI extends JFrame implements ActionListener
{
JTable tb;
JButton bt;
public TableGUI()
{
setTitle("This is a table GUI");
setSize(300,300);
setLayout(new BorderLayout());
Object[][] studentDetails = {{new String("Mary"), new String("A101"), new Double(22.1)},{new String("John"), new String("A102"), new Double(25.1)}};
String[] title = {"Name", "ID", "Score"};
DefaultTableModel model = new DefaultTableModel( studentDetails, title ) ;
tb = new JTable( model );
bt = new JButton("Score");
bt.addActionListener(this)
add(new JScrollPane(tb), BorderLayout.CENTER);
add(bt, BorderLayout.SOUTH);
}
public void actionPerformed(ActionEven
{
int[] row = tb.getSelectedRows();
if(row.length == 0)
{
Object[][] studentDetails = {{new String("Mary - 1"), new String("A101"), new Double(22.1)},{new String("John - 1"), new String("A102"), new Double(25.1)}};
String[] title = {"Name", "ID", "Score"};
DefaultTableModel model = ( DefaultTableModel )tb.getModel() ;
model.setDataVector( studentDetails, title ) ;
}
}
public static void main(String[] args)
{
JFrame f = new TableGUI();
f.setVisible(true);
}
}
Actually in this case you can just update the model and call fireTableDataChanged in the doInBackground method
do you see any exception?
>>it didn't work, the table still doesn't show the update
posting the code that did not work might help someone spot something wrong :) Just a note.
posting the code that did not work might help someone spot something wrong :) Just a note.
if it doesn't work, it won't work with SwingWorker too!
ASKER
this is the code that updates an object to the database and calls for the actualizarGrilla method, which does refresh the updated rows
private void btnActualizarPedidoActionP erformed(j ava.awt.ev ent.Action Event evt) {
Persistir p = Persistir.getInstancia();
int row = jTable1.getSelectedRow();
Integer val =(Integer) jTable1.getValueAt(row, 0);
Pedidos ped = new Pedidos();
Articulos art = new Articulos();
art=(Articulos) cboArticulos.getSelectedIt em();
int id = val;
ped = p.buscarPedidoPorId(id);
ped.setMovilAsignado((Movi les) cboMoviles.getSelectedItem ());
ped.setCantidad(Integer.pa rseInt(txt Cantidad.g etText())) ;
ped.setFlete(Integer.parse Int(txtFle te.getText ()));
ped.setIdArticulo(art);
ped.setMovilAsignado((Movi les) cboMoviles.getSelectedItem ());
ped.setObservaciones(txtOb servacione s.getText( ));
p.actualizarPedido(ped);
actualizarGrilla();
}
private void btnActualizarPedidoActionP
Persistir p = Persistir.getInstancia();
int row = jTable1.getSelectedRow();
Integer val =(Integer) jTable1.getValueAt(row, 0);
Pedidos ped = new Pedidos();
Articulos art = new Articulos();
art=(Articulos) cboArticulos.getSelectedIt
int id = val;
ped = p.buscarPedidoPorId(id);
ped.setMovilAsignado((Movi
ped.setCantidad(Integer.pa
ped.setFlete(Integer.parse
ped.setIdArticulo(art);
ped.setMovilAsignado((Movi
ped.setObservaciones(txtOb
p.actualizarPedido(ped);
actualizarGrilla();
}
ASKER
This is the full code for the class, it´s an internal frame form generated with netbeans.
intFrmPedidos.zip
intFrmPedidos.zip
>>private void btnActualizarPedidoActionP erformed(j ava.awt.ev ent.Action Event evt) {
An intensive code that run in there must be moved into a background thread or it will block your GUI
An intensive code that run in there must be moved into a background thread or it will block your GUI
ASKER
Ok, how do I move it to a background thread? I never did "thread management" before
>>how do I move it to a background thread
I would suggest you to resolve the problem in hand first and then move to thread as that would take some time for you to understand!
I would suggest you to resolve the problem in hand first and then move to thread as that would take some time for you to understand!
>>this is the code that updates an object to the database and calls for the actualizarGrilla method, which does refresh the updated rows
I was under the impression that you are calling refrescarGrilla on button click!
I was under the impression that you are calling refrescarGrilla on button click!
ASKER
but, the problem in hand wouldn't be the refreshing of the table? wich would be solved moving those methods to another thread? excuse me if i'm lost, but this problem is driving me nuts and i haven't found a working solution in any other place
try this then,
public void actualizarGrilla(){
List lista;
lista = Persistir.getInstancia().l istarPedid os();
DefaultTableModel modelo = ( DefaultTableModel )jTable1.getModel();
modelo.setDataVector((Vect or) lista, headVector);
}
public void actualizarGrilla(){
List lista;
lista = Persistir.getInstancia().l
DefaultTableModel modelo = ( DefaultTableModel )jTable1.getModel();
modelo.setDataVector((Vect
}
ASKER
Yes, the button takes the selected object from the row, updates the object with new values and saves it back to de database, and refrescarGrilla is called at the end to reflect those changes
sorry I am lost with the method names! let me take the look at your complete code!
ASKER
refrescarGrilla would be "refreshGrid" and actualizarGrilla "updateGrid", the names are very similar so the confusion is understandable
the refrescarGrilla is called no where in the actionperformed method!
all the places you are just calling actualizarGrilla!
did you try my comment #24040101?
ASKER
ksivananth: I did try. The same thing, it's not refreshing the table. I don't have the slightest idea where the problem is. I'm starting to feel defeated because I did everithing I'm supposed to do (except the "thread thing") but nothing worked out
"thread thing" is just for efficience and won't fix the problem!
can you check if
lista = Persistir.getInstancia().l istarPedid os();
returns updated list?
lista = Persistir.getInstancia().l
returns updated list?
ASKER
Sorry, my mistake. But I need to find where the problem is, I tried all the solutions people gave me but still nothing. You guys are my last hope
I'm starting to sound pathetic, sorry
I'm starting to sound pathetic, sorry
it would be lot easier for you to locate the problematic area if you debug the code line by line!
ASKER
I ran a debug line by line many times but there is not a single problem in the execution
ASKER
didn't anyone found a solution?
ASKER
Ok, I added a button that calls for the refreshing of the table.
Thing is if I update a record the table don't show the updates, if I hit the new button nothing happens.... After waiting a few seconds if I hit it again calling for actualizarGrilla() THE TABLE REFRESHES!!!!!! why is that?
Thing is if I update a record the table don't show the updates, if I hit the new button nothing happens.... After waiting a few seconds if I hit it again calling for actualizarGrilla() THE TABLE REFRESHES!!!!!! why is that?
>>After waiting a few seconds if I hit it again calling for actualizarGrilla() THE TABLE REFRESHES!!!!!! why is that?
could be that it takes some time to save the data to DB table. so if you press the button before the data get saved to DB, you won't see the update in JTable but if wait for the data to be updated in DB and then hit that button you see the update!
could be that it takes some time to save the data to DB table. so if you press the button before the data get saved to DB, you won't see the update in JTable but if wait for the data to be updated in DB and then hit that button you see the update!
ASKER
But the funny thing is that the List that gets the updated data is loaded normally and in time, so the delay has no sense, and I don't really know why is that.
>>List that gets the updated data is loaded normally and in time
how do you say this?
how do you say this?
you can have some SOPs to know what happens when you click the button!
ASKER
After running a debug in Netbeans I added a watch to the List object that gets the result from the DB, the List gets de data updated, the model takes the new list but the changes are not shown in the table
ASKER
I tried to run the model and table updating processes in the background, it didn't throw any exception but the results are the same, no data updated in the table. Maybe I'm not doing it right.
public void actualizarGrilla(){
SwingWorker<DefaultTableMo del, Object> worker = new SwingWorker<DefaultTableMo del, Object>(){
@Override
protected DefaultTableModel doInBackground(){
Vector lista;
lista = Persistir.getInstancia().l istarPedid os();
DefaultTableModel modelo = new DefaultTableModel();
modelo.addTableModelListen er(jTable1 );
modelo.setDataVector(lista , headVector);
return modelo;
}
@Override
protected void done(){
try {
DefaultTableModel modelo = get();
jTable1 = tblRes.autoResizeColWidth( jTable1, modelo);
modelo.fireTableDataChange d();
} catch (InterruptedException ex) {
Logger.getLogger(intFrmPed idos.class .getName() ).log(Leve l.SEVERE, null, ex);
} catch (ExecutionException ex) {
Logger.getLogger(intFrmPed idos.class .getName() ).log(Leve l.SEVERE, null, ex);
}
}
};
worker.execute();
}
public void actualizarGrilla(){
SwingWorker<DefaultTableMo
@Override
protected DefaultTableModel doInBackground(){
Vector lista;
lista = Persistir.getInstancia().l
DefaultTableModel modelo = new DefaultTableModel();
modelo.addTableModelListen
modelo.setDataVector(lista
return modelo;
}
@Override
protected void done(){
try {
DefaultTableModel modelo = get();
jTable1 = tblRes.autoResizeColWidth(
modelo.fireTableDataChange
} catch (InterruptedException ex) {
Logger.getLogger(intFrmPed
} catch (ExecutionException ex) {
Logger.getLogger(intFrmPed
}
}
};
worker.execute();
}
if you use SwingWorker, in the doInBackground method you would do the DB update operation and in the done method you would get the updated list and set it to model!
>>Vector lista;
lista = Persistir.getInstancia().l istarPedid os();
DefaultTableModel modelo = new DefaultTableModel();
modelo.addTableModelListen er(jTable1 );
modelo.setDataVector(lista , headVector);
>>
btw, the above code is not correct, refer my earlier comments where have taken the model from the table itself instead of creating it!
>>Vector lista;
lista = Persistir.getInstancia().l
DefaultTableModel modelo = new DefaultTableModel();
modelo.addTableModelListen
modelo.setDataVector(lista
>>
btw, the above code is not correct, refer my earlier comments where have taken the model from the table itself instead of creating it!
and as I sadi earlier, SwingWorker won't solve the issue you have but its an efficient way of doing it!
ASKER
Ok, thanks for the advice, your patienece is admirable, I'm feeling like pain in the a.... sorry. I already did take the model from the table in previous tryouts but the result is the same, that delay in the updating table process seems inexplicable
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.