Whats the proper event for changes in any cell of JTable? - java

I have a simple JTable, there are two columns that matter: quantity and value (Integers). Each time user enters a new row or updates one, each rows value must be multiplied by quantity, results sumed together and the result sum displayed in a JLabel outside the JTable. Looks pretty simple. Except that I have no idea what event should I look for. Something like "cell value changed"? When I right click on the JTable in NetBeans I see no such event or dont recognize it ;) Anyway, before I come up with some weird noobish solution I thought I might ask here what's the proper way to do it :)

you should add a TableModelListener as described here.
also, in your listener once you've updated the value of the other cell values programatically you will need to call model.fireTableCellUpdated to let swing know about the changes

Finally I managed to find how to do it in NetBeans with all the code protection, et cetera. It's right click on JTable in Design View, Properties, then Code tab, and then add your code in Pre-Adding Code section (code evaluated before table is added to container or something like that).
The exact code which works for me is this:
table.getModel().addTableModelListener(
new TableModelListener()
{
public void tableChanged(TableModelEvent evt)
{
// here goes your code "on cell update"
}
});
I am aware that Tom, above, suggested never calling getModel() but I'm too new to Java to understand why (care to explain, please..?) :) and it's just an example anyway, I'm adding this answer just to show how to do it in NetBeans (thanks pstanton for answering what to do). Because I found so many people asking this in internet and no real answers (apart from "copy your protected code out of NetBeans protected area and then customize your table).

Related

Options menu for one cell in java table

