use of tel.discord.rtab.board.Game in project RtaB6 by Telnaior.
the class GameController method displayBoardAndStatus.
public void displayBoardAndStatus(boolean printBoard, boolean totals, boolean copyToResultChannel) {
if (gameStatus == GameStatus.SIGNUPS_OPEN) {
// No board to display if the game isn't running!
return;
}
StringBuilder board = new StringBuilder().append("```\n");
// Board doesn't need to be displayed if game is over
if (printBoard) {
// Do we need a complex header, or should we use the simple one?
int boardWidth = Math.max(5, players.size() + 1);
if (boardWidth < 6)
board.append(" RtaB \n");
else {
for (int i = 7; i <= boardWidth; i++) {
// One space for odd numbers, two spaces for even numbers
board.append(i % 2 == 0 ? " " : " ");
}
// Then print the first part
board.append("Race to ");
// Extra space if it's odd
if (boardWidth % 2 == 1)
board.append(" ");
// Then the rest of the header
board.append("a Billion\n");
}
for (int i = 0; i < boardSize; i++) {
board.append(pickedSpaces[i] ? " " : String.format("%02d", (i + 1)));
board.append((i % boardWidth) == (boardWidth - 1) ? "\n" : " ");
}
board.append("\n");
}
// Next the status line
// Start by getting the lengths so we can pad the status bars appropriately
// Add one extra to name length because we want one extra space between name and cash
int nameLength = players.get(0).getName().length();
for (int i = 1; i < players.size(); i++) nameLength = Math.max(nameLength, players.get(i).getName().length());
nameLength++;
// And ignore the negative sign if there is one
int moneyLength;
if (totals) {
moneyLength = String.valueOf(Math.abs(players.get(0).money)).length();
for (int i = 1; i < players.size(); i++) moneyLength = Math.max(moneyLength, String.valueOf(Math.abs(players.get(i).money)).length());
} else {
moneyLength = String.valueOf(Math.abs(players.get(0).getRoundDelta())).length();
for (int i = 1; i < players.size(); i++) moneyLength = Math.max(moneyLength, String.valueOf(Math.abs(players.get(i).getRoundDelta())).length());
}
// Make a little extra room for the commas
moneyLength += (moneyLength - 1) / 3;
// Then start printing - including pointer if currently their turn
for (int i = 0; i < players.size(); i++) {
board.append(currentTurn == i ? "> " : " ");
board.append(String.format("%-" + nameLength + "s", players.get(i).getName()));
// Now figure out if we need a negative sign, a space, or neither
int playerMoney = players.get(i).getRoundDelta();
// What sign to print?
board.append(playerMoney < 0 ? "-" : "+");
// Then print the money itself
board.append(String.format("$%," + moneyLength + "d", Math.abs(playerMoney)));
// Now the booster display
switch(players.get(i).status) {
case ALIVE:
case DONE:
// If they're alive, display their booster
board.append(String.format(" [%3d%%", players.get(i).booster));
// If it's endgame, show their winstreak afterward
if (players.get(i).status == PlayerStatus.DONE || (gameStatus == GameStatus.END_GAME && currentTurn == i))
board.append(String.format("x%1$d.%2$d", players.get(i).winstreak / 10, players.get(i).winstreak % 10));
else // Otherwise, display whether or not they have a peek
if (players.get(i).peeks > 0)
board.append("P");
else
board.append(" ");
// Then close off the bracket
board.append("]");
break;
case OUT:
case FOLDED:
board.append(" [OUT] ");
break;
case WINNER:
board.append(" [WIN] ");
}
// If they have any games, print them too
if (players.get(i).games.size() > 0) {
board.append(" {");
for (Game minigame : players.get(i).games) {
board.append(" " + minigame.getShortName());
}
board.append(" }");
}
board.append("\n");
// If we want the totals as well, do them on a second line
if (totals) {
// Get to the right spot in the line
for (int j = 0; j < (nameLength - 4); j++) board.append(" ");
board.append("Total:");
// Print sign
board.append(players.get(i).money < 0 ? "-" : " ");
// Then print the money itself
board.append("$");
board.append(String.format("%," + moneyLength + "d\n\n", Math.abs(players.get(i).money)));
}
}
// Close it off and print it out
board.append("```");
channel.sendMessage(board.toString()).queue();
if (copyToResultChannel && resultChannel != null)
resultChannel.sendMessage(board.toString()).queue();
}
use of tel.discord.rtab.board.Game in project RtaB6 by Telnaior.
the class GameController method saveData.
private void saveData() {
try {
List<String> list = Files.readAllLines(Paths.get("scores", "scores" + channel.getId() + ".csv"));
// Go through each player in the game to update their stats
for (int i = 0; i < players.size(); i++) {
/*
* Special case - if you lose the round with $1B you get bumped to $999,999,999
* so that an elimination without penalty (eg bribe) doesn't get you declared champion
* This is since you haven't won yet, after all (and it's *extremely* rare to win a round without turning a profit)
* Note that in the instance of a final showdown, both players are temporarily labelled champion
* But after the tie is resolved, one will be bumped back to $900M
*/
if (players.get(i).money == 1_000_000_000 && players.get(i).status != PlayerStatus.DONE)
players.get(i).money--;
// Send messages based on special status
if (// Out of newbie protection
players.get(i).newbieProtection == 1)
channel.sendMessage(players.get(i).getSafeMention() + ", your newbie protection has expired. " + "From now on, your base bomb penalty will be $250,000.").queue();
if (players.get(i).totalLivesSpent % 5 == 0 && players.get(i).getEnhanceCap() > players.get(i).enhancedGames.size()) {
// Just earned an enhancement (or spent 5 lives with an open slot - we don't want to remind them every game)
if (players.get(i).isBot) {
/* Bots need to pick a minigame to enhance on their own, so we do that now
* But first, check to make sure there is a minigame to put in that slot
* (In ultra-low base-multiplier seasons, this might actually be an issue)
* (It'd take roughly 3000 lives spent though)
*/
int enhanceableGames = 0;
for (Game next : Game.values()) if (next.getWeight(players.size()) > 0)
enhanceableGames++;
if (players.get(i).enhancedGames.size() < enhanceableGames) {
Game chosenGame;
do {
chosenGame = Board.generateSpaces(1, players.size(), Game.values()).get(0);
} while (// Reroll until we find one they haven't already done
players.get(i).enhancedGames.contains(chosenGame));
players.get(i).enhancedGames.add(chosenGame);
channel.sendMessage(players.get(i).getName() + " earned an enhancement slot and chose to enhance " + chosenGame.getName() + "!").queue();
}
} else
channel.sendMessage(players.get(i).getSafeMention() + ", you have earned an enhancement slot! " + "Use the !enhance command to pick a minigame to enhance.").queue();
}
// Find if they already exist in the savefile, and where
String[] record;
int location = -1;
for (int j = 0; j < list.size(); j++) {
record = list.get(j).split("#");
if (record[0].compareToIgnoreCase(players.get(i).uID) == 0) {
location = j;
break;
}
}
// Then build their record and put it in the right place
StringBuilder toPrint = new StringBuilder();
toPrint.append(players.get(i).uID);
toPrint.append("#" + players.get(i).getName());
toPrint.append("#" + players.get(i).money);
toPrint.append("#" + players.get(i).booster);
toPrint.append("#" + players.get(i).winstreak);
toPrint.append("#" + Math.max(players.get(i).newbieProtection - 1, 0));
toPrint.append("#" + players.get(i).lives);
toPrint.append("#" + players.get(i).lifeRefillTime);
toPrint.append("#" + players.get(i).hiddenCommand);
toPrint.append("#" + players.get(i).boostCharge);
toPrint.append("#" + players.get(i).annuities);
toPrint.append("#" + players.get(i).totalLivesSpent);
toPrint.append("#" + players.get(i).enhancedGames);
// If they already exist in the savefile then replace their record, otherwise add them
if (location == -1)
list.add(toPrint.toString());
else
list.set(location, toPrint.toString());
// Update their player level if relevant
if (playersLevelUp) {
PlayerLevel playerLevelData = new PlayerLevel(channel.getGuild().getId(), players.get(i).uID, players.get(i).getName());
boolean levelUp = playerLevelData.addXP(players.get(i).money - players.get(i).originalMoney);
if (levelUp)
channel.sendMessage(players.get(i).getSafeMention() + " has achieved Level " + playerLevelData.getTotalLevel() + "!").queue();
playerLevelData.saveLevel();
}
// Update a player's role if it's the role channel, they're human, and have earned a new one
if (players.get(i).money / 100_000_000 != players.get(i).currentCashClub && !players.get(i).isBot && rankChannel) {
// Get the mod controls
Guild guild = channel.getGuild();
List<Role> rolesToAdd = new LinkedList<>();
List<Role> rolesToRemove = new LinkedList<>();
// Remove their old score role if they had one
if (players.get(i).originalMoney / 100_000_000 > 0 && players.get(i).originalMoney / 100_000_000 < 10)
rolesToRemove.addAll(guild.getRolesByName(String.format("$%d00M", players.get(i).originalMoney / 100_000_000), false));
else // Special case for removing Champion role in case of final showdown
if (players.get(i).originalMoney / 100_000_000 == 10)
rolesToRemove.addAll(guild.getRolesByName("Champion", false));
// Add their new score role if they deserve one
if (players.get(i).money / 100_000_000 > 0 && players.get(i).money / 100_000_000 < 10)
rolesToAdd.addAll(guild.getRolesByName(String.format("$%d00M", players.get(i).money / 100_000_000), false));
else // Or do fancy stuff for the Champion
if (players.get(i).money / 100_000_000 == 10)
rolesToAdd.addAll(guild.getRolesByName("Champion", false));
// Then add/remove appropriately
guild.modifyMemberRoles(players.get(i).member, rolesToAdd, rolesToRemove).queue();
}
}
// Then sort and rewrite it
list.sort(new DescendingScoreSorter());
Path file = Paths.get("scores", "scores" + channel.getId() + ".csv");
Path oldFile = Files.move(file, file.resolveSibling("scores" + channel.getId() + "old.csv"));
Files.write(file, list);
Files.delete(oldFile);
} catch (IOException e) {
System.err.println("Could not save data in " + channel.getName());
e.printStackTrace();
}
}
use of tel.discord.rtab.board.Game in project RtaB6 by Telnaior.
the class EnhanceCommand method execute.
@Override
protected void execute(CommandEvent event) {
// Check if they just want the list
if (event.getArgs().equalsIgnoreCase("list")) {
sendEnhanceList(event);
return;
}
// Next check if they've picked a game to enhance
String gameName = event.getArgs();
// Run through the list of games to find the one they asked for
for (Game game : Game.values()) {
if (gameName.equalsIgnoreCase(game.getShortName()) || gameName.equalsIgnoreCase(game.getName())) {
enhanceGame(event, game);
return;
}
}
// If they don't seem to be enhancing a minigame, just send them their status
// Start by checking to see if they're in-game, and read from their player-file instead
Player player = null;
// Find the channel
GameController controller = null;
for (GameController next : RaceToABillionBot.game) if (next.channel.equals(event.getChannel())) {
controller = next;
break;
}
if (controller == null) {
event.reply("This command must be used in a game channel.");
return;
}
for (Player next : controller.players) if (next.uID.equals(event.getAuthor().getId())) {
player = next;
break;
}
// If they aren't in-game, get their data by generating their player object
if (player == null) {
player = new Player(event.getMember(), controller, null);
}
// Now let's start building up the reply message
StringBuilder output = new StringBuilder();
// List their enhance slot status
output.append("```\n" + player.getName() + "'s Enhanced Minigames:\n");
boolean emptySlots = false;
for (int i = 0; i < player.getEnhanceCap(); i++) {
if (i < player.enhancedGames.size()) {
output.append(" (*) ");
output.append(player.enhancedGames.get(i).getName());
} else {
output.append(" ( ) Empty Slot");
emptySlots = true;
}
output.append("\n");
}
int livesToNewSlot = (25 * (player.getEnhanceCap() + 1) * (player.getEnhanceCap() + 2) / 2) - player.totalLivesSpent;
if (player.newbieProtection > 0)
output.append(" (Finish your newbie protection, then use " + livesToNewSlot + " lives to open a new slot)\n\n");
else
output.append(" (Use " + livesToNewSlot + " more lives to open a new slot)\n\n");
output.append("Type '!enhance list' to see the list of available enhancements.\n");
if (emptySlots)
output.append("Type '!enhance' followed by a minigame's name to permanently enhance that minigame.\n");
output.append("```");
event.reply(output.toString());
}
use of tel.discord.rtab.board.Game in project RtaB6 by Telnaior.
the class EnhanceCommand method enhanceGame.
void enhanceGame(CommandEvent event, Game game) {
// First of all, is the game actually in this season?
if (game.getWeight(4) <= 0) {
event.reply("That minigame is not available this season.");
return;
}
// Find the channel
GameController controller = null;
for (GameController next : RaceToABillionBot.game) if (next.channel.equals(event.getChannel())) {
controller = next;
break;
}
if (controller == null) {
event.reply("This command must be used in a game channel.");
return;
}
// Check that they're in game currently, or that there's no game running
if (controller.players.size() <= 0) {
// If there's no game running, find them in the savefile
try {
List<String> list = Files.readAllLines(Paths.get("scores", "scores" + event.getChannel().getId() + ".csv"));
int index = findUserInList(list, event.getAuthor().getId(), false);
if (index < 0 || index >= list.size()) {
event.reply("You currently have no open enhance slots.");
return;
}
String[] record = list.get(index).split("#");
/*
* record[11] = total lives spent
* record[12] = list of enhanced minigames
* (this is copied directly from the player initialisation file)
*/
int totalLivesSpent = Integer.parseInt(record[11]);
ArrayList<Game> enhancedGames = new ArrayList<Game>();
// Remove the brackets
String savedEnhancedGames = record[12].substring(1, record[12].length() - 1);
String[] enhancedList = savedEnhancedGames.split(",");
if (enhancedList[0].length() > 0)
for (int j = 0; j < enhancedList.length; j++) enhancedGames.add(Game.valueOf(enhancedList[j].trim()));
// Do the obvious checks
if (RtaBMath.getEnhanceCap(totalLivesSpent) <= enhancedGames.size()) {
event.reply("You currently have no open enhance slots.");
return;
}
for (Game nextGame : enhancedGames) {
if (game == nextGame) {
event.reply("You have already enhanced that minigame.");
return;
}
}
// Enhance it!
enhancedGames.add(game);
event.reply("Minigame enhanced!");
// Now replace the record in the list
StringBuilder updatedLine = new StringBuilder();
for (int i = 0; i < 11; i++) {
updatedLine.append(record[i]);
updatedLine.append("#");
}
updatedLine.append(totalLivesSpent);
updatedLine.append("#");
updatedLine.append(enhancedGames.toString());
list.set(index, updatedLine.toString());
// And save it
Path file = Paths.get("scores", "scores" + event.getChannel().getId() + ".csv");
Path oldFile = Files.move(file, file.resolveSibling("scores" + event.getChannel().getId() + "old.csv"));
Files.write(file, list);
Files.delete(oldFile);
} catch (IOException e) {
e.printStackTrace();
}
return;
}
boolean playerFound = false;
for (Player next : controller.players) if (next.uID.equals(event.getAuthor().getId())) {
playerFound = true;
if (next.getEnhanceCap() <= next.enhancedGames.size()) {
event.reply("You currently have no open enhance slots.");
return;
}
for (Game nextGame : next.enhancedGames) {
if (game == nextGame) {
event.reply("You have already enhanced that minigame.");
return;
}
}
// Yay they actually met all the conditions was that so hard
next.enhancedGames.add(game);
event.reply("Minigame enhanced!");
}
if (!playerFound) {
event.reply("There is a game currently in progress; please wait until it is finished to enhance.");
return;
}
}
use of tel.discord.rtab.board.Game in project RtaB6 by Telnaior.
the class MinigamesForAll method execute.
@Override
public void execute(GameController game, int player) {
// Small chance in large games of the space mutating, capping at 10% in 16p
if (Math.random() * 100 < game.playersAlive - 6) {
game.channel.sendMessage("It's **Minigame For... One?!**").queue();
Game chosenGame = game.generateEventMinigame(player);
for (int i = 0; i < game.playersAlive; i++) {
game.players.get(player).games.add(chosenGame);
game.channel.sendMessage(game.players.get(player).getSafeMention() + " receives a copy of **" + chosenGame.getName() + "**!").queue();
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
game.players.get(player).games.sort(null);
game.players.get(player).minigameLock = true;
game.channel.sendMessage("Minigame Lock applied to " + game.players.get(player).getSafeMention() + ".").queue();
} else {
game.channel.sendMessage("It's **Minigames For All**! All players remaining receive a minigame!").queue();
for (int i = 0; i < game.players.size(); i++) {
Player nextPlayer = game.players.get(i);
if (nextPlayer.status == PlayerStatus.ALIVE) {
Game chosenGame = game.generateEventMinigame(i);
game.players.get(i).games.add(chosenGame);
game.players.get(i).games.sort(null);
game.channel.sendMessage(nextPlayer.getSafeMention() + " receives a copy of **" + chosenGame.getName() + "**!").queue();
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
Aggregations