Java JTable禁用单个单元格选择边框高亮显示 [英] Java JTable disable single cell selection border highlight

查看:174
本文介绍了Java JTable禁用单个单元格选择边框高亮显示的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个JTable,每行有三列,见图:

I have a JTable with three columns in each row, see the image:

由于某些原因,根据我选择的列,我得到它周围的小深蓝色边框(V140116554)in上面的图片。

For some reason depending on the column i select i get the little dark blue border around it (V140116554) in the image above.

我目前用它来选择整行:

I currently use this to select the entire row:

vTable.setRowSelectionAllowed(true);

如何禁用此功能?

编辑:

添加了一个类:

public class VisitorRenderer extends DefaultTableCellRenderer {
    @Override
    public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
        super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column); 
        setBorder(noFocusBorder);
        return this;
    }
} 

并添加:

vTable.setDefaultRenderer(String.class, new VisitorRenderer());

但仍然获得边界

推荐答案

TableCellRenderer 负责在当前聚焦的单元格周围绘制焦点矩形。您需要提供自己的渲染器,该渲染器能够覆盖此功能或提供自己的功能...

The TableCellRenderer is responsible for drawing the focus rectangle around the currently focused cell. You need to supply your own renderer that is capable of either overriding this feature or providing its own...

例如;

public class MyRenderer extends DefaultTableCellRenderer {

    @Override
    public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
        super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column); 
        setBorder(noFocusBorder);
        return this;
    }

}

这使用 DefaultTableCellRenderer 作为基础渲染器并将组件的 Border 设置为 noFocusBorder ,这是定义的在 DefaultTableCellRenderer 作为 EmptyBorder

This uses the DefaultTableCellRenderer as the base renderer and sets the component's Border to noFocusBorder which is defined in DefaultTableCellRenderer as a EmptyBorder

您将需要将此渲染器设置为受影响列的默认渲染器。查看如何使用表以获取更多详细信息

You will then need to set this renderer as the default renderer for the effected columns. Check out How to use tables for more details

使用示例更新

对我来说工作正常...

Works fine for me...

import java.awt.Color;
import java.awt.Component;
import java.awt.EventQueue;
import javax.swing.JFrame;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.border.LineBorder;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.DefaultTableModel;

public class TableRenderer {

    public static void main(String[] args) {
        new TableRenderer();
    }

    public TableRenderer() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                DefaultTableModel model = new DefaultTableModel(new Object[][]{{"", "One"}, {"", "Two"}}, new Object[]{"Check", "Vistor"}) {
                    @Override
                    public Class<?> getColumnClass(int columnIndex) {
                        return String.class;
                    }
                };

                JTable table = new JTable(model);
                table.setRowSelectionAllowed(true);
                table.setShowGrid(false);
                table.setDefaultRenderer(String.class, new VisitorRenderer());

                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(new JScrollPane(table));
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class VisitorRenderer extends DefaultTableCellRenderer {

        @Override
        public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
            super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
            setBorder(noFocusBorder);
            return this;
        }
    }
}

为了确保,我将 setBorder(noFocusBorder); 更改为...

And just to be sure, I changed setBorder(noFocusBorder); to...

if (hasFocus) {
    setBorder(new LineBorder(Color.RED));
}

从外观上看,访客列类类型未报告为字符串 TableModel ...

From the looks of things, the visitor column class type isn't being reported as String by the TableModel...

已更新为代理渲染器概念

因为要从每个单元格中删除焦点边框。你有三个选择...

Because you want to remove the focus border from every cell. You three choices...


  1. Class 您可能需要的表格类型。这可能会花费很多时间并重复使用很多代码来实现很小的效果。

  2. 不做任何事情......

  3. 使用代理渲染器。这是一个渲染器,它使用另一个 TableCellRenderer 来执行实际渲染过程,但对结果应用了一些细微的更改,例如,删除边框......

  1. Write a custom cell renderer for every possibility of Class type you might need for your table. This can time consuming and repeats a lot of code to achieve only a small effect.
  2. Do nothing a live with it...
  3. Use a "proxy" renderer. This is a renderer that uses another TableCellRenderer to perform the actual rendering process, but applies some minor changes to the result, for example, remove the border...

...

public static class ProxyCellRenderer implements TableCellRenderer {

    protected static final Border DEFAULT_BORDER = new EmptyBorder(1, 1, 1, 1);
    private TableCellRenderer renderer;

    public ProxyCellRenderer(TableCellRenderer renderer) {
        this.renderer = renderer;
    }

    @Override
    public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
        Component comp = renderer.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
        if (comp instanceof JComponent) {
            ((JComponent)comp).setBorder(DEFAULT_BORDER);
        }
        return comp;
    }        
}

而不是像...那样做...

Instead of doing something like...

table.setDefaultRenderer(String.class, new VisitorRenderer());

之前我们做过,我们会这样做......

Which we did before, we would do this instead...

table.setDefaultRenderer(String.class, 
    new ProxyCellRenderer(table.getDefaultRenderer(String.class)));

这意味着我们可以利用已经可用的默认渲染器,而不知道可能是什么,还提供我们自己的定制要求...

This means we can take advantage of the what ever default renderer is already available without knowing what that might be, but also supply our own custom requirements to it...

这篇关于Java JTable禁用单个单元格选择边框高亮显示的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