I'm developping a game lobby with swing. I have a JTable with all the different players logged in the room, and I want to add a JComboBox in only one cell. My problem is that the comboBox doesn't render correctly.
I know there are plenty of other Threads about this subject but I couldn't find someone with the same problem.
JComboBox box = new JComboBox();
box.addItem("Warrior");
/* Adds few other items (strings)*/
this.box.addActionListener (new ActionListener () {
public void actionPerformed(ActionEvent e) {
/* sends message to server to change character when the combobox's chosen element is changed*/
}
});
TableUserModel model = new TableUserModel(localUser,this.box); //Specifying the local user as I don't want a JComboBox in the others user's rows.
JTable table = new JTable(this.model);
table.getColumnModel().getColumn(1).setCellEditor(new DefaultCellEditor(this.box));
Table Model class
public class TableUserModel extends AbstractTableModel{
private String[] columnNames = {"Username","Class","TeamColor","Action"};
private Object[][] data = {{null,null,null,null}};
private User localUser;
private JComboBox box;
public TableUserModel(User u,JComboBox box) {
this.localUser = u;
this.box = box;
}
@Override
public int getColumnCount() {
return this.columnNames.length;
}
@Override
public int getRowCount() {
return this.data.length;
}
@Override
public Object getValueAt(int row, int col) {
return this.data[row][col];
}
public String getColumnName(int col) {
return columnNames[col];
}
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;
}
//The following method updates my data array when the informations are refreshed from the server
public void refreshUsers(ArrayList<User> users) {
int elementNumber = 0;
//clears the data[][] array
this.data = new Object[][];
for (User usr : users) {
this.data[elementNumber][0] = usr.getUsername();
/*if it's the GriffinBabe's (local user) row */
this.data[elementNumber][1] = this.box; //HERE!!! I add the JComboBox into the specific cell
/*else adds a simple string information (for users other than localplayer) */
this.data[elementNumber][2] = usr.getTeamColor();
this.data[elementNumber][3] = null;
elementNumber++;
}
}
User Class
Is just a class containing some informations, the problem is certainly not here
and I want to add a JComboBox in only one cell.
This has nothing to do with the TableModel. It is the view (ie. the table) that displays the editor so you need to customize the table.
One way to do this is to override the getCellEditor(...)
method of the JTable
. For example:
import java.awt.*;
import java.awt.event.*;
import java.util.List;
import java.util.ArrayList;
import javax.swing.*;
import javax.swing.event.*;
import javax.swing.border.*;
import javax.swing.table.*;
public class TableComboBoxByRow extends JPanel
{
List<String[]> editorData = new ArrayList<String[]>(3);
public TableComboBoxByRow()
{
setLayout( new BorderLayout() );
// Create the editorData to be used for each row
editorData.add( new String[]{ "Red", "Blue", "Green" } );
editorData.add( new String[]{ "Circle", "Square", "Triangle" } );
editorData.add( new String[]{ "Apple", "Orange", "Banana" } );
// Create the table with default data
Object[][] data =
{
{"Color", "Red"},
{"Shape", "Square"},
{"Fruit", "Banana"},
{"Plain", "Text"}
};
String[] columnNames = {"Type","Value"};
DefaultTableModel model = new DefaultTableModel(data, columnNames);
JTable table = new JTable(model)
{
// Determine editor to be used by row
public TableCellEditor getCellEditor(int row, int column)
{
int modelColumn = convertColumnIndexToModel( column );
if (modelColumn == 1 && row < 3)
{
JComboBox<String> comboBox1 = new JComboBox<String>( editorData.get(row));
return new DefaultCellEditor( comboBox1 );
}
else
return super.getCellEditor(row, column);
}
};
JScrollPane scrollPane = new JScrollPane( table );
add( scrollPane );
}
private static void createAndShowUI()
{
JFrame frame = new JFrame("Table Combo Box by Row");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add( new TableComboBoxByRow() );
frame.setSize(200, 200);
frame.setLocationByPlatform( true );
frame.setVisible( true );
}
public static void main(String[] args)
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowUI();
}
});
}
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.