1

我在网格布局中向特定元素(网格?)添加图标时遇到问题。我的网格布局包含 64 个“砖块”,旨在用作棋盘。

我的网格代码如下所示:

棋盘

public class SjakkBrett extends JFrame implements Config {

public ChessBoard() {

    setSize(800,800);
    setLayout(new GridLayout(BRICKS/ ROWS, 0) );

    for (int id = 0; id < BRICKS; id++)         
        add(new Brick(id)); 

    setVisible(true);

}

配置

public interface Config {
    public int ROWS= 8;
    public int BRICKS= 64;
}

我的问题是我似乎无法找到将图标添加到板上特定积木的方法,例如setIcon(new ImageIcon("pawn.png"));因为我不知道如何使用我正在制作的积木 ID。

任何人都可以在这里帮助我吗?

4

4 回答 4

4

要回答您的具体问题:

List<Brick> bricks = new ArrayList<Brick>();

public ChessBoard() {

    setSize(800,800);
    setLayout(new GridLayout(BRICKS/ ROWS, 0) );

    for (int id = 0; id < BRICKS; id++) {
        Brick brick = new Brick(id);        
        add(brick); 
        bricks.add(brick);
    }

    setVisible(true);

}

public void setBrick(int id, int piece) {
    bricks.get(id).setPiece(piece);
}

为了回答您未提出的问题,让我们考虑一下国际象棋游戏。

在此处输入图像描述

棋盘已经有符号。典型的第一步是 e4。由于没有指定一块,这意味着一个棋子。唯一可以移动到 e4 的棋子是坐在 e2 上的棋子。因此,e4 是“将 pawn 从 e2 移动到 e4”的简写方式。

因此,我们有排列成板的砖块(正方形)。根据每块不同的规则,我们有能够从一块砖移到另一块的块。我们还有捕获规则和确定谁获胜的规则。

所有这些元素都必须以对象或方法的形式出现在游戏中。

所以,让我们谈谈对象。

我们有一块砖(正方形)。我们有一组称为板的砖块。我们有碎片。

这些对象是相互关联的。它们的共同点是位置的概念。

一块砖位于特定位置 (e2)。董事会需要知道如何将一个点 (e2) 转换为有意义的东西(第 1 行,第 4 列;假设第 0 行,第 0 列是左下角)。一块需要知道它的位置(e2),它可以合法去哪里(e3,e4),以及它将去哪里(e4)。

这应该足以让你开始。

于 2013-01-31T09:38:36.273 回答
3

我猜想,用图标添加标签可能会让稍后为游戏制作可移动的部分变得更容易,但我仍然不知道如何将标签添加到网格布局中的特定 ID。BRICKS 只是从 Config 中获取它的信息,它在哪里声明(?)值 64。很抱歉,如果我在这里使用了错误的名称和东西,但我可以重新使用 java 来实际使用它。

  • 查看put/getClientProperty ,然后从s数组或从数组中返回适当坐标的任何动作/事件KeyboardMouseXxxListenerJLabelJButtons

  • 你可以有多个put/getClientProperty,没有任何限制

  • 我将使用JButton在 API中实现setXxxIcon)而不是JLabel(需要调用repaint()for MouseMotionListener

于 2013-01-31T09:26:54.257 回答
2

我有这个代码,我用它作为我自己的国际象棋游戏的基础。

基本上由6个类组成:

  • Test基本上保存main和创建 GUI 以及将单个棋子加载到棋盘上。
  • NotationPanel用于在板的侧面显示行和列。
  • Chessboard它包含ChessboardBlock组成电路板的所有 s,还在适当的位置用黑白标签布置电路板。
  • ChessboardBlock它有一个固定的位置(即 A4 等)并且可以保存一个ChessPiece实例。
  • ChessPiece它保存Piece实例的数据/图像。
  • ChessPieceMouseAdapter处理 s 的拖放Piece

在此处输入图像描述

典型动作的输出:

来自位置:A1 件类型:骑士件颜色:白色

到位置:D3 件类型:骑士件颜色:白色

import java.awt.*;
import java.awt.event.*;
import java.awt.image.BufferedImage;
import java.net.URL;
import java.util.ArrayList;
import javax.imageio.ImageIO;
import javax.swing.*;

public class Test {

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                JFrame frame = new JFrame("Test");
                frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);

                ChessPieceMouseAdapter chessPieceMouseAdapter = new ChessPieceMouseAdapter() {
                    @Override
                    boolean chessPieceSelected(ChessPiece chessPiece, ChessboardBlock cb) {
                        System.out.println("From Location: " + chessPiece.getLocation()
                                + " Piece Type: " + chessPiece.getType()
                                + " Piece Color: " + chessPiece.getColor());
                        return true;
                    }

                    @Override
                    void chessPiecePlaced(ChessPiece chessPiece, ChessboardBlock cb) {
                        cb.setPiece(new ChessPiece(chessPiece.getImage(),
                                chessPiece.getType(),
                                cb.getBlockLocation(),
                                chessPiece.getColor()));

                        System.out.println("To Location: " + cb.getChessPiece().getLocation()
                                + " Piece Type: " + cb.getChessPiece().getType()
                                + " Piece Color: " + cb.getChessPiece().getColor());
                    }
                };

                Chessboard chessBoard = new Chessboard(chessPieceMouseAdapter);
                chessPieceMouseAdapter.setChessboard(chessBoard);//or else NPE will be thrown when press/drag/release on chessboard occurs

                BufferedImage knightImage = null;
                try {
                    knightImage = ImageIO.read(new URL("http://i.stack.imgur.com/qdppY.png"));
                } catch (Exception e) {
                    e.printStackTrace();
                }
                ChessPiece knightPiece = new ChessPiece(knightImage, "Knight", null, "White");//location parameter can be null or anything will be set if matching block is found
                chessBoard.setChessPiece("A1", knightPiece);

                NotationPanel rows = new NotationPanel(new String[]{"8", "7", "6", "5", "4", "3", "2", "1"}, NotationPanel.VERTICAL);
                NotationPanel cols = new NotationPanel(new String[]{"A", "B", "C", "D", "E", "F", "G", "H"}, NotationPanel.HORIZONTAL);

                frame.add(rows, BorderLayout.WEST);
                frame.add(cols, BorderLayout.SOUTH);
                frame.add(chessBoard);

                frame.pack();
                frame.setVisible(true);
            }
        });
    }
}

