我正在开发一个登录房间应用程序,登录用户可以选择访问者(最多3位)与他们一起进入房间。处理访问者的类返回一个ArrayList
,我希望从中将数据输入到JTable
的单元格中,该单元格显示签入房间的用户。我的问题是我不确定如何在JTable
的特定单元格中将列表中的每个记录显示为单独的一行。
这是主类(称为SignBoardTest):
import java.awt.*;
import java.awt.event.*;
import java.util.Random;
import javax.swing.*;
import javax.swing.border.*;
import javax.swing.table.*;
public class SignBoardTest {
public static void main(String[] args) {
new SignBoardTest();
}
private JFrame inOutFrame;
private JPanel topPanel;
private JPanel headerPanel;
private JPanel mainPanel;
private JPanel btnPanel;
private JLabel roomLabel;
private JButton addUserBtn;
private JTable testTbl;
private String[] answer = {"Eligible", "Not Eligible"};
private String[] first = {"Jack", "Kelly", "Mike", "Lisa"};
private String[] last = {"Donovan", "Marshall", "Jones", "Kinder"};
private Visitor visitor;
public SignBoardTest()
{
//place GUI components on JFrame's content pane
inOutFrame = new JFrame("ISF Out of Office Board");
topPanel = new JPanel();
topPanel.setLayout(new BorderLayout());
headerPanel = new JPanel();
btnPanel = new JPanel();
mainPanel = new JPanel(new BorderLayout());
roomLabel = new JLabel("CLOSED AREA ROOM");
roomLabel.setFont(new Font("Segoe UI", Font.BOLD, 30));
addUserBtn = new JButton("Add user");
String [] colNames = {"First Name", "Last Name",
"Can be area monitor?", "Visitor(s)",
"Status", ""};
DefaultTableModel model = new DefaultTableModel(colNames, 0);
testTbl = new JTable(model);
testTbl.setFillsViewportHeight(true);
MultilineTableCellRenderer renderer = new MultilineTableCellRenderer();
testTbl.setDefaultRenderer(String.class, renderer);
testTbl.setRowHeight(testTbl.getRowHeight() * 3);
JScrollPane pane = new JScrollPane(testTbl);
mainPanel.add(pane, BorderLayout.CENTER);
//action for add user feature
addUserBtn.addActionListener(new ActionListener()
{
@Override
public void actionPerformed(ActionEvent e)
{
String fName = first[new Random().nextInt(first.length)];
String lName = last[new Random().nextInt(last.length)];
String areaMonitor = answer[new Random().nextInt(answer.length)];
model.addRow(new Object[] {fName, lName, areaMonitor, visitor,
"Logout", "Add/Remove Visitors"});
BtnColumn visitorBtnColumn = new BtnColumn(testTbl, visitorMgmt, 5);
visitorBtnColumn.setMnemonic(KeyEvent.VK_E);
BtnColumn logoutBtnColumn = new BtnColumn(testTbl, logout, 4);
logoutBtnColumn.setMnemonic(KeyEvent.VK_D);
}
});
btnPanel.add(addUserBtn);
headerPanel.add(roomLabel);
topPanel.add(headerPanel, BorderLayout.PAGE_START);
topPanel.add(btnPanel, BorderLayout.PAGE_END);
topPanel.setBorder(new EtchedBorder(EtchedBorder.RAISED));
mainPanel.setBorder(new EtchedBorder(EtchedBorder.RAISED));
inOutFrame.add(topPanel, BorderLayout.PAGE_START);
inOutFrame.add(mainPanel, BorderLayout.CENTER);
inOutFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
inOutFrame.pack();
inOutFrame.setSize(1200, 1000); //default size in case screen is not full
inOutFrame.setLocationRelativeTo(null);
inOutFrame.setVisible(true);
inOutFrame.setResizable(false);
}
//handling of adding/removing users
//with ButtonColumn class
@SuppressWarnings("serial")
Action visitorMgmt = new AbstractAction()
{
public void actionPerformed(ActionEvent e)
{
int row = testTbl.getSelectedRow();
visitor = new Visitor();
//make window modal
visitor.setModalityType(Dialog.ModalityType.APPLICATION_MODAL);
visitor.setLocationRelativeTo(null);
visitor.setVisible(true);
if(visitor.getChoice() == JOptionPane.YES_OPTION)
{
for(String name : visitor.getVisitorList())
{
System.out.println("Adding user: " + name);
String value = testTbl.getValueAt(row, 3) + name + " \n";
testTbl.setValueAt(value, row, 3);
}
}
}
};
//handle of logging out users using ButtonColumn class
@SuppressWarnings("serial")
Action logout = new AbstractAction()
{
public void actionPerformed(ActionEvent e)
{
int row = testTbl.getSelectedRow();
String first = testTbl.getModel().getValueAt(row, 0).toString();
String last = testTbl.getModel().getValueAt(row, 1).toString();
String name = first.concat(" ").concat(last);
if(doesUserHaveVisitors(row))
JOptionPane.showMessageDialog(null,
"Visitors must be logged out or transferred to \nanother employee before signing out",
"ERROR: ILLEGAL ACTION", JOptionPane.ERROR_MESSAGE);
else
{
int response = JOptionPane.showConfirmDialog(null,
"Are you sure you want to log out " + name + "?",
"Logout confirmation",
JOptionPane.OK_CANCEL_OPTION,
JOptionPane.QUESTION_MESSAGE);
if(response == JOptionPane.YES_OPTION)
{
JTable table = (JTable)e.getSource();
int modelRow = Integer.valueOf(e.getActionCommand());
((DefaultTableModel)table.getModel()).removeRow(modelRow);
}
}
}
};
private boolean doesUserHaveVisitors(int selectedRow)
{
Object value = testTbl.getValueAt(selectedRow, testTbl.getColumn("Visitor(s)").getModelIndex());
if(value != null)
return true;
else
return false;
}
} //end class SignInBoard
/**
* The MultiLineTableCellRenderer class is a customized to allow for multi-line
* entry into a column of a JTable. This will allow for users to enter multiple
* visitors (max 3) against their login record.
*
*/
@SuppressWarnings("serial")
class MultilineTableCellRenderer extends JList<String> implements TableCellRenderer
{
@Override
public Component getTableCellRendererComponent(JTable table, Object value,
boolean isSelected, boolean hasFocus, int row, int column)
{
//make multi-line where the cell value is String[]
if (value instanceof String[]) {
setListData((String[]) value);
}
return this;
}
}
用于用户管理访问者的Visitor类:
import java.awt.Container;
import java.util.ArrayList;
import java.awt.event.*;
import javax.swing.*;
@SuppressWarnings("serial")
public class Visitor extends JDialog implements ActionListener {
private JButton newVisitorButton;
private JButton doneButton;
private JPanel contentPanel; //"body" of JDialog
private JOptionPane visitorInputPane;
private ArrayList<String> visitorList; //list to store visitors
private int visitorCtr = 0; //counter for
public Visitor() {
setTitle("Visitor Management");
newVisitorButton = new JButton("New Visitor Entry");
doneButton = new JButton("Done");
contentPanel = new JPanel();
contentPanel.setLayout(new BoxLayout(contentPanel, BoxLayout.Y_AXIS));
newVisitorButton.setAlignmentX(CENTER_ALIGNMENT);
contentPanel.add(newVisitorButton);
//since users can only have 3 visitors max,
//list will be initialized to this size
visitorList = new ArrayList<String>(3);
JButton[] buttonChoices = {doneButton};
visitorInputPane = new JOptionPane(contentPanel,
JOptionPane.PLAIN_MESSAGE,
JOptionPane.YES_NO_OPTION,
null,
buttonChoices,
buttonChoices[0]);
setContentPane(visitorInputPane);
//handle the window closing - force
//the user to use one of the buttons
//to avoid closing w/out any action
setDefaultCloseOperation(DO_NOTHING_ON_CLOSE);
addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent we)
{
JOptionPane.showMessageDialog(visitorInputPane,
"Please close this using the Cancel button");
}
});
pack();
//listeners for button pushes
doneButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
dispose();
}
});
newVisitorButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e)
{
if(visitorCtr > 2)
JOptionPane.showMessageDialog(visitorInputPane, "Cannot add more visitors (max 3)!",
"MAX LIMIT REACHED", JOptionPane.ERROR_MESSAGE);
else
{
contentPanel.add(new VisitorEntryPanel());
pack();
visitorCtr++;
}
}
});
}
@Override
public void actionPerformed(ActionEvent e) {
}
//return visitor list
public ArrayList<String> getVisitorList() {
return visitorList;
}
//return choice from JDialog
public int getChoice() {
return visitorInputPane.getOptionType();
}
//custom JPanel inner class for adding
//new user to list
private class VisitorEntryPanel extends JPanel
{
private JLabel nameLabel;
private JTextField nameField;
private JButton removeVisitorButton;
private JButton addVisitorButton;
VisitorEntryPanel()
{
nameLabel = new JLabel("Name: ");
nameField = new JTextField(20);
removeVisitorButton = new JButton("Remove");
addVisitorButton = new JButton("Add");
add(nameLabel);
add(nameField);
add(addVisitorButton);
add(removeVisitorButton);
removeVisitorButton.addActionListener(new ActionListener()
{
@Override
public void actionPerformed(ActionEvent event)
{
visitorList.remove(getVisitorName());
Container myParent = removeVisitorButton.getParent();
Container parent = myParent.getParent();
parent.remove(myParent);
parent.repaint();
parent.revalidate();
visitorCtr--;
System.out.println("New visitor count: " + visitorCtr);
}
});
addVisitorButton.addActionListener(new ActionListener()
{
@Override
public void actionPerformed(ActionEvent ev)
{
if(getVisitorName().length() != 0)
{
visitorList.add(getVisitorName());
//disable button after good entry
addVisitorButton.setEnabled(false);
}
else //can't submit null/empty name
JOptionPane.showMessageDialog(visitorInputPane, "Visitor name cannot be empty!",
"EMPTY NAME ENTERED", JOptionPane.ERROR_MESSAGE); }
});
}
public String getVisitorName() {
return(nameField.getText().trim());
}
} //end class visitorPanel
} //end class Visitor
按钮列类来自以下link(我认为没有必要在此处重新发布)。我在此post中使用了Channa提供的答案来创建自定义TableCellRenderer
,以从我的ArrayList
获取数据,但是我无法正确执行它。任何帮助,将不胜感激。谢谢。