I'm in a computer science class, and am making a Monopoly program on my own time for fun. All was going well until about an hour ago, when I came across some bugs I cannot explain.
The first has to do with Eclipse. If I try to debug my program, it crashes with a NullPointerException. However, I cannot for the life of me figure out why that NullPointerException ever occurs. If I export the project to a JAR file and run it, I have no trouble at all with it. The line in question is:cPrinter.println("╔═════════╦═════════╤═════════╤═════════╤═════════╤═════════╤═════════╤═════════╤═════════╤═════════╦═════════╗", Attribute.NONE, FColor.WHITE, BColor.NONE);
(cPrinter is an instance of the class print.Color.ColoredPrinter, from the JCDP library.)
Google only returns results for the opposite - programs running in Eclipse, but not in JAR files.
I am using proper parameters for the constructor, and it works in Windows command prompt as a JAR file if I change the type to ColorPrinterWIN (although since command prompt does not display UTF-8 characters it shows up as a bunch of ?'s).
Edit: On time, Eclipse gave me this debugging info:
Exception in thread "main" java.lang.NullPointerException
at MonopolyBoardDraw.drawBoard(MonopolyBoardDraw.java:35)
at MonopolyLaunch.main(MonopolyLaunch.java:76)
FATAL ERROR in native method: JDWP on checking for an interface, jvmtiError=JVMTI_ERROR_WRONG_PHASE(112)
JDWP exit error JVMTI_ERROR_WRONG_PHASE(112): on checking for an interface [util.c:1313]
A fatal error has been detected by the Java Runtime Environment:
EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0000000072cf2868, pid=14860, tid=13652
JRE version: Java(TM) SE Runtime Environment (8.0_66-b18) (build 1.8.0_66-b18)
Java VM: Java HotSpot(TM) 64-Bit Server VM (25.66-b18 mixed mode windows-amd64 compressed oops)
Problematic frame:
Edit 2: Sorry that this bolds for some reason. I do not know why, and I removed the code tags since they did not work properly. There are supposed to be # pound signs at the start of each line that is bolded (besides this one).
The second problem I have come across is a really disturbing logic error.
I could not catch a NullPointerException no matter how many different ways I tried, and I have no clue why. I was trying to determine how many players were in the game.
Each player is an instance of the class MonopolyPlayerManager. Since you cannot create variables not originally written (that is, I cannot create X instances of a class because the user typed X players will be playing), I defined 4 players, but only have 1 actually created according to the constructor's parameters, like this:
public static MonopolyPlayerManager p1;
public static MonopolyPlayerManager p2;
public static MonopolyPlayerManager p3;
public static MonopolyPlayerManager p4;
...
public static void main(String[] args){
...
//createPlayers(players);
System.out.println("[Debug] For debug purposes, there is 1 player, name \"Test\", piece ♜.");
p1 = new MonopolyPlayerManager("Test", "♜", 0); //For testing purposes ONLY! Remove in final builds.
...
}
The constructor is as follows:public MonopolyPlayerManager(String playerName, String playerSymbol, int currentPosition){
....
pID = totalPlayers;
totalPlayers++;
}
The totalPlayers is important, as it is the only way I can determine how many players are actually active without throwing a NullPointerException when trying to check any player's properties (i.e. p2.getName() will return null because p2 was not given a name since it was not constructed).
In the MonopolyPlayerManager class is this method:public static String getPlayersOnSpace(int space){
String r = "";
if(totalPlayers == 1 && MonopolyLaunch.p1.getPosition() == space)
r += MonopolyLaunch.p1.getPiece();
if(totalPlayers == 2 && MonopolyLaunch.p2.getPosition() == space)
r += MonopolyLaunch.p2.getPiece();
if(totalPlayers == 3 && MonopolyLaunch.p3.getPosition() == space)
r += MonopolyLaunch.p3.getPiece();
if(totalPlayers == 4 && MonopolyLaunch.p4.getPosition() == space)
r += MonopolyLaunch.p4.getPiece();
for(int i = 1; i <= 9 - r.length(); i++){ //Fills the rest of the space with spaces.
r += "x";
}
return r;
}
What this does is it makes a 9 character length string, "r". If a player is at that spot, their symbol/piece (a UTF-8 character) is placed there, and the rest is filled with spaces.
Since there is only one player active (p1), and p1 is at position 0 (Go/collect $200), not position 20 (free parking), it should fail for all of these and I should have just 9 spaces, right?
Well, it printed 5 spaces, but just to make sure that my terminal was not resizing the spaces, I changed it to X's. 5 X's were printed.
Even if all 4 players were properly instantiated, they would still be at position 0 (Go) because this is when the board is being drawn for the first time, before they could have moved. Yet it is filling in 5 X's as if there were 4 characters there already. Even if it was inserting null
characters, that still returns a space to the console, which I learned when working on a tic-tac-toe program.
Have I found a crazy logic bug or have I managed to miss something big. I can link you to my BitBucket repo, if you want to examine my code further.
Edit: I formatted my code on here with the spaces the way they should be, but I have no indentations. Sorry that it looks so sloppy, is it more than 4 spaces or is indentation broken?