java - JButton 和 ActionListener 导致许多运行时错误
问题描述
所以我正在尝试使用 Eclipse 和 JSwing 制作康威生命游戏的一个版本,我的问题是当我尝试启动代码以运行一代时,它会产生大量运行时错误当我尝试按下我目前用作下一代模拟的开始按钮的第一个 JButton。Cell 类只是其当前状态及其在按钮数组中的位置的一组 setter 和 getter,当我按下第一个按钮时发生的错误列表位于代码下方
public class MainPage extends JFrame implements ActionListener{
JButton[] screen = new JButton[2500];
JButton start = new JButton("Start");
Cell[] cells = new Cell[2500];
int select = 0;
public static void main(String args[]) {
new MainPage();
}
public MainPage() {
super("The Game Of Life");
int k = 0;
while (k < 2500) {
screen[k] = new JButton("");
screen[k].setBackground(Color.BLACK);
cells[k] = new Cell(k);
cells[k].setState(0);
k++;
}
Container surface = this.getContentPane();
surface.setLayout(new GridLayout(50,50));
// k == row j == col
for (int i = 0; i < 2500; i++) {
int finalI = i; // no final modifier
surface.add(screen[i]);
screen[i].addActionListener(e -> {
Color color = screen[finalI].getBackground();
if (color == Color.BLACK)
{
screen[finalI].setBackground(Color.WHITE);
cells[finalI].setState(1);
}
else {
screen[finalI].setBackground(Color.BLACK);
cells[finalI].setState(0);
}
});
screen[0].addActionListener(this);
}
this.pack();
this.setVisible(true);
}
public void setnewstates() {
int k = 51;
int screensize = 50;
while (k < 2500 || k > 50 || k % 50 != 0 || (k + 1) % 50 != 0) // avoid borders for now
{
int neighbors = 0;
int state = cells[k].getState();
neighbors = cells[k - 1].getState() + neighbors; // check neighbors
neighbors = cells[k + 1].getState() + neighbors;
neighbors = cells[k + screensize].getState() + neighbors;
neighbors = cells[k - screensize].getState() + neighbors;
neighbors = cells[k + screensize + 1].getState() + neighbors;
neighbors = cells[k + screensize - 1].getState() + neighbors;
neighbors = cells[k - screensize - 1].getState() + neighbors;
neighbors = cells[k - screensize + 1].getState() + neighbors;
if (state == 1) {
if (neighbors < 2)
{
cells[k].setState(0);
screen[k].setBackground(Color.BLACK);
}
if (neighbors > 3)
{
cells[k].setState(0);
screen[k].setBackground(Color.BLACK);
}
}
else if (state == 0) {
if (neighbors == 3)
{
cells[k].setState(1);
screen[k].setBackground(Color.WHITE);
}
}
k++;
}
}
public void actionPerformed(ActionEvent e) {
if (e.getSource() == screen[0])
{
setnewstates();
}
}
}
这是我按下第一个按钮时发生的错误
Exception in thread "AWT-EventQueue-0" java.lang.ArrayIndexOutOfBoundsException: -1
at MainPage.setnewstates(MainPage.java:72)
at MainPage.actionPerformed(MainPage.java:106)
at javax.swing.AbstractButton.fireActionPerformed(Unknown Source)
at javax.swing.AbstractButton$Handler.actionPerformed(Unknown Source)
at javax.swing.DefaultButtonModel.fireActionPerformed(Unknown Source)
at javax.swing.DefaultButtonModel.setPressed(Unknown Source)
at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(Unknown Source)
at java.awt.Component.processMouseEvent(Unknown Source)
at javax.swing.JComponent.processMouseEvent(Unknown Source)
at java.awt.Component.processEvent(Unknown Source)
at java.awt.Container.processEvent(Unknown Source)
at java.awt.Component.dispatchEventImpl(Unknown Source)
at java.awt.Container.dispatchEventImpl(Unknown Source)
at java.awt.Component.dispatchEvent(Unknown Source)
at java.awt.LightweightDispatcher.retargetMouseEvent(Unknown Source)
at java.awt.LightweightDispatcher.processMouseEvent(Unknown Source)
at java.awt.LightweightDispatcher.dispatchEvent(Unknown Source)
at java.awt.Container.dispatchEventImpl(Unknown Source)
at java.awt.Window.dispatchEventImpl(Unknown Source)
at java.awt.Component.dispatchEvent(Unknown Source)
at java.awt.EventQueue.dispatchEventImpl(Unknown Source)
at java.awt.EventQueue.access$500(Unknown Source)
at java.awt.EventQueue$3.run(Unknown Source)
at java.awt.EventQueue$3.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(Unknown Source)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(Unknown Source)
at java.awt.EventQueue$4.run(Unknown Source)
at java.awt.EventQueue$4.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(Unknown Source)
at java.awt.EventQueue.dispatchEvent(Unknown Source)
at java.awt.EventDispatchThread.pumpOneEventForFilters(Unknown Source)
at java.awt.EventDispatchThread.pumpEventsForFilter(Unknown Source)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(Unknown Source)
at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
at java.awt.EventDispatchThread.run(Unknown Source)
解决方案
在setnewstates()
中,首先设置 k=0,然后在 while 循环中做的第一件事就是引用cells[k - screensize - 1]
例如:
int neighbors = 0;
int state = cells[k].getState();
if (k > 0) neighbors = cells[k - 1].getState() + neighbors; // check neighbors
if (k < 2500) neighbors = cells[k + 1].getState() + neighbors;
if (k + screensize < 2500) neighbors = cells[k + screensize].getState() + neighbors;
只是一个想法:使用一维数组让你的生活变得非常困难。生活是在二维网格上播放的(你有 50x50),所以我建议你尝试使用二维数组 [50][50]。
推荐阅读
- css - 我的折叠菜单列表未显示在其父级之外。菜单列表扩展了父级,但不是每个菜单中的列表
- php - 多次插入数据
- python - pyYAML 中的自定义转储程序
- python - 错误是 exec(compile(f.read(), filename, 'exec'), namespace) 。第 26 行 ---- def__init__(self, battery_size = 70):
- java - 如何将 .crt 文件添加到密钥库和信任库
- r - 如何将 R 中的过滤子集保存在新列中?
- python - 从 0 到 n 每隔一个整数相加(递归函数)
- c++ - 未知大小的数组作为类成员,用于在运行时制作数组对象(对象创建时)
- apache-flink - 对随机数源中的数字求和
- xamarin - 服务运行一次......然后再也不会