I want to display all 5 columns of my SQL database table bk_det in my jtable which is in netbeans ide in java language but I am only able to display 4 columns instead of 5. What is the problem can any one help m posting the code below:
private void btviewbkdetActionPerformed(java.awt.event.ActionEvent evt) {
if(evt.getSource()==btviewbkdet){
try {
DBUtil util = new DBUtil();
Connection con = util.getConnection();
Statement stmt = con.createStatement();
ResultSet rs = stmt.executeQuery("select * from bk_det");
ResultSetMetaData rsmetadata = rs.getMetaData();
int columns = rsmetadata.getColumnCount();
DefaultTableModel dtm = new DefaultTableModel();
Vector columns_name = new Vector();
Vector data_rows = new Vector();
for(int i=1; i< columns; i++){
columns_name.addElement(rsmetadata.getColumnName(i));
}
dtm.setColumnIdentifiers(columns_name);
while(rs.next()){
data_rows = new Vector();
for(int j=1; j< columns; j++){
data_rows.addElement(rs.getString(j));
}
dtm.addRow(data_rows);
}
tblbnkdet.setModel(dtm);
} catch (Exception ex) {
JOptionPane.showMessageDialog(null, ex.getMessage());
Logger.getLogger(Demo.class.getName()).log(Level.SEVERE, null, ex);
} // TODO add your handling code here:
}
}
private void btbkrepviewActionPerformed(java.awt.event.ActionEvent evt) {
if(evt.getSource()==btviewbkdet){
try {
DBUtil util = new DBUtil();
Connection con = util.getConnection();
Statement stmt = con.createStatement();
ResultSet rs = stmt.executeQuery("select * from dbo.bk_rep");
ResultSetMetaData rsmetadata = rs.getMetaData();
int columns = rsmetadata.getColumnCount();
DefaultTableModel dtm = new DefaultTableModel();
Vector columns_name = new Vector();
Vector data_rows = new Vector();
for(int i=1; i< columns; i++){
columns_name.addElement(rsmetadata.getColumnName(i));
}
dtm.setColumnIdentifiers(columns_name);
while(rs.next()){
data_rows = new Vector();
for(int j=1; j< columns; j++){
data_rows.addElement(rs.getString(j));
}
dtm.addRow(data_rows);
}
tblbkrep.setModel(dtm);
} catch (Exception ex) {
JOptionPane.showMessageDialog(null, ex.getMessage());
Logger.getLogger(Demo.class.getName()).log(Level.SEVERE, null, ex);
} // TODO add your handling code here:
} // TODO add your handling code here:
}
Here is the change
for(int i=1; i<= columns; i++){
columns_name.addElement(rsmetadata.getColumnName(i));
}
Related
This is a followup question to Display database table with swing
I wrapped my table to a JScrollPane but the columns' headers are still not showing up!
Can anyone tell me what is wrong?
try {
con = (Connection) DriverManager.getConnection(DATABASE_URL , USERNAME, PASSWORD);
stmt = (Statement) con.createStatement();
ResultSet rs = stmt.executeQuery(QUERY_FIND_ITEMS);
{
ResultSetMetaData md = (ResultSetMetaData) rs.getMetaData();
int columns = md.getColumnCount();
// Get column names
for (int i = 1; i <= columns; i++)
{
columnNames.add( md.getColumnName(i) );
}
// Get row data
while (rs.next())
{
ArrayList row = new ArrayList(columns);
for (int i = 1; i <= columns; i++)
{
row.add( rs.getObject(i) );
}
data.add( row );
}
}
}
catch (SQLException e)
{
System.out.println( e.getMessage() );
}
Vector<String> columnNamesVector = new Vector();
Vector dataVector = new Vector();
for (int i = 0; i < data.size(); i++)
{
ArrayList subArray = (ArrayList)data.get(i);
Vector subVector = new Vector();
for (int j = 0; j < subArray.size(); j++)
{
subVector.add(subArray.get(j));
}
dataVector.add(subVector);
}
for (int i = 0; i < columnNames.size(); i++ ) {
columnNamesVector.add(columnNames.get(i));
}
// Create table with database data
JTable table = new JTable(dataVector, columnNamesVector)
{
public Class getColumnClass(int column)
{
for (int row = 0; row < getRowCount(); row++)
{
Object o = getValueAt(row, column);
if (o != null)
{
return o.getClass();
}
}
return Object.class;
}
};
JScrollPane scrollPane =new JScrollPane(table);
getContentPane().add( scrollPane, BorderLayout.WEST );
JPanel buttonPanel = new JPanel();
getContentPane().add( buttonPanel, BorderLayout.SOUTH );
table.setForeground(Color.BLUE);
catch (SQLException e)
{
System.out.println( e.getMessage() );
}
The code after the end of the catch block will not work correctly if the DB query fails. Best to include that code within the try block.
And a tip: change
System.out.println( e.getMessage() );
to
e.printStackTrace();
Both shorter & more informative.
i already searched the whole web but I can't find a solution, so i decided to ask here.
Following problem: I am using those 2 methods to populate a JTable with a DefaultTableModel, the ResultSet shows the right amount of data entries (i already searched it with System.out.println) but the JTable always misses the first row
I am using a method to get a ResultSet like this:
public static JTable DBCFillBTableAuftraege() {
Connection con = null;
Statement stmt = null;
ResultSet rs = null;
JTable table = null;
try {
con = DriverManager.getConnection(host, uName, uPass);
stmt = con.createStatement( );
rs = stmt.executeQuery("SELECT a.auftrags_nr, k.firma, a.auftragsdatum, a.lieferdatum, a.rechnungsbetrag, k.name, k.strasse, k.plz, k.ort from auftrag a join kunde k on k.kunden_nr = a.kunden_nr ");
while (rs.next()) {
table = new JTable(tableModel(rs));
return table;
}
} catch (SQLException e) {
System.out.println(e);
} finally {
try {
if (rs != null) {
rs.close();
}
if (stmt != null) {
stmt.close();
}
con.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
return table;
}
Which then calls this method:
public static DefaultTableModel TableModel(ResultSet rs)
throws SQLException {
ResultSetMetaData metaData = rs.getMetaData();
System.out.println(rs);
// names of columns
Vector<String> columnNames = new Vector<String>();
int columnCount = metaData.getColumnCount();
for (int column = 1; column <= columnCount; column++) {
columnNames.add(metaData.getColumnName(column));
}
// data of the table
Vector<Vector<Object>> data = new Vector<Vector<Object>>();
while (rs.next()) {
Vector<Object> vector = new Vector<Object>();
for (int columnIndex = 1; columnIndex <= columnCount; columnIndex++) {
vector.add(rs.getObject(columnIndex));
}
data.add(vector);
}
return new DefaultTableModel(data, columnNames);
}
In my main:
TableAuftrag = DBCFillBTableAuftraege();
scpaneBestell.setViewportView(TableAuftrag);
It works fine, it is showing me my column headers and the data, except one problem:
It is always missing the first row and starts with the second one
Your problem starts here...
// Move to first row...
while (rs.next()) {
table = new JTable(tableModel(rs));
return table;
}
and manifests
// Move to second row and beyond...
while (rs.next()) {
Vector<Object> vector = new Vector<Object>();
for (int columnIndex = 1; columnIndex <= columnCount; columnIndex++) {
vector.add(rs.getObject(columnIndex));
}
data.add(vector);
}
Basically, in the first while (rs.next()), you move to the first row, but in the second while (rs.next()) you move to the second row, without handling the first...
It might be better to simply pass the ResultSet directly to the TableModel.
Convention would also suggest that you probably should not need to create a new JTable, but instead, just create a new TableModel and apply to a pre-existing table
while (rs.next()) {
table = new JTable(tableModel(rs));
return table;
}
You're consuming the first row of the result set here, and then call tableModel(), which consumes the other rows. The while loop is useless. Just do
table = new JTable(tableModel(rs));
return table;
I have a problem in updating my single jtable from Microsoft Access Database.
I do not have any error messages. I tried out the Query for the database using like, but my jtable does not populate in relation to the data stored in the database.
public TableModel setAuthorSearchEjournalTableValues(){
String eJournalAuthor = jTextField30.getText();
ResultSet tableData = DCE.searchEjournalbyAuthor(eJournalAuthor);
try {
ResultSetMetaData md = tableData.getMetaData();
int columnCount = md.getColumnCount();
Vector columns = new Vector(columnCount);
for (int i = 1; i <= columnCount; i++) {
columns.add(md.getColumnName(i));
}
Vector data = new Vector();
Vector row;
while (tableData.next()) {
row = new Vector(columnCount);
for (int i = 1; i <= columnCount; i++) {
row.addElement( tableData.getString(i) );
}
data.add(row);
}
DefaultTableModel tableModel = new DefaultTableModel(data, columns);
return tableModel;
//Debugging
} catch (SQLException ex) {
ex.printStackTrace();
}
return null;
}`
And my result retrieving query is here
public ResultSet searchEjournalbyAuthor(String author){
conn = Connect();
try{
String myQuery = "select AuthorDetails,Year,Titleofarticle,Journaltitle,volume,pagenumbers,URL,AccessedDate from Ejournalcitation where AuthorDetails = '"+author+"'";
pst = conn.prepareStatement(myQuery);
rs = pst.executeQuery();
return rs;
}catch(SQLException ex){
ex.printStackTrace();
}
return null;
}
with the code to display as
private void jTextField30KeyReleased(java.awt.event.KeyEvent evt) {
// TODO add your handling code here:
if(jComboBox1.getSelectedIndex()==0&&jComboBox2.getSelectedIndex()==0){//BookTitle
jTable1.setModel(setTitleSearchBookTableValues());
}
else if(jComboBox1.getSelectedIndex()==0&&jComboBox2.getSelectedIndex()==1){//BookAuthor
jTable1.setModel(setAuthorSearchBookTableValues());
}
else if(jComboBox1.getSelectedIndex()==1&&jComboBox2.getSelectedIndex()==0){//WebSiteTitle
jTable1.setModel(setTitleSearchWebSiteTableValues());
}
else if(jComboBox1.getSelectedIndex()==1&&jComboBox2.getSelectedIndex()==1){//WebSiteAuthor
jTable1.setModel(setAuthorSearchWebSiteTableValues());
}
else if(jComboBox1.getSelectedIndex()==2&&jComboBox2.getSelectedIndex()==0){//Ejournaltitle
jTable1.setModel(setTitleSearchEjournalTableValues());
}
else if(jComboBox1.getSelectedIndex()==3&&jComboBox2.getSelectedIndex()==1){//EjournalAuthor
jTable1.setModel(setAuthorSearchEjournalTableValues());
}
else{
JOptionPane.showMessageDialog(null, "Please enter a value and select the type of search");
}
}
Help me out!! Thanks in advance
you must include
DefaultTableModel tableModel = (DefaultTableModel) jTable1.getModel();
tableModel.fireTableDataChanged();
with the corrected query
String myQuery = "select AuthorDetails,Year,Titleofarticle,Journaltitle,volume,pagenumbers,URL,AccessedDate from Ejournalcitation where AuthorDetails like '%"+author+"%'";
I would like to create DefaultTableModel from ResultSet. To do that, I need Object[][].
For that, I have to specify the size of the object before I iterate through the table: I go to the rs.last(), then rs.getRow(), then rs.beforeFirst();
After that, the rs.next() does not executes in the while cycle.
What am I doing wrong?
public static DefaultTableModel buildTableModel(ResultSet _resultSet) {
ResultSetMetaData metaData;
Object[] columnNames = null;
Object[][] tableData = null;
int columnCount;
int currentRowNumber = 0;
try {
metaData = _resultSet.getMetaData();
columnCount = metaData.getColumnCount();
columnNames = new Object[columnCount];
_resultSet.last();
tableData = new Object[_resultSet.getRow()][columnCount];
_resultSet.beforeFirst();
for (int currentColumn = 0; currentColumn <= columnCount; currentColumn++) {
columnNames[currentColumn] = metaData.getColumnName(currentColumn + 1);
}
while (_resultSet.next()) {
for (int columnIndex = 0; columnIndex <= columnCount; columnIndex++) {
tableData[currentRowNumber][columnIndex] = _resultSet.getObject(columnIndex + 1);
}
currentRowNumber++;
}
} catch (SQLException ex) {
System.out.println("bad");
}
return new DefaultTableModel(tableData, columnNames);
}
Probably your ResultSet is not scroll insensitive, that is, it can only be traversed forward.
See the documentation here:
[...] A default ResultSet object is not updatable and has a cursor that moves forward only. Thus, you can iterate through it only once and only from the first row to the last row. [...]
To create a bi-directional one, do something like:
Connection conn = DriverManager.getConnection(...);
Statement stmt = conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ...);
ResultSet rset = stmt.executeQuery(sql);
At first you need to print column name from ResultSetMetaData. Than you apply _resultSet.last(); and _resultSet.beforeFirst();. This way it has been working my machine.
public static DefaultTableModel buildTableModel(ResultSet _resultSet) {
ResultSetMetaData metaData;
Object[] columnNames = null;
Object[][] tableData = null;
int columnCount;
int currentRowNumber = 0;
try {
metaData = _resultSet.getMetaData();
columnCount = metaData.getColumnCount();
columnNames = new Object[columnCount];
// Print column here.
for (int currentColumn = 0; currentColumn <= columnCount; currentColumn++) {
columnNames[currentColumn] = metaData.getColumnName(currentColumn + 1);
}
tableData = new Object[_resultSet.getRow()][columnCount];
//Here point resultSet cursor to last and beforeFirst.
_resultSet.last();
_resultSet.beforeFirst();
// After swaping the above part. Now it will enter on while loop.
while (_resultSet.next()) {
for (int columnIndex = 0; columnIndex <= columnCount; columnIndex++) {
tableData[currentRowNumber][columnIndex] = _resultSet.getObject(columnIndex + 1);
}
currentRowNumber++;
}
} catch (SQLException ex) {
System.out.println("bad");
}
return new DefaultTableModel(tableData, columnNames);
}
I'm having a strange problem with the below code, it works fine when its run without the if else statements, but displays no results in the jtable when if else is used. Is there something stupid I'm missing here?
try {
Class.forName(dbClass);
Connection con = DriverManager.getConnection (dbUrl,dbUsername, dbPassword);
Statement stmt = con.createStatement();
String userQuery = "SELECT p_id AS 'Patient ID', forename AS 'Forename', surname AS 'Surname', address AS 'Address' FROM Patient WHERE surname LIKE '%"+s+"%'";
ResultSet userResult = stmt.executeQuery(userQuery);
if(!userResult.next())
{
JOptionPane.showMessageDialog(null, "No Results.");
{
else{
ResultSetMetaData rsMetaData =userResult.getMetaData();
DefaultTableModel dtm = new DefaultTableModel();
int cols = rsMetaData.getColumnCount();
Vector colName = new Vector();
Vector dataRows = new Vector();
for (int i=1; i<cols; i++){
colName.addElement(rsMetaData.getColumnName(i));
}
dtm.setColumnIdentifiers(colName);
while(userResult.next()){
dataRows = new Vector();
for(int j = 1; j<cols; j++){
dataRows.addElement(userResult.getString(j));
}
dtm.addRow(dataRows);
}
searchTable.setModel(dtm);
con.close();
}
} //end try
catch(ClassNotFoundException e) {
JOptionPane.showMessageDialog(null, "Database Error.");
e.printStackTrace();
}
catch(SQLException e) {
JOptionPane.showMessageDialog(null, "Database Error.");
e.printStackTrace();
}
I'm using netbeans for the GUI.
Thanks
The connection object (con) should be closed outside if/else block.
Beside, the userResult.next() was called twice in the else statement block..
You may fix it by replacing while() by do while loop:
do {
dataRows = new Vector();
for (int j = 1; j < cols; j++) {
dataRows.addElement(userResult.getString(j));
}
dtm.addRow(dataRows);
}
while (userResult.next());
Please include finally to handle closing the connection and removing the other resources.