class NotationPanel extends JPanel {

    final static String HORIZONTAL = "horizontal";
    final static String VERTICAL = "vertical";

    public NotationPanel(String[] strings, String direction) {
        if (direction.equals(VERTICAL)) {
            setLayout(new GridLayout(8, 0));
        } else {
            setLayout(new GridLayout(0, 8));
        }
        for (String string : strings) {
            this.add(new JLabel(string, JLabel.CENTER));
        }

    }
}

class Chessboard extends JPanel {

    private final ArrayList<ChessboardBlock> chessBoardBlocks;
    ChessPieceMouseAdapter chessPieceMouseAdapter;

    public Chessboard(ChessPieceMouseAdapter chessPieceMouseAdapter) {
        super(new GridLayout(8, 8));
        chessBoardBlocks = new ArrayList<>(64);
        layoutBoard();
        this.chessPieceMouseAdapter = chessPieceMouseAdapter;
        addMouseListener(this.chessPieceMouseAdapter);
        addMouseMotionListener(this.chessPieceMouseAdapter);
    }

    private void layoutBoard() {
        String[] cols = new String[]{"A", "B", "C", "D", "E", "F", "G", "H"};
        int[] rows = new int[]{1, 2, 3, 4, 5, 6, 7, 8};
        int NUMBER_OF_BLOCKS = 64;
        String row, col;
        int rowCount = 7, colCount = 0, trigger = 8;

        for (int i = 0; i < NUMBER_OF_BLOCKS; i++) {
            if (trigger == 0) {
                colCount = 0;
                trigger = 8;
                rowCount--;
            }
            col = cols[colCount++];
            row = String.valueOf(rows[rowCount]);
            trigger--;

            Color pieceHolderColor = ((rowCount + colCount) % 2 == 0 ? Color.WHITE : Color.BLACK);
            String pieceHolderLocation = col + row;

            ChessboardBlock pieceHolder = new ChessboardBlock(pieceHolderLocation, pieceHolderColor);
            pieceHolder.setPiece(null);

            add(pieceHolder);//add to the board
            chessBoardBlocks.add(pieceHolder);//add to piece holder array
        }
    }

    boolean setChessPiece(String location, ChessPiece piece) {
        for (int i = 0; i < chessBoardBlocks.size(); i++) {
            if (chessBoardBlocks.get(i).getBlockLocation().equalsIgnoreCase(location)) {
                chessBoardBlocks.get(i).setPiece(new ChessPiece(piece.getImage(),
                        piece.getType(), chessBoardBlocks.get(i).getBlockLocation(),
                        piece.getColor()));
                return true;
            }
        }
        return false;
    }

    public ArrayList<ChessboardBlock> getChessBoardBlocks() {
        return chessBoardBlocks;
    }

    @Override
    protected void paintChildren(Graphics g) {
        super.paintChildren(g);

        if (chessPieceMouseAdapter.isDragging()) {
            if (chessPieceMouseAdapter.getDraggedPiece() != null) {
                Graphics2D g2d = (Graphics2D) g;
                g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
                g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);

                g2d.drawImage(chessPieceMouseAdapter.getDraggedPiece().getImage(),
                        chessPieceMouseAdapter.getDraggedPieceLocation().x, chessPieceMouseAdapter.getDraggedPieceLocation().y, this);
            }
        }
    }
}

class ChessboardBlock extends JLabel {

    private final Dimension labelDimensions = new Dimension(50, 50);
    private ChessPiece chessPiece;
    private String location;

    public ChessboardBlock(String location, Color backgroundColor) {
        //super(location,JLabel.CENTER);//puts location as text on label
        this.location = location;
        setBackground(backgroundColor);
        setOpaque(true);
    }

