如果我在上面的JTable中选择一行,那么与该数据对应的一行将出现在下面的JTable中。以下Jtable中的所有单元格都是可编辑的。我需要的是:
如果我按下按钮,下面Jtable中的更改将被保存。如果我不按下按钮,JTable单元格将保持应用程序的原始状态。
PS:这是一个演示,真实案例包含更多参数,但目的是一样的。
package guarreo;
import java.awt.BorderLayout;
import java.awt.EventQueue;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.EmptyBorder;
import javax.swing.JTable;
import javax.swing.table.DefaultTableModel;
import javax.swing.JButton;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
public class demo extends JFrame {
private JPanel contentPane;
private JTable tablePATIENTS;
private JTable tableREPORTS;
/**
* Launch the application.
*/
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
demo frame = new demo();
frame.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
/**
* Create the frame.
*/
public demo() {
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setBounds(100, 100, 571, 336);
contentPane = new JPanel();
contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
setContentPane(contentPane);
contentPane.setLayout(null);
tablePATIENTS = new JTable();
tablePATIENTS.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent arg0) {
if(tablePATIENTS.getSelectedRow()!=-1){//If there is a patient selected with a report, enable the save changes button
DefaultTableModel dtm2 = (DefaultTableModel) tableREPORTS.getModel();
dtm2.addRow(new Object[]{"200$", "Pills", "Headache"});
tableREPORTS.setModel(dtm2);
}
}
});
tablePATIENTS.setModel(new DefaultTableModel(
new Object[][] {
},
new String[] {
"Name", "Surrname", "Doctor"
}
));
DefaultTableModel dtm = (DefaultTableModel) tablePATIENTS.getModel();
dtm.addRow(new Object[]{"Jon", "Snow", "Jack"});
JButton btnSaveChanges = new JButton("Save changes tableREPORTS");
btnSaveChanges.setEnabled(false);
btnSaveChanges.setBounds(155, 260, 212, 23);
contentPane.add(btnSaveChanges);
tablePATIENTS.setModel(dtm);
tablePATIENTS.setBounds(20, 11, 486, 107);
contentPane.add(tablePATIENTS);
tableREPORTS = new JTable();
tableREPORTS.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
btnSaveChanges.setEnabled(true); //Enabled only if something selected in this table
}
});
tableREPORTS.setModel(new DefaultTableModel(
new Object[][] {
},
new String[] {
"Cost", "Treatment", "Disease"
}
));
tableREPORTS.setBounds(20, 144, 486, 105);
contentPane.add(tableREPORTS);
}
}
一般的解决方案是制作患者数据的深度副本,并使用该数据副本创建辅助JTable数据。然后,用户可以对JTable数据进行任何他们想做的更改,而不用担心副作用。按下按钮后,ActionListener会将JTable模型的数据转换回患者的数据,替换原始数据。所以关键是在按钮被按下之前不要做这个替换。
如果Patient类拥有一个信息类对象的ArrayList,那么此列表的获取者应该通过创建一个新的ArrayList来创建一个深度副本,并在for循环中,用原始列表中的对象的深度副本填充它。
例如:
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.util.ArrayList;
import java.util.List;
import java.util.Vector;
import javax.swing.*;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumnModel;
@SuppressWarnings("serial")
public class MyDemo extends JPanel {
private static final int GAP = 3;
private MyPatientTableModel patientModel = new MyPatientTableModel();
private JTable patientTable = new JTable(patientModel);
private JTable ptVisitTable = new JTable(new MyPtVisitTableModel(new ArrayList<MyPtVisit>()));
public MyDemo() {
MyPatient pt0 = new MyPatient("001", "Johnson", "Michael");
pt0.addVisit(new MyPtVisit(200, "Head Ache", "Narcotics"));
pt0.addVisit(new MyPtVisit(300, "Body Ache", "Aspirin"));
pt0.addVisit(new MyPtVisit(400, "Total Ache", "Nothing"));
MyPatient pt1 = new MyPatient("002", "Smith", "John");
pt1.addVisit(new MyPtVisit(220, "Head Ache", "Narcotics"));
pt1.addVisit(new MyPtVisit(320, "Body Ache", "Aspirin"));
pt1.addVisit(new MyPtVisit(420, "Total Ache", "Nothing"));
MyPatient pt2 = new MyPatient("003", "Baker", "Betty");
pt2.addVisit(new MyPtVisit(240, "Head Ache", "Narcotics"));
pt2.addVisit(new MyPtVisit(340, "Body Ache", "Aspirin"));
pt2.addVisit(new MyPtVisit(440, "Total Ache", "Nothing"));
MyPatient pt3 = new MyPatient("004", "Duck", "Donald");
pt3.addVisit(new MyPtVisit(260, "Head Ache", "Narcotics"));
pt3.addVisit(new MyPtVisit(360, "Body Ache", "Aspirin"));
pt3.addVisit(new MyPtVisit(460, "Total Ache", "Nothing"));
MyPatient[] pts = { pt0, pt1, pt2, pt3 };
for (MyPatient myPatient : pts) {
patientModel.addRow(myPatient);
}
patientTable.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
patientTable.getSelectionModel().addListSelectionListener(new PatientTableListener());
TableColumnModel tcm = patientTable.getColumnModel();
tcm.removeColumn(tcm.getColumn(3)); // visits column should be invisible
patientTable.setFillsViewportHeight(true);
ptVisitTable.setFillsViewportHeight(true);
Dimension size = patientTable.getPreferredScrollableViewportSize();
size = new Dimension(size.width, size.height / 2);
patientTable.setPreferredScrollableViewportSize(size);
size = ptVisitTable.getPreferredScrollableViewportSize();
size = new Dimension(size.width, size.height / 2);
ptVisitTable.setPreferredScrollableViewportSize(size);
JScrollPane ptTableScrollPane = new JScrollPane(patientTable);
JScrollPane ptVisitScrollPane = new JScrollPane(ptVisitTable);
JPanel btnPanel = new JPanel();
btnPanel.add(new JButton(new SaveChangesAction("Save Changes")));
setBorder(BorderFactory.createEmptyBorder(GAP, GAP, GAP, GAP));
setLayout(new BoxLayout(this, BoxLayout.PAGE_AXIS));
add(ptTableScrollPane);
add(Box.createVerticalStrut(GAP));
add(ptVisitScrollPane);
add(Box.createVerticalStrut(GAP));
add(btnPanel);
}
private class SaveChangesAction extends AbstractAction {
public SaveChangesAction(String name) {
super(name);
int mnemonic = (int) name.charAt(0);
putValue(MNEMONIC_KEY, mnemonic);
}
@Override
public void actionPerformed(ActionEvent e) {
int index = patientTable.getSelectedRow();
if (index < 0) {
return;
}
// to capture edits not yet complete
if (ptVisitTable.isEditing()) {
CellEditor cellEditor = ptVisitTable.getCellEditor();
if (cellEditor != null) {
cellEditor.stopCellEditing();
}
}
index = patientTable.convertRowIndexToModel(index);
MyPatient selectedPatient = patientModel.getPatient(index);
MyPtVisitTableModel visitsModel = (MyPtVisitTableModel) ptVisitTable.getModel();
List<MyPtVisit> visits = visitsModel.getVisits();
selectedPatient.setVisits(visits);
patientModel.setPatientAt(index, selectedPatient);
}
}
private class PatientTableListener implements ListSelectionListener {
@Override
public void valueChanged(ListSelectionEvent e) {
if (e.getValueIsAdjusting()) {
return;
}
int index = patientTable.getSelectedRow();
if (index < 0) {
return;
}
index = patientTable.convertRowIndexToModel(index);
MyPatient selectedPatient = patientModel.getPatient(index);
List<MyPtVisit> visits = selectedPatient.getVisits();
MyPtVisitTableModel visitsModel = new MyPtVisitTableModel(visits);
ptVisitTable.setModel(visitsModel);
}
}
private static void createAndShowGui() {
MyDemo mainPanel = new MyDemo();
JFrame frame = new JFrame("My Demo");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> createAndShowGui());
}
}
@SuppressWarnings("serial")
class MyPatientTableModel extends DefaultTableModel {
public MyPatientTableModel() {
super(MyPatient.HEADINGS, 0);
}
@SuppressWarnings("unchecked")
public MyPatient getPatient(int index) {
String patientId = (String) getValueAt(index, 0);
String lastName = (String) getValueAt(index, 1);
String firstName = (String) getValueAt(index, 2);
// non-displayed data
List<MyPtVisit> visits = (List<MyPtVisit>) getValueAt(index, 3);
MyPatient patient = new MyPatient(patientId, lastName, firstName);
patient.setVisits(visits);
return patient;
}
@Override
public Class<?> getColumnClass(int columnIndex) {
if (getRowCount() != 0 && getValueAt(0, columnIndex) != null) {
return getValueAt(0, columnIndex).getClass();
} else {
return super.getColumnClass(columnIndex);
}
}
public void addRow(MyPatient patient) {
Vector<Object> rowData = new Vector<>();
rowData.add(patient.getPatientId());
rowData.add(patient.getLastName());
rowData.add(patient.getFirstName());
rowData.add(patient.getVisits()); // not displayed!
addRow(rowData);
}
public void setPatientAt(int row, MyPatient patient) {
setValueAt(patient.getPatientId(), row, 0);
setValueAt(patient.getLastName(), row, 1);
setValueAt(patient.getFirstName(), row, 2);
setValueAt(patient.getVisits(), row, 3);
}
}
@SuppressWarnings("serial")
class MyPtVisitTableModel extends DefaultTableModel {
public MyPtVisitTableModel(List<MyPtVisit> visits) {
super(MyPtVisit.HEADINGS, 0);
for (MyPtVisit myPtVisit : visits) {
addRow(myPtVisit);
}
}
@Override
public Class<?> getColumnClass(int columnIndex) {
if (getRowCount() != 0 && getValueAt(0, columnIndex) != null) {
return getValueAt(0, columnIndex).getClass();
} else {
return super.getColumnClass(columnIndex);
}
}
public void addRow(MyPtVisit myPtVisit) {
Vector<Object> rowData = new Vector<>();
rowData.add(myPtVisit.getCost());
rowData.add(myPtVisit.getSymptom());
rowData.add(myPtVisit.getTreatment());
addRow(rowData);
}
// extract data from table model
public List<MyPtVisit> getVisits() {
List<MyPtVisit> visits = new ArrayList<>();
for (int i = 0; i < getRowCount(); i++) {
double cost = (double) getValueAt(i, 0);
String symptom = (String) getValueAt(i, 1);
String treatment = (String) getValueAt(i, 2);
visits.add(new MyPtVisit(cost, symptom, treatment));
}
return visits;
}
}
// class that represents each patient
class MyPatient {
public static final String[] HEADINGS = { "Patient ID", "Last Name", "First Name", "Visits" };
private String patientId;
private String lastName;
private String firstName;
private List<MyPtVisit> visits = new ArrayList<>();
public MyPatient(String patientId, String lastName, String firstName) {
this.patientId = patientId;
this.lastName = lastName;
this.firstName = firstName;
}
public String getPatientId() {
return patientId;
}
public void setPatientId(String patientId) {
this.patientId = patientId;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public void addVisit(MyPtVisit ptVisit) {
visits.add(ptVisit);
}
public List<MyPtVisit> getVisits() {
// create new ArrayList to hold copy
List<MyPtVisit> copyVisits = new ArrayList<>();
for (MyPtVisit myPtVisit : visits) {
// use MyPtVisit's copy constructor to create a new MyPtVisit
copyVisits.add(new MyPtVisit(myPtVisit));
}
return copyVisits;
}
public void setVisits(List<MyPtVisit> visits) {
this.visits = visits;
}
@Override
public String toString() {
return "MyPatient [patientId=" + patientId + ", lastName=" + lastName + ", firstName="
+ firstName + ", visits=" + visits + "]";
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((firstName == null) ? 0 : firstName.hashCode());
result = prime * result + ((lastName == null) ? 0 : lastName.hashCode());
result = prime * result + ((patientId == null) ? 0 : patientId.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
MyPatient other = (MyPatient) obj;
if (firstName == null) {
if (other.firstName != null)
return false;
} else if (!firstName.equals(other.firstName))
return false;
if (lastName == null) {
if (other.lastName != null)
return false;
} else if (!lastName.equals(other.lastName))
return false;
if (patientId == null) {
if (other.patientId != null)
return false;
} else if (!patientId.equals(other.patientId))
return false;
return true;
}
}
// my patient visit
// holds information for each patient's visit to the doctor
class MyPtVisit {
public static final String[] HEADINGS = { "Cost", "Chief Symptom", "Treatment" };
private double cost;
private String symptom;
private String treatment;
public MyPtVisit(double cost, String symptom, String treatment) {
this.cost = cost;
this.symptom = symptom;
this.treatment = treatment;
}
// copy constructor
public MyPtVisit(MyPtVisit original) {
this.cost = original.cost;
this.symptom = original.symptom;
this.treatment = original.treatment;
}
public double getCost() {
return cost;
}
public void setCost(double cost) {
this.cost = cost;
}
public String getSymptom() {
return symptom;
}
public void setSymptom(String symptom) {
this.symptom = symptom;
}
public String getTreatment() {
return treatment;
}
public void setTreatment(String treatment) {
this.treatment = treatment;
}
@Override
public String toString() {
return "MyPtVisit [cost=" + cost + ", symptom=" + symptom + ", treatment=" + treatment
+ "]";
}
}
问题内容: 我正在尝试获取所有用户,并通过另一个表上的字段对他们进行排序,但是此字段并不总是存在吗? 用户-持有用户用户元-持有元数据,特别是“权重”,这是我要根据其排序的内容。 一个更具体的解决方案是自动为它们定义默认权重,但是无论如何,我可以使它不起作用吗?当前工作查询: 失去部分订单,任何/所有帮助将不胜感激! 问题答案: 如果您在表()之间具有关键关系,并且想要列出所有用户,则可以使用类似
问题内容: 我正在使用此处找到的自定义表格模型。我已经使用该帖子中提供的建议更新了我的代码,并遇到了一个新问题。我对我的代码所做的改变是一个注入到我,以避免与线程的问题。完成此操作后,通过按按钮更新我的表的代码已停止工作。 用于初始化的代码如下: 我用来更新的代码如下: 我也尝试过使用,但这也不起作用。截至目前,更新的唯一方法是关闭并重新打开程序。具有我正在使用的,随着用户添加更多玩家,尺寸会增加
我正在制作一个表单,其中使用jQuery进行客户端验证,然后在提交后使用PHP进行服务器端验证。我的问题是,通过使用$(“Form”).Submit(函数(e){},当我单击Cancel和Delete按钮时,验证消息也会出现,而这是不应该的。我只希望只有当单击Save按钮时才会发生验证。有没有其他方法可以做到这一点?非常感谢。下面是我的代码:
我有一些问题与内置的Android按钮栏样式。在给我的每个按钮宽度0和重量1之后,两个按钮之间仍然有大约1px的间隙(见图)。 消除这种差距的最好方法是什么?为什么它一开始就在那里?
问题内容: 我有一个包含几个用户可编辑项(EditText字段,RatingBar等)的活动。我想提示用户是否按下了后退/主页按钮,并且所做的更改尚未保存。阅读完android文档后,似乎这段代码应该放在onPause方法中。我尝试将AlertDialog放在onPause中,但是显示对话框然后立即将其删除,因为没有任何内容可以阻止暂停完成。 到目前为止,这是我想出的: 我是在正确的轨道上吗,还是
我想更改按钮的背景色和前景色。我使用了setBackground、setForeground和SetObque(true),它适用于前景,但不适用于按钮的背景。按钮周围有点像黑色边框,但我希望按钮本身是黑色的。我该怎么修?