该文本框用于过滤JTable表格中的内容,显示与文本框中的内容相匹配的记录。
实现JTable表格的过滤和排序主要就是设置JTable的RowSorter,RowSorter提供为我们提供了排序和过滤的基础。
import java.awt.Graphics;
import java.awt.Insets;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.ImageIcon;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.RowFilter;
import javax.swing.table.TableModel;
import javax.swing.table.TableRowSorter;
/**
* 表格过滤文本框,过滤表格中的数据,显示与本文本框中匹配的文字
* @author wzh
*/
public class JTableFilterTextField extends JTextField implements KeyListener {
private JTable mTable;
private ImageIcon icon;
public JTableFilterTextField() {
this.addKeyListener(this);
//获取当前路径下的图片
icon = new ImageIcon(getClass().getResource("./search.png"));
Insets insets = new Insets(0, 20, 0, 0);
//设置文本输入距左边20
this.setMargin(insets);
}
/**
* 设置需要过滤的表格
* @param table
*/
public void setTable(JTable table) {
this.mTable = table;
}
@Override
public void keyTyped(KeyEvent e) {
}
@Override
public void keyPressed(KeyEvent e) {
}
@Override
public void keyReleased(KeyEvent e) {
if(mTable == null) {
return;
}
TableRowSorter<TableModel> sorter = (TableRowSorter<TableModel>) mTable.getRowSorter();
if(sorter == null) {
sorter = new TableRowSorter<>(mTable.getModel());
mTable.setRowSorter(sorter);
}
String text = this.getText();
if (text.length() == 0) {
sorter.setRowFilter(null);
} else {
//设置RowFilter 用于从模型中过滤条目,使得这些条目不会在视图中显示
sorter.setRowFilter(RowFilter.regexFilter(text));
}
}
@Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
Insets insets = getInsets();
int iconWidth = icon.getIconWidth();
int iconHeight = icon.getIconHeight();
int Height = this.getHeight();
//在文本框中画上之前图片
icon.paintIcon(this, g, (insets.left - iconWidth)/2, (Height - iconHeight) / 2);
}
}
值得注意的地方在于两个地方:
1、清除JTable中数据的方式有三种
第一种:((DefaultTableModel)jTable1.getModel()).setRowCount(0);
第二种:int rowcount=((DefaultTableModel)jTable1.getModel()).getRowCount();
for (int j = 0; j <rowcount; j++) {
((DefaultTableModel)jTable1.getModel()).removeRow(0);
}
这两种在表格中内容没有排序的情况下,用于清除表格中数据是可行的,但是当有排序时,Model中的数据和View中的数据就不是一一对应了,在对表内容进行增删改之后,用该方法清除表格内容再加载数据,则有可能会报ArrayIndexOutOfBoundsException。
第三种:((DefaultTableModel)table.getModel()).getDataVector().clear();
((DefaultTableModel) table.getModel()).fireTableDataChanged();
用这种方式清除表格中的内容就避免了抛出ArrayIndexOutOfBoundsException异常。
2、通过排序之后的JTable,通过int viewRow = jTable1.getSelectedRow()获取到选中行时,此时选中的为View中的行数而不是底层Model中的行数,如需转换可以调用 int modelRow = jTable1.convertRowIndexToModel(viewRow)方法,反之
int viewRow = jTable1.convertRowIndexToView(modelRow ))方法将底层Model中的索引转化成View中的索引。