    @Override
    public Dimension getPreferredSize() {
        return labelDimensions;
    }

    void setPiece(ChessPiece p) {
        this.chessPiece = p;
        if (chessPiece == null) {
            setIcon(null);
        } else if (chessPiece.getImage() != null) {
            setIcon(new ImageIcon(chessPiece.getImage()));
        }
    }

    String getBlockLocation() {
        return location;
    }

    public ChessPiece getChessPiece() {
        return chessPiece;
    }
}

class ChessPiece {

    private BufferedImage image;
    private String location;
    private String type;
    private final String color;

    public ChessPiece(BufferedImage image, String type, String location, String color) {
        this.image = image;
        this.type = type;
        this.location = location;
        this.color = color;
    }

    public ChessPiece(ChessPiece p) {
        this.image = p.getImage();
        this.type = p.getType();
        this.location = p.getLocation();
        this.color = p.getColor();
    }

    public String getLocation() {
        return location;
    }

    public String getColor() {
        return color;
    }

    public void setLocation(String location) {
        this.location = location;
    }

    public BufferedImage getImage() {
        return image;
    }

    String getType() {
        return type;
    }
}

abstract class ChessPieceMouseAdapter extends MouseAdapter {

    private Chessboard chessboard;
    private ChessPiece draggedChessPiece;
    private boolean dragging;
    private Rectangle pieceRectangle;
    private Point draggedPieceInitialLocation;
    private Point pressedPoint;

    public ChessPieceMouseAdapter() {
        dragging = false;
        draggedPieceInitialLocation = new Point();
        pressedPoint = new Point();
    }

    public Point getDraggedPieceLocation() {
        return new Point(pieceRectangle.x, pieceRectangle.y);
    }

    public ChessPiece getDraggedPiece() {
        return draggedChessPiece;
    }

    @Override
    public void mousePressed(MouseEvent me) {
        pressedPoint = me.getPoint();
        ArrayList<ChessboardBlock> chessBoardBlocks = chessboard.getChessBoardBlocks();
        for (int i = 0; i < chessBoardBlocks.size(); i++) {
            if (chessBoardBlocks.get(i).getChessPiece() != null) {
                pieceRectangle = chessBoardBlocks.get(i).getBounds();
                if (pieceRectangle.contains(pressedPoint)) {
                    ChessPiece chessPiece = chessBoardBlocks.get(i).getChessPiece();
                    if (chessPieceSelected(chessPiece, chessBoardBlocks.get(i))) {
                        draggedChessPiece = new ChessPiece(chessPiece);
                        chessBoardBlocks.get(i).setPiece(null);

                        draggedPieceInitialLocation.x = pieceRectangle.x;
                        draggedPieceInitialLocation.y = pieceRectangle.y;

                        dragging = true;
                        chessboard.repaint();
                    }
                    break;
                }
            }
        }
    }

    @Override
    public void mouseReleased(MouseEvent me) {

        ArrayList<ChessboardBlock> chessBoardBlocks = chessboard.getChessBoardBlocks();
        for (int i = 0; i < chessBoardBlocks.size(); i++) {
            pieceRectangle = chessBoardBlocks.get(i).getBounds();
            if (pieceRectangle.contains(me.getPoint())) {
                if (draggedChessPiece != null) {
                    chessPiecePlaced(draggedChessPiece, chessBoardBlocks.get(i));
                }
            }
        }
        dragging = false;
        draggedChessPiece = null;
        chessboard.repaint();
    }

    @Override
    public void mouseDragged(MouseEvent me) {
        dragging = true;
        pieceRectangle.x = me.getX() - (pressedPoint.x - draggedPieceInitialLocation.x);
        pieceRectangle.y = me.getY() - (pressedPoint.y - draggedPieceInitialLocation.y);
        chessboard.repaint();
    }

    boolean isDragging() {
        return dragging;
    }

    abstract boolean chessPieceSelected(ChessPiece chessPiece, ChessboardBlock cb);

    abstract void chessPiecePlaced(ChessPiece chessPiece, ChessboardBlock cb);

    void setChessboard(Chessboard chessBoard) {
        this.chessboard = chessBoard;
    }
}
于 2013-01-31T13:00:42.217 回答
0

首先,您有new GridLayout(BRICKS/ ROWS, 0)这表明您正在将布局设置为具有 0 列。(API 规定GridLayout(int rows, int cols)

至于找到的问题x, y coords,你不需要。如果您有占位符(即自定义标签),您可以将背景颜色设置为对应于板单元格并将图像保存在单元格中。可以将图像设置在背景之上,以实现国际象棋的外观和感觉。在标签上有点击事件,这样当用户点击标签时,你需要做任何你需要做的事情(将一块移到/从一个单元格移到另一个单元格,玩家拿一块,检查棋盘是否有配对/检查配对等.)

您可以在标签上实现MouseListener'smousePressedmouseReleased方法以获得所需的开始和结束标签,如果您想要拖放功能,可以实现MouseMotionListener'smouseDragged方法和paint板的自定义方法(不是标签)。

于 2013-01-31T09:34:57.127 回答