gpt4 book ai didi

java - 程序添加太多按钮

转载 作者:行者123 更新时间:2023-12-04 13:06:14 24 4
gpt4 key购买 nike

我正在尝试制作一个西洋跳棋游戏,到目前为止所有接缝都很好,但是当我将鼠标悬停在按钮上时,图形出现故障,我不知道为什么。它还在顶部添加了很多按钮,当我移动它(调整大小)时它会添加更多。当我按下任何绿色按钮时,它还会添加更多。它们是顶部非常小的按钮,我看不到它们在我的代码中弹出的位置。

import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class Test {
private JButton Green;
private JButton Blue;

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

public Test() {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
JFrame frame = new JFrame("Checkers");
JPanel contentPane = new JPanel();


GameListener listener = new GameListener() {

@Override
public void gameWasCompleted() {
contentPane.repaint();
}

@Override
public void startNewGame() {
System.out.println("button worked");
contentPane.repaint();
}
};

MainPane mainPane = new MainPane();
mainPane.setGameListener(listener);

contentPane.add(mainPane);

frame.setContentPane(contentPane);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}

public interface GameListener {

void gameWasCompleted();

void startNewGame();
}


public class MainPane extends JPanel implements MouseListener {

private GameListener gameListener;

public MainPane() {
addMouseListener(this);
}

public void setGameListener(GameListener gameListener) {
this.gameListener = gameListener;
}

@Override
public Dimension getPreferredSize() {
return new Dimension(1000, 1000);
}

@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
int xshift;
int yshift = 0;

g.setColor(new Color(0, 0, 0));
for (int i = 0; i < 4; i++) {
xshift = 125;
for (int j = 0; j < 4; j++) {
g.fillRect(xshift, yshift, 125, 125);
xshift += 250;
}
xshift = 0;
yshift += 125;

for (int k = 0; k < 4; k++) {
g.fillRect(xshift, yshift, 125, 125);
xshift += 250;
}
yshift += 125;
}
initalprnt(g);
}



protected void initalprnt(Graphics g) {
int xshift = 125;
int yshift = 0;
g.setColor(new Color(0, 100, 0));

for (int i = 0; i < 3; i++) {
if (i == 2) {
xshift = 125;
}
for (int j = 0; j < 4; j++) {
g.fillOval(xshift, yshift, 125, 125);
Green = new JButton();
Green.setBackground(new Color(0, 100, 0, 0));
Green.setBounds(xshift, yshift, 125, 125);
add(Green);



xshift += 250;
}
xshift = 0;
yshift += 125;
}
yshift += 250;
g.setColor(new Color(0, 0, 100));
for (int k = 0; k < 3; k++) {
if (k == 2) {
xshift = 0;
}
for (int j = 0; j < 4; j++) {
g.fillOval(xshift, yshift, 125, 125);
Blue = new JButton();
Blue.setBackground(new Color(0, 0, 100, 0));
Blue.setBounds(xshift, yshift, 125, 125);
add(Blue);
xshift += 250;
}
xshift = 125;
yshift += 125;
}
buttons();
}

public void buttons() {
Green.addActionListener(e -> {
System.out.println("this does something");
gameListener.startNewGame();
});
Blue.addActionListener(e -> {
System.out.println("this did something");
gameListener.startNewGame();
});
}


public void mouseClicked(MouseEvent e) {}

public void mousePressed(MouseEvent e) {}

public void mouseReleased(MouseEvent e) {}

public void mouseEntered(MouseEvent e) {}

public void mouseExited(MouseEvent e) {}
}

}

最佳答案

基本经验法则,在任何情况下都不要在绘制过程中修改组件(或任何其他组件)的状态。这可能(并且可能会)导致组件重新安排另一个绘制 channel ,您将陷入无限循环。

您“可能”实现这一目标的方法有很多,例如,您可以在 GridLayout 中使用 JButton

然后你需要做的就是设计一个合适的模型和委托(delegate)/观察者工作流来保持 UI 与模型同步

Checkers board

import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.GridLayout;
import java.awt.Point;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.HashMap;
import java.util.Map;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class Test {

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

public Test() {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
JFrame frame = new JFrame();
BoardPane boardPane = new BoardPane();
boardPane.setBoardListener(new BoardListener() {
@Override
public void cellWasSelected(Point p) {
System.out.println("Cell selected " + p);
}
});
frame.add(boardPane);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}

public interface BoardListener {
public void cellWasSelected(Point p);
}

public class BoardPane extends JPanel {

private Map<Point, JButton> cells = new HashMap<>();
private BoardListener boardListener;

public BoardPane() {
int gridSize = 8 * 8;
setLayout(new GridLayout(8, 8));
int index = 0;
for (int row = 0; row < 8; row++) {
int xPos = (row % 2 == 0) ? gridSize : 0;
for (int col = 0; col < 8; col++) {
index++;
JButton btn = new JButton();
btn.setOpaque(true);
btn.setFocusPainted(false);
btn.setBorderPainted(false);
// I'd prefer to rely on something like
// an image, such as an empty image for
// cells which are empty
btn.setPreferredSize(new Dimension(100, 100));
if (index % 2 == 0) {
btn.setBackground(Color.BLACK);
btn.setForeground(Color.WHITE);
} else {
btn.setBackground(Color.WHITE);
btn.setForeground(Color.BLACK);
}
Point p = new Point(col, row);
btn.putClientProperty("cell", p);
cells.put(p, btn);
add(btn);

btn.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
BoardListener listener = getBoardListener();
if (listener == null) {
return;
}
Point p = (Point)btn.getClientProperty("cell");
listener.cellWasSelected(p);
}
});
}
index++;
}
}

public void setBoardListener(BoardListener boardListener) {
this.boardListener = boardListener;
}

public BoardListener getBoardListener() {
return boardListener;
}

}
}

通常,我会使用完全基于组件或基于自定义绘画的解决方案,并避免将两者混用。

请记住,董事会应该只关注董事会需要做的事情,而不应该做任何其他事情。这就是“关注/责任分离”的要点

一个复杂得多的解决方案可能会使用自定义布局来管理自定义绘制(paint)板上的组件,但这远远超出了问题的范围或您此时的能力

关于java - 程序添加太多按钮,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/69322273/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com