Granny's Programming Pearls
"inside of every large program is a small program struggling to get out"
JavaRanch.com/granny.jsp
  • Post Reply Bookmark Topic Watch Topic
  • New Topic

Help with DefaultTableModel  RSS feed

 
Talhah Mafawalla
Greenhorn
Posts: 24
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Hi again.

I have am having a problem extending on a DefaultTableModel class. The following is the code that i am working with:

The nex two lines is how i am calling the MyTableModel Class which is an inner class.

MyTableModel mtm = new MyTableModel();
JTable table = new JTable(mtm);

The following class is an inner class:
class MyTableModel extends DefaultTableModel{

Vector vColumnNames;
Vector vData;

public MyTableModel(){
vColumnNames = new Vector();
vData = new Vector();

vColumnNames.addElement("Product");
vColumnNames.addElement("Quantity");
vColumnNames.addElement("Total");
vData.addElement("Hello1");
vData.addElement("Hello2");
vData.addElement("Hello3");

}

public int getRowCount() {
return vData.size(); //The Error occurs here
}

public int getColumnCount() {
return vColumnNames.size();
}

public String getColumnName(int col) {
return (String)vColumnNames.elementAt(col);
}

public Class getColumnClass(int c) {
return getValueAt(0, c).getClass();
}

public Object getValueAt(int rowIndex, int columnIndex) {

return vData.elementAt(rowIndex);
}

public boolean isCellEditable(int row, int col) {
if (row == 0 && col == 0 || row == 0 && col == 1) {
return true;
}if(row == 0 && col == 2){
return false;
}else {
return false;
}
}

public void setValueAt(Object value, int row, int col) {
if (DEBUG) {
System.out.println("Setting value at " + row + "," + col
+ " to " + value
+ " (an instance of "
+ value.getClass() + ")");
}

vData.setElementAt(value, row);
fireTableCellUpdated(row, col);

if (DEBUG) {
System.out.println("New value of data:");
printDebugData();
}
}

private void printDebugData() {
int numRows = getRowCount();
int numCols = getColumnCount();

for (int i=0; i < numRows; i++) {
System.out.print(" row " + i + ":");
for (int j=0; j < numCols; j++) {
//System.out.print(" " + oData[i][j]);
}
System.out.println();
}
System.out.println("--------------------------");
}

}


What happens is that when i run the class the following error is thrown:
init:
deps-jar:
compile:
Exception in thread "main" java.lang.NullPointerException
at ordermanagementsystem.OrderForm$MyTableModel.getRowCount(OrderForm.java:156)
at javax.swing.table.DefaultTableModel.setDataVector(DefaultTableModel.java:198)
at javax.swing.table.DefaultTableModel.<init>(DefaultTableModel.java:98)
at javax.swing.table.DefaultTableModel.<init>(DefaultTableModel.java:80)
at javax.swing.table.DefaultTableModel.<init>(DefaultTableModel.java:60)
at ordermanagementsystem.OrderForm$MyTableModel.<init>(OrderForm.java:139)
at ordermanagementsystem.OrderForm.<init>(OrderForm.java:76)
at ordermanagementsystem.OrderForm.main(OrderForm.java:131)
Java Result: 1
debug-stepinto:
BUILD SUCCESSFUL (total time: 25 seconds)

The error is on line 20 of the MyTableModel Class, which says
"return vData.size()"

When i run the programe in step through mode and the compiler comes to the line at which i am declaring the object of the MyTableModel Class
MyTableModel mtm = new MyTableModel();

The compiler is then taken to the constructor of the MyTableModel class but only the to the first line

public MyTableModel(){ //Only this line
vColumnNames = new Vector();
vData = new Vector();

vColumnNames.addElement("Product");
vColumnNames.addElement("Quantity");
vColumnNames.addElement("Total");
vData.addElement("Hello1");
vData.addElement("Hello2");
vData.addElement("Hello3");

}

, then the compiler goes straight to the following method:

public int getRowCount() {
return vData.size();
}

Thus the the vectors where not initialised or even known and thus giving the NullPointerException. This is a really odd problem because when i change it to "extends AbstractTableModel" the lines where i declare the variables "vData" and "vColumnNames" then the constructor of the MyTableModel class are before any of the other methods.

Please can anyone help me for the solution. Thanks in advance for any help that anyone gives. Also sorry for posting so much text but i wanted to put as much information as possible about the problem as i could.

Thanks again
Talhah Mafawalla
 
Michael Dunn
Ranch Hand
Posts: 4632
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
just a thought (untested).
from what you've described in the step-through, try these changes

 
Talhah Mafawalla
Greenhorn
Posts: 24
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Thanks you for replying, though i have tryed your suggestion but the results are the same. The problem is that it is not reading the declaration of the variables first it is juping to the
public int getRowCount(){
return vData.size();
}


method, thus it sees that "vData" as bieng null. What i thought is that, shouldnt the contructor of MyTableModel be run first.

Please help.

Thanks for the help
Talhah Mafawalla
 
Michael Dunn
Ranch Hand
Posts: 4632
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
another guess

 
Brian Cole
Author
Ranch Hand
Posts: 949
1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
It seems to me if you just declare it extends AbstractTableModel instead of DefaultTableModel it should work fine. Is there some DefaultTableModel functionality that you need or something?
 
Talhah Mafawalla
Greenhorn
Posts: 24
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
To Michael Dunn,

Thank you that was part of the solution this is what i actually did:

public int getRowCount() {
if(vData == null){
return 0;
}else{
return vData.size()/3;
}
}

This seems to work fine,though i had to divide by three because i intially wanted one row of data but it was repeating the one row two extra times. I think i am grasping the logic behind whats happening, thanks alot Michael.

To Brian Cole,

The reason for using DefaultTableModel is that when i initialy extended on the AbstractTableModel then changed it to DefaultTableModel the implemented methods were the same but i thought that DefaultTableModel would handle vectors better. Now that i have sat on this problem for almost a week i think both seems to work very similar only that DefaultTableModel does not execute the inheritant classes constructor first. I am still learning java and i am still trying to get my head around things. Though i think i will change back to AbstractTableModel

Thanks for all the help you guys.
Talhah Mafawalla
 
Brian Cole
Author
Ranch Hand
Posts: 949
1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Originally posted by Talhah Mafawalla:
The reason for using DefaultTableModel is that when i initialy extended on the AbstractTableModel then changed it to DefaultTableModel the implemented methods were the same but i thought that DefaultTableModel would handle vectors better.


Well I'm not sure I follow that logic.

You have overridden getValueAt(), setValueAt(), getColumnName(), getRowCount(), and getColumnCount(). So these methods now bypass the Vectors inherited from DefaultTableModel.

You do inherit methods such as addColumn(), addRow(), and moveRow() from DefaultTableModel but they won't work correctly because they manipulate the Vectors defined in DefaultTableModel, not the ones defined in your subclass.

Since you're storing all the data in your own Vectors (which btw you might want to change to ArrayLists for performance reasons) I think it makes more sense to subclass AbstactTableModel directly. But of course it's your call.
 
Talhah Mafawalla
Greenhorn
Posts: 24
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Thanks Brian for all the help. I am still learning java and hopefully will get a better understanding of how the language works. Thanks alot for all your input. Also i think i have solved the problems that i had and used the AbstractTableModel afterall.

Thanks again for the help.
Talhah Mafawalla
 
With a little knowledge, a cast iron skillet is non-stick and lasts a lifetime.
  • Post Reply Bookmark Topic Watch Topic
  • New Topic
Boost this thread!