Swing/TableModelEvent のバックアップ差分(No.3)
- バックアップ一覧
- 現在との差分 を表示
- 現在との差分 - Visual を表示
- ソース を表示
- バックアップ を表示
- Swing/TableModelEvent へ行く。
- 追加された行はこの色です。
- 削除された行はこの色です。
---
title: JTableのモデルが変更されたことをイベントで受け取る
tags: [JTable, TableModelListener, TableModelEvent, JCheckBox]
author: aterai
pubdate: 2014-03-31T00:21:38+09:00
description: JTableのモデルの変更を受け取ってJTableHeaderに追加したJCheckBoxを更新します。
---
* 概要 [#i5b94092]
`JTable`のモデルの変更を受け取って`JTableHeader`に追加した`JCheckBox`を更新します。
#download(https://lh3.googleusercontent.com/-Mndxsu0wtCM/Uzg00YuVfyI/AAAAAAAACCw/HoRS9CVP_-o/s800/TableModelEvent.png)
* サンプルコード [#obcbca53]
#code(link){{
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));
}
}
}}
* 解説 [#z0c8a08b]
上記のサンプルでは、`0`行目の値(`boolean`)の変更、行の追加、削除を受け取って`JTableHeader`のチェック状態を更新する`TableModelListener`を作成して、これを`TableModel#addTableModelListener(...)`で設定しています。
- `e.getType() == TableModelEvent.DELETE`: 行の削除
-- 削除によって行数が`0`になった場合は、`JTableHeader`は未選択状態
-- `JTableHeader`が選択状態、または未選択状態の場合、削除によってその状態は変化しない
-- `JTableHeader`が不定状態の場合は、全行を検索して選択状態を変更するかどうかを調査する
- `e.getType() == TableModelEvent.INSERT`: 行の追加
-- `JTableHeader`がすでに不定状態の場合は、追加される行の選択状態にかかわらず、その状態は変化しない
-- `JTableHeader`が不定状態でない場合は、追加される行と`JTableHeader`の選択状態を合わせて調査する
- `e.getType() == TableModelEvent.UPDATE`: `0`列目の更新
-- `JTableHeader`が不定状態の場合は、全行を検索して選択状態を変更するかどうかを調査する
-- `JTableHeader`が不定状態でない場合は、この更新によって`JTableHeader`は不定状態になる
* 参考リンク [#t968531f]
- [[JTableHeaderにJCheckBoxを追加してセルの値を切り替える>Swing/TableHeaderCheckBox]]
* コメント [#d9fb2d0a]
#comment
- 修正: `src.zip`などがアップロードされていない -- &user(aterai); &new{2014-05-09 (金) 17:17:04};
#comment