JTableのモデルが変更されたことをイベントで受け取る
Total: 10121
, Today: 7
, Yesterday: 3
Posted by aterai at
Last-modified:
概要
JTable
のモデルの変更を受け取ってJTableHeader
に追加したJCheckBox
を更新します。
Screenshot
Advertisement
サンプルコード
class HeaderCheckBoxHandler implements TableModelListener {
private final JTable table;
private final int targetColumnIndex;
public HeaderCheckBoxHandler(JTable table, int index) {
this.table = table;
this.targetColumnIndex = index;
}
@Override public void tableChanged(TableModelEvent e) {
int vci = table.convertColumnIndexToView(targetColumnIndex);
TableColumn column = table.getColumnModel().getColumn(vci);
Object status = column.getHeaderValue();
TableModel m = table.getModel();
if (e.getType() == TableModelEvent.DELETE) {
if (m.getRowCount() == 0) {
column.setHeaderValue(Status.DESELECTED);
} else if (Status.INDETERMINATE.equals(status)) {
boolean selected = true;
boolean deselected = true;
for (int i = 0; i < m.getRowCount(); i++) {
Boolean b = (Boolean) m.getValueAt(i, targetColumnIndex);
selected &= b;
deselected &= !b;
}
if (deselected) {
column.setHeaderValue(Status.DESELECTED);
} else if (selected) {
column.setHeaderValue(Status.SELECTED);
} else {
return;
}
}
} else if (e.getType() == TableModelEvent.INSERT
&& !Status.INDETERMINATE.equals(status)) {
boolean selected = Status.DESELECTED.equals(status);
boolean deselected = Status.SELECTED.equals(status);
for (int i = e.getFirstRow(); i <= e.getLastRow(); i++) {
Boolean b = (Boolean) m.getValueAt(i, targetColumnIndex);
selected &= b;
deselected &= !b;
}
if (selected && m.getRowCount() == 1) {
column.setHeaderValue(Status.SELECTED);
} else if (selected || deselected) {
column.setHeaderValue(Status.INDETERMINATE);
}
} else if (e.getType() == TableModelEvent.UPDATE
&& e.getColumn() == targetColumnIndex) {
if (Status.INDETERMINATE.equals(status)) {
boolean selected = true;
boolean deselected = true;
for (int i = 0; i < m.getRowCount(); i++) {
Boolean b = (Boolean) m.getValueAt(i, targetColumnIndex);
selected &= b;
deselected &= !b;
if (selected == deselected) {
return;
}
}
if (deselected) {
column.setHeaderValue(Status.DESELECTED);
} else if (selected) {
column.setHeaderValue(Status.SELECTED);
} else {
return;
}
} else {
column.setHeaderValue(Status.INDETERMINATE);
}
}
JTableHeader h = table.getTableHeader();
h.repaint(h.getHeaderRect(vci));
}
}
View in GitHub: Java, Kotlin解説
上記のサンプルでは、0
列目のセルの値(boolean
)変更、行の追加、削除イベントなどを受け取って、JTableHeader
のチェック状態を更新するTableModelListener
を作成して、これをTableModel#addTableModelListener(...)
で設定しています。
- 行の削除:
e.getType() == TableModelEvent.DELETE
- 削除によって行数が
0
になった場合はJTableHeader
は未選択状態 JTableHeader
が選択状態、または未選択状態の場合、削除によってその状態は変化しないJTableHeader
が不定状態の場合は全行を検索して選択状態を変更するかどうかを調査する
- 削除によって行数が
- 行の追加:
e.getType() == TableModelEvent.INSERT
JTableHeader
がすでに不定状態の場合は追加される行の選択状態にかかわらずその状態は変化しないJTableHeader
が不定状態でない場合は追加される行とJTableHeader
の選択状態を合わせて調査する
- 行(
0
列目)の更新:e.getType() == TableModelEvent.UPDATE
JTableHeader
が不定状態の場合は全行を検索して選択状態を変更するかどうかを調査するJTableHeader
が不定状態でない場合はこの更新によってJTableHeader
は不定状態になる