我有一个学校遗留的项目,无法按预期工作。该课程有一个Connect4文字游戏,然后是一个GUI(使用JavaFX),然后是它的服务器-客户端。
我的独立GUI会一直持续到玩家赢得游戏为止,但是如果绿色获胜,它会在那一刻崩溃(错误消息很长,但似乎以与Java的Parent类有关的IllegalArgumentException结尾)
我也不知道为此进行JavaFX服务器交互是否可行,或者我是否应该报废并摇摆,但我真的想让此工作为我的安心。现在,我在为后端取胜和GUI逻辑的想法而苦苦挣扎,但这是我可以在这种程度上工作的唯一设计,因为它本身就是糟糕的设计...
请让我知道是否需要更多信息,我知道该程序是一团糟,因为我以前没有做过GUI,因此恐怕在修复该程序之前先对其进行清理。源文件很长,但错误似乎与父对象的非法参数异常有关。
@Override
public void start(Stage primaryStage)
{
GridPane rectangleRoot = new GridPane();
GridPane circleRoot = new GridPane();
makeCircleBoard(rectangleRoot, circleRoot, playerColor);
rectangleRoot.setAlignment(Pos.CENTER);
circleRoot.setAlignment(Pos.CENTER);
Scene scene = new Scene(rectangleRoot, 1000, 1000);
Rectangle gameBoardSpace = new Rectangle(scene.getWidth() / 2, scene.getHeight()
/2, Color.DARKBLUE);
rectangleRoot.getChildren().add(gameBoardSpace);
rectangleRoot.getChildren().add(circleRoot);
primaryStage.setTitle("Connect4");
primaryStage.setScene(scene);
primaryStage.show();
}
public GridPane makeCircleBoard(GridPane rectangleRoot, GridPane circleRoot, String colorPassed)
{
int rowPerCol[] = new int[7]; //for back end 2D array
int turn = 1; //game logic
for(int i = 0; i < ROWMAX; i++)
{
for(int j = 0; j < COLMAX; j++)
{
gridLayout[i][j] = ' ';
}
}
for(int row = 0; row < 6; row++)
{
for(int col = 0; col < 7; col++)
{
GameSlot newCircle = new GameSlot(30, Color.WHITE);
newCircle.setStrokeType(StrokeType.OUTSIDE);
newCircle.setStroke(Color.web("black", 1.0));
newCircle.setStrokeWidth(4);
newCircle.setLocationRow(row);
newCircle.setLocationCol(col);
newCircle.setOnMouseClicked(new EventHandler<MouseEvent>()
{
@Override
public void handle(MouseEvent e)
{
if(newCircle.getOccupied() == false)
{
if(playerColor.equals("Yellow"))
{
gridLayout[newCircle.getLocationRow()][newCircle.getLocationCol()] = 'Y';
playerColor = "Green";
newCircle.setFill(Color.YELLOW);
newCircle.setOccupiedTrue();
}
else
{
gridLayout[newCircle.getLocationRow()][newCircle.getLocationCol()] = 'G';
playerColor = "Yellow";
newCircle.setFill(Color.GREEN);
newCircle.setOccupiedTrue();
}
}
if(gameWon(gridLayout))
{
if(playerColor.equals("Green"))
{
final Text actiontarget = new Text();
actiontarget.setFill(Color.CRIMSON);;
actiontarget.setText("YELLOW WON!!!");
actiontarget.setScaleX(10);
actiontarget.setScaleY(10);
actiontarget.setTranslateX(rectangleRoot.getWidth() / 5);
rectangleRoot.getChildren().add(actiontarget);
}
else
{
final Text actiontarget = new Text();
actiontarget.setFill(Color.CRIMSON);;
actiontarget.setText("GREEN WON!!!");
rectangleRoot.getChildren().add(actiontarget);
actiontarget.setScaleX(10);
actiontarget.setScaleY(10);
actiontarget.setTranslateX(rectangleRoot.getWidth() / 5);
rectangleRoot.getChildren().add(actiontarget);
}
}
} //end handle()
});
//circle.setId(Integer.toString(i));
circleRoot.add(newCircle, row, col);
//newCircle.isWon(row, col);
}
}
绿色和黄色的检查相同。它检查与下一个向上的颜色相反的颜色字符的不同方向。在任何获胜条件下,我都看不到Yellow的错误,并且在gridLayout2中进行了索引检查。
Exception in thread "JavaFX Application Thread"
java.lang.IllegalArgumentException: Children: duplicate children added: parent = Grid hgap=0.0, vgap=0.0, alignment=CENTER
at javafx.scene.Parent$2.onProposedChange(Parent.java:454)
at com.sun.javafx.collections.VetoableListDecorator.add(VetoableListDecorator.java:206)
at Connect4.ui.Connect4GUI$1.handle(Connect4GUI.java:128)
at Connect4.ui.Connect4GUI$1.handle(Connect4GUI.java:1)
at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:86)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:238)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:191)
at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:59)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:58)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:74)
at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:54)
at javafx.event.Event.fireEvent(Event.java:198)
at javafx.scene.Scene$ClickGenerator.postProcess(Scene.java:3470)
at javafx.scene.Scene$ClickGenerator.access$8100(Scene.java:3398)
at javafx.scene.Scene$MouseHandler.process(Scene.java:3766)
at javafx.scene.Scene$MouseHandler.access$1500(Scene.java:3485)
at javafx.scene.Scene.impl_processMouseEvent(Scene.java:1762)
at javafx.scene.Scene$ScenePeerListener.mouseEvent(Scene.java:2494)
at com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(GlassViewEventHandler.java:381)
at com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(GlassViewEventHandler.java:295)
at java.security.AccessController.doPrivileged(Native Method)
at com.sun.javafx.tk.quantum.GlassViewEventHandler.lambda$handleMouseEvent$353(GlassViewEventHandler.java:417)
at com.sun.javafx.tk.quantum.QuantumToolkit.runWithoutRenderLock(QuantumToolkit.java:389)
at com.sun.javafx.tk.quantum.GlassViewEventHandler.handleMouseEvent(GlassViewEventHandler.java:416)
at com.sun.glass.ui.View.handleMouseEvent(View.java:555)
at com.sun.glass.ui.View.notifyMouse(View.java:937)
at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
at com.sun.glass.ui.win.WinApplication.lambda$null$147(WinApplication.java:177)
at java.lang.Thread.run(Thread.java:748)
答案 0 :(得分:0)
您得到的错误是一个IllegalArgumentException
,它表示您试图多次向同一个Node
中添加一个Parent
,这在JavaFX中是不允许的。如果您查看堆栈跟踪,就会看到代码在哪里发生。
java.lang.IllegalArgumentException: Children: duplicate children added: parent = Grid hgap=0.0, vgap=0.0, alignment=CENTER
at javafx.scene.Parent$2.onProposedChange(Parent.java:454)
at com.sun.javafx.collections.VetoableListDecorator.add(VetoableListDecorator.java:206)
at Connect4.ui.Connect4GUI$1.handle(Connect4GUI.java:128)
at Connect4.ui.Connect4GUI$1.handle(Connect4GUI.java:1)
不是内部JavaFX代码的第一帧是Connect4.ui.Connect4GUI$1.handle(Connect4GUI.java:128)
,它表明错误发生在您的128
类的行Connect4GUI
内的一个名为handle
的方法中。您没有指定第128
行是什么行,而是基于您的代码和我们知道的以上信息,我们将重点放在代码的这一部分:
newCircle.setOnMouseClicked(new EventHandler<MouseEvent>()
{
@Override
public void handle(MouseEvent e)
{
if(newCircle.getOccupied() == false)
{
if(playerColor.equals("Yellow"))
{
gridLayout[newCircle.getLocationRow()][newCircle.getLocationCol()] = 'Y';
playerColor = "Green";
newCircle.setFill(Color.YELLOW);
newCircle.setOccupiedTrue();
}
else
{
gridLayout[newCircle.getLocationRow()][newCircle.getLocationCol()] = 'G';
playerColor = "Yellow";
newCircle.setFill(Color.GREEN);
newCircle.setOccupiedTrue();
}
}
if(gameWon(gridLayout))
{
if(playerColor.equals("Green"))
{
final Text actiontarget = new Text();
actiontarget.setFill(Color.CRIMSON);;
actiontarget.setText("YELLOW WON!!!");
actiontarget.setScaleX(10);
actiontarget.setScaleY(10);
actiontarget.setTranslateX(rectangleRoot.getWidth() / 5);
rectangleRoot.getChildren().add(actiontarget);
}
else
{
final Text actiontarget = new Text();
actiontarget.setFill(Color.CRIMSON);;
actiontarget.setText("GREEN WON!!!");
rectangleRoot.getChildren().add(actiontarget);
actiontarget.setScaleX(10);
actiontarget.setScaleY(10);
actiontarget.setTranslateX(rectangleRoot.getWidth() / 5);
rectangleRoot.getChildren().add(actiontarget);
}
}
} //end handle()
});
查看代码,可以将问题放在else
块内的if(gameWon(gridLayout))
块内:
else
{
final Text actiontarget = new Text();
actiontarget.setFill(Color.CRIMSON);;
actiontarget.setText("GREEN WON!!!");
rectangleRoot.getChildren().add(actiontarget); // DUPLICATE LINE BELOW
actiontarget.setScaleX(10);
actiontarget.setScaleY(10);
actiontarget.setTranslateX(rectangleRoot.getWidth() / 5);
rectangleRoot.getChildren().add(actiontarget); // DUPLICATE: Must be line 128
}
删除这些语句之一,代码不应再抛出IllegalArgumentException
。请注意,顺便说一句,堆栈跟踪将您直接指向了有害的代码行。