如何在 java 中绘制热图,显示圆圈而不是颜色
How to draw heatmap in java, showing circles instead of color
我正在生成一个热图,使用 Jtable 并用数字填充它,然后用颜色填充
. Instead of colors, I want to show the circles or some other graphical image, which would be relative in size, like this 。
我在 R 中找到了一个库可以做到这一点,geom_tile,但找不到任何在 Javs 中做到这一点的方法。你们有什么想法或例子吗?
要绘制自定义 table 单元格,您需要提供自己的 TableCellRenderer
实现。
您的自定义 TableCellRenderer 只能实现一个方法:getTableCellRendererComponent
,它必须 return 一个 Component
or JComponent
.
您的 TableCellRenderer 然后可以 return 自定义 JComponent,它根据预先设置的单元格值绘制圆。
下面的示例代码演示了如何设置您的自定义 HeatmapCellRenderer
,它使用 DotRenderer
作为组件来呈现单个单元格:
public class TableHeatmap {
public static void main(String[] args) {
JFrame frame = new JFrame();
// create a demo table 10 x 10 cells
JTable table = new JTable(10, 10);
frame.setContentPane(table);
// fill in some random data
for (int row = 0; row < 10; row++) {
for (int col = 0; col < 10; col++) {
table.setValueAt((int) (Math.random() * 10), row, col);
}
}
// set our custom TableCellRenderer
table.setDefaultRenderer(Object.class, new HeatmapCellRenderer());
table.setRowHeight(30);
// show the window
frame.pack();
frame.setVisible(true);
}
private static class HeatmapCellRenderer implements TableCellRenderer {
private final DotRenderer renderer = new DotRenderer();
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
if (value instanceof Integer) {
this.renderer.setValue((Integer) value);
return this.renderer;
}
return null;
}
}
private static class DotRenderer extends JComponent {
private int value;
public void setValue(int value) {
this.value = value;
}
@Override
protected void paintComponent(Graphics g) {
g.setColor(Color.BLUE);
g.fillRect(0, 0, this.getWidth(), this.getHeight());
g.setColor(Color.RED);
int centerX = this.getWidth() / 2;
int centerY = this.getHeight() / 2;
g.fillOval(centerX - this.value, centerY - this.value, this.value * 2, this.value * 2);
}
}
}
以上代码应生成类似于以下屏幕截图的 table:
通过为您的单元格使用比 Integer
更复杂的对象,您可以实现更复杂的渲染器。例如,如果您有一个简单的数据 class class MyData { int value1; int value2; }
并将这些值插入 table,您可以实现一个根据 value1
设置背景颜色的渲染器,以及点的大小基于单元格值的 value2
。将 value3
添加到 class 将进一步允许根据这些值为点着色,非常接近您的示例图像。
我正在生成一个热图,使用 Jtable 并用数字填充它,然后用颜色填充
要绘制自定义 table 单元格,您需要提供自己的 TableCellRenderer
实现。
您的自定义 TableCellRenderer 只能实现一个方法:getTableCellRendererComponent
,它必须 return 一个 Component
or JComponent
.
您的 TableCellRenderer 然后可以 return 自定义 JComponent,它根据预先设置的单元格值绘制圆。
下面的示例代码演示了如何设置您的自定义 HeatmapCellRenderer
,它使用 DotRenderer
作为组件来呈现单个单元格:
public class TableHeatmap {
public static void main(String[] args) {
JFrame frame = new JFrame();
// create a demo table 10 x 10 cells
JTable table = new JTable(10, 10);
frame.setContentPane(table);
// fill in some random data
for (int row = 0; row < 10; row++) {
for (int col = 0; col < 10; col++) {
table.setValueAt((int) (Math.random() * 10), row, col);
}
}
// set our custom TableCellRenderer
table.setDefaultRenderer(Object.class, new HeatmapCellRenderer());
table.setRowHeight(30);
// show the window
frame.pack();
frame.setVisible(true);
}
private static class HeatmapCellRenderer implements TableCellRenderer {
private final DotRenderer renderer = new DotRenderer();
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
if (value instanceof Integer) {
this.renderer.setValue((Integer) value);
return this.renderer;
}
return null;
}
}
private static class DotRenderer extends JComponent {
private int value;
public void setValue(int value) {
this.value = value;
}
@Override
protected void paintComponent(Graphics g) {
g.setColor(Color.BLUE);
g.fillRect(0, 0, this.getWidth(), this.getHeight());
g.setColor(Color.RED);
int centerX = this.getWidth() / 2;
int centerY = this.getHeight() / 2;
g.fillOval(centerX - this.value, centerY - this.value, this.value * 2, this.value * 2);
}
}
}
以上代码应生成类似于以下屏幕截图的 table:
通过为您的单元格使用比 Integer
更复杂的对象,您可以实现更复杂的渲染器。例如,如果您有一个简单的数据 class class MyData { int value1; int value2; }
并将这些值插入 table,您可以实现一个根据 value1
设置背景颜色的渲染器,以及点的大小基于单元格值的 value2
。将 value3
添加到 class 将进一步允许根据这些值为点着色,非常接近您的示例图像。