JTable通过TableCellRenderer和TableCellEditor支持自定义数据类型(checkbox等)

本文介绍了如何通过实现TableCellRenderer和TableCellEditor接口,为JTable创建自定义数据类型的支持,特别是如何使用CheckBox。在设计中,定义了一个MColoredValue类来保存数据和背景色状态。针对不同数据类型,如Boolean和String,实现特定的Renderer和Editor。通过Editor处理用户操作事件,并确保在编辑时正确更新和保存数据模型的状态。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

概述

JTable通过TableCellRenderer和TableCellEditor这两个接口实现每个单元格的渲染和编辑,这两个接口都各有一个方法可以返回JComponent的子类,例如BooleanRenderer对应的是Boolean类型的数据,getTableCellRendererComponent返回的是JCheckBox:

class BooleanRenderer extends JCheckBox implements TableCellRenderer, UIResource
{
   
   
   private final Border noFocusBorder = new EmptyBorder(1, 1, 1, 1);

   public BooleanRenderer() {
   
   
       super();
       setHorizontalAlignment(JLabel.CENTER);
       setBorderPainted(true);
   }

   public Component getTableCellRendererComponent(JTable table, Object value,
                                                  boolean isSelected, boolean hasFocus, int row, int column) {
   
   
       if (isSelected) {
   
   
           setForeground(table.getSelectionForeground());
           super.setBackground(table.getSelectionBackground());
       }
       else {
   
   
           setForeground(table.getForeground());
           setBackground(table.getBackground());
       }
       setSelected((value != null && ((Boolean)value).booleanValue()));

       if (hasFocus) {
   
   
           setBorder(UIManager.getBorder("Table.focusCellHighlightBorder"));
       } else {
   
   
           setBorder(noFocusBorder);
       }

       return this; //返回自己,也就是JCheckBox 
   }
}

从如上代码中可以看出,getTableCellRendererComponent方法(TableCellRenderer中的唯一方法)返回的Component就是一个JCheckBox,因此使用个Renderer会在表格的单元格中显示一个勾选框。

只有Renderer只能显示静态数据,如果需要支持对数据进行编辑,那么必须同时实现Editor,不然点击单元格进行编辑时会使用默认的Editor,而默认的Editor使用的是JTextField,所以就会发现点完之后变成“true”和“false”了:
在这里插入图片描述如果只实现Editor也不行,会变成只有在点击的时候显示成Checkbox,其他时候是文本框。

整体设计

在本博客中,我们要实现通过自定义的类型,让JTable用不同的UI组件进行显示,并支持根据数据模型的状态改变单元格的背景色。

设计思路是定义一个MColoredValue类,该类用于保存数据以及保存是否添加背景色。


public class MColoredValue<T> {
   
   
	T value;
	boolean colored;
	
	public MColoredValue(T v, boolean colored){
   
   
		this.value = v;
		this.colored = colored;
	}
	
	public T getValue() {
   
   
		return value;
	}
	public boolean isColored() {
   
   
		return colored;
	}

	public void setValue(T value) {
   
   
		this.value = value;
	}

	public void setColored(boolean colored) {
   
   
		this.colored = colored;
	}

	@Override
	public String toString() {
   
   
		return ""+value;
	}
}

根据我们的设计,如果isColored为true,那么给单元格使用红色背景色,否则用白色。然后我们的数据又分Boolean类型和String类型,我们希望Boolean类型使用CheckBox的形式来显示,String就用默认的文本框来显示。


public class MColoredBoolValue extends MColoredValue<Boolean> {
   
   
	
	public MColoredBoolValue(Boolean v, boolean colored){
   
   
		super(v, colored);
	}
	
	@Override
	public boolean isColored(){
   
   
		return this.value;
	}
	
}

public class MColoredStringValue extends MColoredValue<String> {
   
   
	
	public MColoredStringValue(String v, boolean colored){
   
   
		super(v, colored);
	}
	
}

然后我们实现TableCellRenderer和TableCellEditor接口,但只作为一个壳来使用,在JTable调用getTableCellRendererComponent和getTableCellEditorComponent实例化具体的类,例如如果传入的是MColoredBoolValue类型,那么我们就实例化对应的BooleanRenderer和BooleanEditor,否则用默认的Renderer和Editor。

TableCellRenderer

TableCellRenderer接口中只有getTableCellRendererComponent这一个方法,该方法会传入一个Object类型的参数,该参数就是我们设置到JTable某个单元格里面的值,因此我们可以通过判断这个参数的类型来选择使用不同的Renderer,比如Boolean类型可以用勾选框或下拉框来显示。

import java.awt.Color;
import java.awt.Component;
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值