java - 如何在 Swing 中制作自定义尺寸的组件

标签 java swing jcomponent

我有 2 个组件(均源自 jComponent)。一个是 map ,另一个是该 map 内的领土,如下图所示。

Map with Territories

到目前为止, map 的绘制尺寸固定为 1200x800。对于每个领土,我都有一个点列表,这些点将连接成每个国家的形状。

到目前为止,绘制一切都工作得很好。但是,当我单击一个国家/地区时,总是会调用最后绘制的领土。似乎每个领土都是整个 map 上的一层。我怎样才能让它工作,如果我点击一个区域,那么只有这个区域被点击。这样如果我点击中国,中国的点击事件就会被调用?

下面是两个组件的代码,以防有帮助:

map .java

public class Map extends JComponent {

    private Collection<Territory> territories;
    public Map(Collection<Territory> territories) {
        super();
        this.territories = territories;
    }

    @Override
    public void paintComponent(Graphics graphics)
    {
        graphics.setColor(new Color(8, 114, 200));
        graphics.fillRect(0, 0, this.getWidth(), this.getHeight());

        for (Territory tmp : this.territories) {
            TerritoryComponent territoryComponent = new TerritoryComponent(tmp);
            this.add(territoryComponent);
        }
        this.updateUI();
    }

}

TerritoryComponent.java

public class TerritoryComponent extends JComponent implements MouseListener {

    private Territory territory;

    public TerritoryComponent(Territory tmp) {
        super();
        this.setSize(this.getMaximumSize());
        this.addMouseListener(this);
        this.territory = tmp;
    }

    @Override
    public void paintComponent(Graphics graphics)
    {
        for (Patch patch : this.territory.getPatches()) {
            ArrayList<Point> points = patch.getPoints();
            int x[] = new int[points.size() + 1];
            int y[] = new int[points.size() + 1];
            for (int i = 0; i < points.size(); i++) {
                x[i] = (int) points.get(i).getX();
                y[i] = (int) points.get(i).getY();
            }
            x[points.size()] = (int) points.get(0).getX();
            y[points.size()] = (int) points.get(0).getY();

            graphics.setColor(new Color(255, 255, 255));
            graphics.fillPolygon(x, y, points.size() + 1);

            graphics.setColor(new Color(52, 52, 52));
            graphics.drawPolyline(x, y, points.size() + 1);
        }

    }

    @Override
    public void mouseClicked(MouseEvent e) {
        System.out.println("clicked " + this.territory.getName());
    }

    @Override
    public void mousePressed(MouseEvent e) {

    }

    @Override
    public void mouseReleased(MouseEvent e) {

    }

    @Override
    public void mouseEntered(MouseEvent e) {

    }

    @Override
    public void mouseExited(MouseEvent e) {

    }
}

最佳答案

And for each territorys I have a list of points,

  1. 创建一个多边形对象来代表您的每个领土。
  2. 将每个多边形添加到 ArrayList
  3. 在paintComponent()方法中,您只需迭代ArrayList来绘制每个Polygon

if I click on a single territory that only this gets clicked.

在 mouseClicked(...) 事件中,您将获取鼠标点并迭代包含所有多边形的 ArrayList。然后,您可以使用 Polygon.contains(...) 方法来确定您单击的区域。

也不要使用 updateUI() 方法。仅当 LAF 更改时才应调用该方法。尤其不应在绘画方法中调用它,因为这将导致组件可能重新绘制自身。

关于java - 如何在 Swing 中制作自定义尺寸的组件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34518591/

相关文章:

java - 将相同的组件添加到 JTextPane

java - Servlet-调用java函数

java - 我真正使用的是哪个 JRE?

java - 垃圾收集器是否处理 java 中的静态变量或方法?

java - 更新 JComponent 以反射(reflect)对象更改

java - 在 Java 中创建矩形时,我真的调用了 paintComponent 方法吗?

java - Apache CXF java.lang.StackOverflowError

java - 如何高效、快速地用 JButton 完全填充 JFrame?

java - 使 JTable 单元格不可编辑

java - JlayeredPane 透明度 setOpaque 不起作用