Welcome
In this table, I made the column mentioned cells editable to let the users make the needed value as they want ...
But they told me the values of this column can take just one of the values: 25,50,75,100, so, they asked me I make an options menu (like it is mention in the pic) allow them to choose directly the needed value and working fast.
So, how can I solve it, please!
(note: I'm working with java swing)
It's not the same question, but you can take a look on solution from below question:
How do I create a right click context menu in Java Swing?
you should create such listener, and add it to your Cell / Table.
you can take a look on below question to understand how to add listener to your Cell (it's not obvious :/)
JTable cell listener?

getValueIsAdjusting() disable in JList but now I cant select a choice twice in a row

I have a JList in which each option increments a variable and do some other simple stuff. My ListSelectionListener run twice at each selection with mouse, so I put the condition if(!getValueIsAdjusting()) to run my code inside the listener just once per click selection. Now once I select, for example, option 1 it runs well, but if I want to select again this option nothing happens. So basically I cant select twice in a row the same option. (There is no problem if I go back to a choice I've chosen before). Any solution is welcomed. Thanks in advance
I found a solution to the problem and I wanted to share it with you guys.
After doing the stuff inside the valueChanged method I call the method
clearSelection(). This put the selected index to -1. To handle errors from this, in the the if condition I added getSelectedIndex()>=0. So the code:
private class KategoriHandler implements ListSelectionListener{
public void valueChanged(ListSelectionEvent e) { if(!e.getValueIsAdjusting()&&kategori.getSelectedIndex()>=0){
//do the stuff;
kategori.clearSelection();}

JTable Data Refresh Issue

I want to refresh the JTable data by clicking a button.
The problem is that the old data in the JTable can't be removed and the new data are just added into the table. I tried below ways to remove the old data but none of them works.
1. table.setModel(new DefaultTableModel());
2. ((DefaultTableModel)table.getModel()).setRowCount(0);
3. ((DefaultTableModel)table.getModel()).fireTableDataChanged();
4. ((DefaultTableModel)table.getModel()).getDataVector().removeAllElements();
5. table.repaint();
6. model = (DefaultTableModel)table.getModel();
while(model.getRowCount() > 0) {
model.removeRow(0);
}
Having a refresh button for a JTable is very suspect. It makes me think you aren't correctly adding data as JTables should refresh everytime data is added or removed.
I would verify a couple of things when using a DefaultTableModel:
Make sure to only add data using addRow
Data should only be inserted using insertRow
Remove data using removeRow
Never modify the internal vectors directly. It won't cause events to fire and you're stuck with a refresh button. I don't know why they even expose it. The JavaDocs should at least specifically warn against this.
If all else fails, fire up a debugger and see what happens.
More of your code might be appropriate here. Hard to tell exactly where you're calling these methods and the order. If you change the model and then call fireTableDataChanged() it should work....assuming you've updated the right TableModel. There is a good Java tutorial for using tables: http://docs.oracle.com/javase/tutorial/uiswing/components/table.html
Had the same issue myself, but my solution was different. After checking just about everything, I checked the contents of the table via the console, and found that the contents were indeed being updated. However, the update was not being reflected on the table which was visible on the screen.
In fact, this code:
model = (DefaultTableModel)table.getModel();
while(model.getRowCount() > 0) {
model.removeRow(0);
}
Did not only remove the rows, but also removed the table.
My solution was to remove the table from the form and then re-add it, whenever the table data was changed.
Seemed in my case there was nothing wrong with my coding to generate the table but that the layout manager didn't like overwriting or updating a component the area where I wanted to put it already had something in there.
Something weird going on methinks but at the end of the day this worked for me.

Changing current selection in JXTable doesn't work?

I have a JXTable where the users need to introduce data, then save it. Only the thing is, the user has to deselect the last edited cell before saving it. If they don't, the data of that cell isn't saved.
The only thing I thought of is to change the current selection automatically just before saving. This is what i tried :
table.getSelectionModel().setSelectionInterval(0, 0);
table.getColumnModel().getSelectionModel().setSelectionInterval(0, 0);
OR
table.getSelectionModel().setLeadSelectionIndex(0);
table.getColumnModel().getSelectionModel().setLeadSelectionIndex(0);
None of both seem to work yet these are the only two methods I found to do this.
Can anyone please tell me how to do this properly or propose an alternative to also let it save the data from that last cell?
I am assuming the user clicks on another component (JButton) when he wishes to save data. If you have a reference to the JXTable when that event happens you could add the following piece of code there:
if (table.isEditing()) {
table.getCellEditor().stopCellEditing();
}
The stopCellEditing() should save the state of the model and allow you to save all the contents, including the currently selected / edited cell.
EDIT: As kleopatra pointed out, the default (and better!) way to handle this is through the client property of JTable component:
table.putClientProperty("terminateEditOnFocusLost", Boolean.TRUE);
For JXTable this should already be set though, which indicates that the way your UI handling of the save functionality works does not include moving the focus away from the table. So in essence you'd be better off changing the focus when your 'save' event is being fired.

Java table arraylist modification

Basically it's a task to manage properties, and I am doing a much more complex solution than it is required. It is just the last bit where I struggle.
To give you an idea of what we have:
Properties (superclass)
PropertiesToLet(extends Properties)
PropertiesToSell(extends Properties)
EstateAgent (GUI to manage the properties)
So the part I am struggling with is basically the EstateAgent class.
What I wrote so far: http://pastebin.com/0qieM67j
That a about 500 lines - But I need help with the theoretical part not the programming part - because I dont want you to do my coursework - I just need the solution how to approach that.
The lines I am struggling with are from:
55 to 113
Its about a table that I create and insert rows into it. Each row represents a property. It could be a propertyToLet or a propertyToSell object. Those properties come from my ArrayList<Property> properties.
The inserting row and showing the table is fine and it is working the way it should. So there is problem with the code. I apologize for the code structure - but we are limited in the submission - so we cannot submit more than 4 files those file are obviously the named classes - so I cannot extend any more classes or files to the project.
So what I want to do now is: Editing a property.
I have the row that represents a property. It is showing me the position in the arrayList and all the values that I can get.
So now there are a few more possibilities.:
Add and Remove a tenant from a PropertyToLet
base on a tenant you can collect the rent and pay the rent and see how much rent is left to pay.
Add and Remove a purchaser from a PropertyToSell (the sold will then change according if there is a purchaser or not)
So basically there are several ways how to continue from here. For instance it could be a behaviour like this:
RightClick on the property opens a context menu where the mouse is and I can choose other options such as: Remove Tenant, Add Tenant, Collect Rent, Show Rent Owed, Add a purchaser, Remove a purchaser ---- ofcourse depending on what kind of property it is.
Double click on a row => edit the property ( have a look at this screenshot)
it shows a window that I use to add a property - I could add all the values in the field and that button changes to "Update Property"
That would be one solution another one would be:
- Edit the cell of the row => changes the value of the property (they will inspect the object and see if that really changed and not just the row value)
That are my ideas of how to inject the last steps of bringing the functionality into the application.
So here are my questions:
And than I need an outside opinion what is easier and faster to implement in this very limited task. The way of opening the existing add window and change it to an edit window - I don't want to have redundant code!
Or changing the value by editing the cell so that the values in the arraylist change.
I need some help with the approach what is easier and what is better.
I really appreciate any help here!
I am looking forward to see some answers.
EDIT
I finished the popup Menu thank you for your help. I edited the question as wel.
Since jdk5, the recommended way to attach a JPopupMenu to a component is
component.setComponentPopupMenu(menu)
This popup is automatically shown when a user gesture (mouse or keyboard) is interpreted as popup trigger - which may vary across OSs.
As to selecting a row on right (popup-trigger) mouseEvent: it's not done by default in Swing, but seems to be the norm nowadays for (near-)native applications (on vista) - arguably a but in Swing. Volunteers to report, anybody ;-)

Categories

Resources