mirror of
https://github.com/coding-horror/basic-computer-games.git
synced 2026-02-05 19:32:48 -08:00
Merge branch 'main' of https://github.com/coding-horror/basic-computer-games into war-cpp
This commit is contained in:
174
01 Acey Ducey/perl/aceyducey.pl
Normal file
174
01 Acey Ducey/perl/aceyducey.pl
Normal file
@@ -0,0 +1,174 @@
|
||||
#!/usr/bin/perl
|
||||
|
||||
use strict;
|
||||
use warnings;
|
||||
|
||||
# The List::Util module is part of the core Perl distribution. Using this
|
||||
# means we don't need to re-invent the wheel and create a way to shuffle
|
||||
# a list.
|
||||
use List::Util qw(shuffle);
|
||||
|
||||
# Rather than put in a number of print (or say) statements here, we use a
|
||||
# "here document". This is very useful for long strings of text. In this
|
||||
# case, everything between the end of the "print" line and the line with
|
||||
# "END_INSTRUCTIONS" on it will be printed verbatim.
|
||||
print << 'END_INSTRUCTIONS';
|
||||
|
||||
Acey-Ducey
|
||||
Adapted from Creative Computing, Morristown, New Jersey
|
||||
|
||||
|
||||
Acey-Ducey is played as follows. The dealer (computer) deals two cards face up.
|
||||
You have an option to bet or not bet, depending on whether or not you feel that
|
||||
the next card drawn will have a value between the first two. Aces are low.
|
||||
|
||||
Bets must be in whole-dollar amounts only.
|
||||
|
||||
If you do not want to bet, input a 0. If you want to quit, input a -1.
|
||||
|
||||
END_INSTRUCTIONS
|
||||
|
||||
my @cards = (1 .. 13); # That is, Ace through King.
|
||||
my $keepPlaying = 1;
|
||||
|
||||
GAME:
|
||||
while ($keepPlaying)
|
||||
{
|
||||
my $playerBalance = 100; # The player starts with $100
|
||||
|
||||
HAND:
|
||||
while (1)
|
||||
{
|
||||
print "\nYou now have $playerBalance dollars.\n\n";
|
||||
|
||||
# We'll create a new array that is a shuffled version of the deck.
|
||||
my @shuffledDeck = shuffle(@cards);
|
||||
|
||||
# Then, by taking the two "top cards" off the deck, we're guaranteed
|
||||
# that those will be unique. This way we don't have to keep drawing
|
||||
# if we get, say, two queens. We sort them as we pull them to make
|
||||
# sure that the first card is lower than the second one.
|
||||
my ($firstCard, $secondCard) = sort { $a <=> $b } @shuffledDeck[ 0 .. 1 ];
|
||||
|
||||
print "I drew ", nameOfCard($firstCard), " and ", nameOfCard($secondCard), ".\n";
|
||||
|
||||
my $bet = getValidBet($playerBalance);
|
||||
if ($bet == 0)
|
||||
{
|
||||
print "Chicken!\n\n";
|
||||
next HAND;
|
||||
}
|
||||
|
||||
if ($bet < 0)
|
||||
{
|
||||
last GAME;
|
||||
}
|
||||
|
||||
# Now we re-shuffle the whole deck again and choose a third card.
|
||||
# (Note: This is how the odds get stacked in favor of the dealer since
|
||||
# the third card can be exactly the same as the first or second.)
|
||||
@shuffledDeck = shuffle(@cards);
|
||||
my $thirdCard = $shuffledDeck[0];
|
||||
|
||||
print "I drew ", nameOfCard($thirdCard), "!\n";
|
||||
|
||||
if (($firstCard < $thirdCard) && ($thirdCard < $secondCard))
|
||||
{
|
||||
print "You win!\n\n";
|
||||
$playerBalance += $bet;
|
||||
}
|
||||
else
|
||||
{
|
||||
print "You lose!\n\n";
|
||||
$playerBalance -= $bet;
|
||||
}
|
||||
|
||||
if ($playerBalance <= 0)
|
||||
{
|
||||
print "Sorry, buddy, you blew your wad!\n\n";
|
||||
last HAND;
|
||||
}
|
||||
}
|
||||
|
||||
$keepPlaying = promptUserToKeepPlaying();
|
||||
}
|
||||
|
||||
print "Thanks for playing!\n";
|
||||
|
||||
###############
|
||||
sub getValidBet
|
||||
{
|
||||
my $maxBet = shift;
|
||||
|
||||
print "\nWhat's your bet? ";
|
||||
|
||||
my $input = <STDIN>;
|
||||
chomp $input;
|
||||
|
||||
# This regular expression will validate that the player entered an integer.
|
||||
# The !~ match operate *negates* the match, so if the player did NOT enter
|
||||
# an integer, they'll be given an error and prompted again.
|
||||
if ($input !~ /^ # Match the beginning of the string
|
||||
[+-]? # Optional plus or minus...
|
||||
\d+ # followed by one more more digits...
|
||||
$ # and then the end of the string
|
||||
/x # The x modifier ignores whitespace in this regex...
|
||||
)
|
||||
{
|
||||
print "Sorry, numbers only!\n";
|
||||
$input = getValidBet($maxBet);
|
||||
}
|
||||
|
||||
if ($input > $maxBet)
|
||||
{
|
||||
print "Sorry, my friend, you can't bet more money than you have.\n";
|
||||
print "You only have $maxBet dollars to spend!\n";
|
||||
$input = getValidBet($maxBet);
|
||||
}
|
||||
|
||||
if ($input != int($input))
|
||||
{
|
||||
print "Sorry, you must bet in whole dollars. No change!\n";
|
||||
$input = getValidBet($maxBet);
|
||||
}
|
||||
|
||||
return $input;
|
||||
}
|
||||
|
||||
# Since arrays in Perl are 0-based, we need to convert the value that we drew from
|
||||
# the array to its proper position in the deck.
|
||||
sub nameOfCard
|
||||
{
|
||||
my $value = shift;
|
||||
|
||||
# Note that the Joker isn't used in this game, but since arrays in Perl are
|
||||
# 0-based, it's useful to have something there to represent the "0th"
|
||||
# position. This way the rest of the elements match their expected values
|
||||
# (e.g., element 1 is Ace, element 7 is 7, and element 12 is Queen).
|
||||
|
||||
my @cardlist = qw(Joker Ace 2 3 4 5 6 7 8 9 10 Jack Queen King);
|
||||
return $cardlist[$value];
|
||||
}
|
||||
|
||||
sub promptUserToKeepPlaying
|
||||
{
|
||||
print "Try again (Y/N)? ";
|
||||
my $input = <STDIN>;
|
||||
chomp $input;
|
||||
|
||||
my $keepGoing;
|
||||
if (uc($input) eq 'Y')
|
||||
{
|
||||
$keepGoing = 1;
|
||||
}
|
||||
elsif (uc($input) eq 'N')
|
||||
{
|
||||
$keepGoing = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
$keepGoing = promptUserToKeepPlaying();
|
||||
}
|
||||
|
||||
return $keepGoing;
|
||||
}
|
||||
45
15 Boxing/java/Basic.java
Normal file
45
15 Boxing/java/Basic.java
Normal file
@@ -0,0 +1,45 @@
|
||||
import java.util.Scanner;
|
||||
|
||||
/**
|
||||
* It provide some kind of BASIC language behaviour simulations.
|
||||
*/
|
||||
final class Basic {
|
||||
|
||||
public static int randomOf(int base) {
|
||||
return (int)Math.round(Math.floor(base* Math.random() + 1));
|
||||
}
|
||||
|
||||
/**
|
||||
* The Console "simulate" the message error when input does not match with the expected type.
|
||||
* Specifically for this game if you enter an String when and int was expected.
|
||||
*/
|
||||
public static class Console {
|
||||
private final Scanner input = new Scanner(System.in);
|
||||
|
||||
public String readLine() {
|
||||
return input.nextLine();
|
||||
}
|
||||
|
||||
public int readInt() {
|
||||
int ret = -1;
|
||||
boolean failedInput = true;
|
||||
do {
|
||||
boolean b = input.hasNextInt();
|
||||
if (b) {
|
||||
ret = input.nextInt();
|
||||
failedInput = false;
|
||||
} else {
|
||||
input.next(); // discard read
|
||||
System.out.print("!NUMBER EXPECTED - RETRY INPUT LINE\n? ");
|
||||
}
|
||||
|
||||
} while (failedInput);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
public void print(String message, Object... args) {
|
||||
System.out.printf(message, args);
|
||||
}
|
||||
}
|
||||
}
|
||||
227
15 Boxing/java/Boxing.java
Normal file
227
15 Boxing/java/Boxing.java
Normal file
@@ -0,0 +1,227 @@
|
||||
/**
|
||||
* Boxing
|
||||
*
|
||||
* <p>
|
||||
* Based on the Basic game of BatNum here
|
||||
* https://github.com/coding-horror/basic-computer-games/tree/main/15%20Boxing
|
||||
* <p>
|
||||
*/
|
||||
public class Boxing {
|
||||
|
||||
private static final Basic.Console console = new Basic.Console();
|
||||
|
||||
private GameSession session;
|
||||
|
||||
public void play() {
|
||||
showIntro();
|
||||
|
||||
loadPlayers();
|
||||
|
||||
console.print("%s'S ADVANTAGE IS %d AND VULNERABILITY IS SECRET.\n", session.getOpponent().getName(), session.getOpponent().getBestPunch().getCode());
|
||||
|
||||
|
||||
for (int roundNro = 1; roundNro <= 3; roundNro++) {
|
||||
if (session.isOver())
|
||||
break;
|
||||
|
||||
session.resetPoints();
|
||||
console.print("\nROUND %d BEGINS...%n", roundNro);
|
||||
|
||||
for (int majorPunches = 1; majorPunches <= 7; majorPunches++) {
|
||||
long i = Basic.randomOf(10);
|
||||
|
||||
if (i > 5) {
|
||||
boolean stopPunches = opponentPunch();
|
||||
if (stopPunches ) break;
|
||||
} else {
|
||||
playerPunch();
|
||||
}
|
||||
}
|
||||
showRoundWinner(roundNro);
|
||||
}
|
||||
showWinner();
|
||||
}
|
||||
|
||||
private boolean opponentPunch() {
|
||||
final Punch punch = Punch.random();
|
||||
|
||||
if (punch == session.getOpponent().getBestPunch()) session.addOpponentPoints(2);
|
||||
|
||||
if (punch == Punch.FULL_SWING) {
|
||||
console.print("%s TAKES A FULL SWING AND", session.getOpponent().getName());
|
||||
long r6 = Basic.randomOf(60);
|
||||
|
||||
if (session.getPlayer().hitVulnerability(Punch.FULL_SWING) || r6 < 30) {
|
||||
console.print(" POW!!!!! HE HITS HIM RIGHT IN THE FACE!\n");
|
||||
if (session.getPoints(session.getOpponent()) > 35) {
|
||||
|
||||
session.setKnocked();
|
||||
return true;
|
||||
}
|
||||
session.addOpponentPoints(15);
|
||||
} else {
|
||||
console.print(" IT'S BLOCKED!\n");
|
||||
}
|
||||
}
|
||||
|
||||
if (punch == Punch.HOOK || punch == Punch.UPPERCUT) {
|
||||
if (punch == Punch.HOOK) {
|
||||
console.print("%s GETS %s IN THE JAW (OUCH!)\n", session.getOpponent().getName(), session.getPlayer().getName());
|
||||
|
||||
session.addOpponentPoints(7);
|
||||
console.print("....AND AGAIN!\n");
|
||||
|
||||
session.addOpponentPoints(5);
|
||||
if (session.getPoints(session.getOpponent()) > 35) {
|
||||
session.setKnocked();
|
||||
return true;
|
||||
}
|
||||
console.print("\n");
|
||||
|
||||
}
|
||||
console.print("%s IS ATTACKED BY AN UPPERCUT (OH,OH)...\n", session.getPlayer().getName());
|
||||
long q4 = Basic.randomOf(200);
|
||||
if (session.getPlayer().hitVulnerability(Punch.UPPERCUT) || q4 <= 75) {
|
||||
console.print("AND %s CONNECTS...\n", session.getOpponent().getName());
|
||||
|
||||
session.addOpponentPoints(8);
|
||||
} else {
|
||||
console.print(" BLOCKS AND HITS %s WITH A HOOK.\n", session.getOpponent().getName());
|
||||
|
||||
session.addPlayerPoints(5);
|
||||
}
|
||||
}
|
||||
else {
|
||||
console.print("%s JABS AND ", session.getOpponent().getName());
|
||||
long z4 = Basic.randomOf(7);
|
||||
if (session.getPlayer().hitVulnerability(Punch.JAB))
|
||||
|
||||
session.addOpponentPoints(5);
|
||||
else if (z4 > 4) {
|
||||
console.print(" BLOOD SPILLS !!!\n");
|
||||
|
||||
session.addOpponentPoints(5);
|
||||
} else {
|
||||
console.print("IT'S BLOCKED!\n");
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private void playerPunch() {
|
||||
console.print("%s'S PUNCH? ", session.getPlayer().getName());
|
||||
final Punch punch = Punch.fromCode(console.readInt());
|
||||
|
||||
if (punch == session.getPlayer().getBestPunch()) session.addPlayerPoints(2);
|
||||
|
||||
switch (punch) {
|
||||
case FULL_SWING -> {
|
||||
console.print("%s SWINGS AND ", session.getPlayer().getName());
|
||||
if (session.getOpponent().getBestPunch() == Punch.JAB) {
|
||||
console.print("HE CONNECTS!\n");
|
||||
if (session.getPoints(session.getPlayer()) <= 35) session.addPlayerPoints(15);
|
||||
} else {
|
||||
long x3 = Basic.randomOf(30);
|
||||
if (x3 < 10) {
|
||||
console.print("HE CONNECTS!\n");
|
||||
if (session.getPoints(session.getPlayer()) <= 35) session.addPlayerPoints(15);
|
||||
} else {
|
||||
console.print("HE MISSES \n");
|
||||
if (session.getPoints(session.getPlayer()) != 1) console.print("\n\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
case HOOK -> {
|
||||
console.print("\n%s GIVES THE HOOK... ", session.getPlayer().getName());
|
||||
long h1 = Basic.randomOf(2);
|
||||
if (session.getOpponent().getBestPunch() == Punch.HOOK) {
|
||||
|
||||
session.addPlayerPoints(7);
|
||||
} else if (h1 == 1) {
|
||||
console.print("BUT IT'S BLOCKED!!!!!!!!!!!!!\n");
|
||||
} else {
|
||||
console.print("CONNECTS...\n");
|
||||
|
||||
session.addPlayerPoints(7);
|
||||
}
|
||||
}
|
||||
case UPPERCUT -> {
|
||||
console.print("\n%s TRIES AN UPPERCUT ", session.getPlayer().getName());
|
||||
long d5 = Basic.randomOf(100);
|
||||
if (session.getOpponent().getBestPunch() == Punch.UPPERCUT || d5 < 51) {
|
||||
console.print("AND HE CONNECTS!\n");
|
||||
|
||||
session.addPlayerPoints(4);
|
||||
} else {
|
||||
console.print("AND IT'S BLOCKED (LUCKY BLOCK!)\n");
|
||||
}
|
||||
}
|
||||
default -> {
|
||||
console.print("%s JABS AT %s'S HEAD \n", session.getPlayer().getName(), session.getOpponent().getName());
|
||||
if (session.getOpponent().getBestPunch() == Punch.JAB) {
|
||||
|
||||
session.addPlayerPoints(3);
|
||||
} else {
|
||||
long c = Basic.randomOf(8);
|
||||
if (c < 4) {
|
||||
console.print("IT'S BLOCKED.\n");
|
||||
} else {
|
||||
|
||||
session.addPlayerPoints(3);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void showRoundWinner(int roundNro) {
|
||||
if (session.isRoundWinner(session.getPlayer())) {
|
||||
console.print("\n %s WINS ROUND %d\n", session.getPlayer().getName(), roundNro);
|
||||
session.addRoundWind(session.getPlayer());
|
||||
} else {
|
||||
console.print("\n %s WINS ROUND %d\n", session.getOpponent().getName(), roundNro);
|
||||
session.addRoundWind(session.getOpponent());
|
||||
}
|
||||
}
|
||||
|
||||
private void showWinner() {
|
||||
if (session.isGameWinner(session.getOpponent())) {
|
||||
console.print("%s WINS (NICE GOING, " + session.getOpponent().getName() + ").", session.getOpponent().getName());
|
||||
} else if (session.isGameWinner(session.getPlayer())) {
|
||||
console.print("%s AMAZINGLY WINS!!", session.getPlayer().getName());
|
||||
} else if (session.isPlayerKnocked()) {
|
||||
console.print("%s IS KNOCKED COLD AND %s IS THE WINNER AND CHAMP!", session.getPlayer().getName(), session.getOpponent().getName());
|
||||
} else {
|
||||
console.print("%s IS KNOCKED COLD AND %s IS THE WINNER AND CHAMP!", session.getOpponent().getName(), session.getPlayer().getName());
|
||||
}
|
||||
|
||||
console.print("\n\nAND NOW GOODBYE FROM THE OLYMPIC ARENA.\n");
|
||||
}
|
||||
|
||||
private void loadPlayers() {
|
||||
console.print("WHAT IS YOUR OPPONENT'S NAME? ");
|
||||
final String opponentName = console.readLine();
|
||||
|
||||
console.print("INPUT YOUR MAN'S NAME? ");
|
||||
final String playerName = console.readLine();
|
||||
|
||||
console.print("DIFFERENT PUNCHES ARE: (1) FULL SWING; (2) HOOK; (3) UPPERCUT; (4) JAB.\n");
|
||||
console.print("WHAT IS YOUR MANS BEST? ");
|
||||
|
||||
final int b = console.readInt();
|
||||
|
||||
console.print("WHAT IS HIS VULNERABILITY? ");
|
||||
final int d = console.readInt();
|
||||
|
||||
final Player player = new Player(playerName, Punch.fromCode(b), Punch.fromCode(d));
|
||||
final Player opponent = new Player(opponentName);
|
||||
|
||||
session = new GameSession(player, opponent);
|
||||
}
|
||||
|
||||
private void showIntro () {
|
||||
console.print(" BOXING\n");
|
||||
console.print(" CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n\n\n");
|
||||
console.print("BOXING OLYMPIC STYLE (3 ROUNDS -- 2 OUT OF 3 WINS)\n\n");
|
||||
}
|
||||
}
|
||||
6
15 Boxing/java/BoxingGame.java
Normal file
6
15 Boxing/java/BoxingGame.java
Normal file
@@ -0,0 +1,6 @@
|
||||
public class BoxingGame {
|
||||
|
||||
public static void main(String[] args) {
|
||||
new Boxing().play();
|
||||
}
|
||||
}
|
||||
67
15 Boxing/java/GameSession.java
Normal file
67
15 Boxing/java/GameSession.java
Normal file
@@ -0,0 +1,67 @@
|
||||
/**
|
||||
* Game Session
|
||||
* The session store the state of the game
|
||||
*/
|
||||
public class GameSession {
|
||||
private final Player player;
|
||||
private final Player opponent;
|
||||
private int opponentRoundWins = 0;
|
||||
private int playerRoundWins = 0;
|
||||
|
||||
int playerPoints = 0;
|
||||
int opponentPoints = 0;
|
||||
boolean knocked = false;
|
||||
|
||||
GameSession(Player player, Player opponent) {
|
||||
this.player = player;
|
||||
this.opponent = opponent;
|
||||
}
|
||||
|
||||
public Player getPlayer() { return player;}
|
||||
public Player getOpponent() { return opponent;}
|
||||
|
||||
public void setKnocked() {
|
||||
knocked = true;
|
||||
}
|
||||
|
||||
public void resetPoints() {
|
||||
playerPoints = 0;
|
||||
opponentPoints = 0;
|
||||
}
|
||||
|
||||
public void addPlayerPoints(int ptos) { playerPoints+=ptos;}
|
||||
public void addOpponentPoints(int ptos) { opponentPoints+=ptos;}
|
||||
|
||||
public int getPoints(Player player) {
|
||||
if(player.isPlayer())
|
||||
return playerPoints;
|
||||
else
|
||||
return opponentPoints;
|
||||
}
|
||||
|
||||
public void addRoundWind(Player player) {
|
||||
if(player.isPlayer()) playerRoundWins++; else opponentRoundWins++;
|
||||
}
|
||||
|
||||
public boolean isOver() {
|
||||
return (opponentRoundWins >= 2 || playerRoundWins >= 2);
|
||||
}
|
||||
|
||||
public boolean isRoundWinner(Player player) {
|
||||
if (player.isPlayer())
|
||||
return playerPoints > opponentPoints;
|
||||
else
|
||||
return opponentPoints > playerPoints;
|
||||
}
|
||||
|
||||
public boolean isGameWinner(Player player) {
|
||||
if (player.isPlayer())
|
||||
return playerRoundWins > 2;
|
||||
else
|
||||
return opponentRoundWins > 2;
|
||||
}
|
||||
|
||||
public boolean isPlayerKnocked() {
|
||||
return knocked;
|
||||
}
|
||||
}
|
||||
42
15 Boxing/java/Player.java
Normal file
42
15 Boxing/java/Player.java
Normal file
@@ -0,0 +1,42 @@
|
||||
/**
|
||||
* The Player class model the user and compuer player
|
||||
*/
|
||||
public class Player {
|
||||
private final String name;
|
||||
private final Punch bestPunch;
|
||||
private final Punch vulnerability;
|
||||
private boolean isPlayer = false;
|
||||
|
||||
public Player(String name, Punch bestPunch, Punch vulnerability) {
|
||||
this.name = name;
|
||||
this.bestPunch = bestPunch;
|
||||
this.vulnerability = vulnerability;
|
||||
this.isPlayer = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Player with random Best Punch and Vulnerability
|
||||
*/
|
||||
public Player(String name) {
|
||||
this.name = name;
|
||||
|
||||
int b1;
|
||||
int d1;
|
||||
|
||||
do {
|
||||
b1 = Basic.randomOf(4);
|
||||
d1 = Basic.randomOf(4);
|
||||
} while (b1 == d1);
|
||||
|
||||
this.bestPunch = Punch.fromCode(b1);
|
||||
this.vulnerability = Punch.fromCode(d1);
|
||||
}
|
||||
|
||||
public boolean isPlayer() { return isPlayer; }
|
||||
public String getName() { return name; }
|
||||
public Punch getBestPunch() { return bestPunch; }
|
||||
|
||||
public boolean hitVulnerability(Punch punch) {
|
||||
return vulnerability == punch;
|
||||
}
|
||||
}
|
||||
27
15 Boxing/java/Punch.java
Normal file
27
15 Boxing/java/Punch.java
Normal file
@@ -0,0 +1,27 @@
|
||||
import java.util.Arrays;
|
||||
|
||||
/**
|
||||
* Types of Punches
|
||||
*/
|
||||
public enum Punch {
|
||||
FULL_SWING(1),
|
||||
HOOK(2),
|
||||
UPPERCUT(3),
|
||||
JAB(4);
|
||||
|
||||
private final int code;
|
||||
|
||||
Punch(int code) {
|
||||
this.code = code;
|
||||
}
|
||||
|
||||
int getCode() { return code;}
|
||||
|
||||
public static Punch fromCode(int code) {
|
||||
return Arrays.stream(Punch.values()).filter(p->p.code == code).findAny().orElse(null);
|
||||
}
|
||||
|
||||
public static Punch random() {
|
||||
return Punch.fromCode(Basic.randomOf(4));
|
||||
}
|
||||
}
|
||||
163
32 Diamond/java/Diamond.java
Normal file
163
32 Diamond/java/Diamond.java
Normal file
@@ -0,0 +1,163 @@
|
||||
import java.util.Scanner;
|
||||
|
||||
/**
|
||||
* Game of Diamond
|
||||
* <p>
|
||||
* Based on the BASIC game of Diamond here
|
||||
* https://github.com/coding-horror/basic-computer-games/blob/main/32%20Diamond/diamond.bas
|
||||
* <p>
|
||||
* Note: The idea was to create a version of the 1970's BASIC game in Java, without introducing
|
||||
* new features - no additional text, error checking, etc has been added.
|
||||
*
|
||||
* Converted from BASIC to Java by Darren Cardenas.
|
||||
*/
|
||||
|
||||
public class Diamond {
|
||||
|
||||
private static final int LINE_WIDTH = 60;
|
||||
|
||||
private static final String PREFIX = "CC";
|
||||
|
||||
private static final char SYMBOL = '!';
|
||||
|
||||
private final Scanner scan; // For user input
|
||||
|
||||
|
||||
public Diamond() {
|
||||
|
||||
scan = new Scanner(System.in);
|
||||
|
||||
} // End of constructor Diamond
|
||||
|
||||
|
||||
public void play() {
|
||||
|
||||
showIntro();
|
||||
startGame();
|
||||
|
||||
} // End of method play
|
||||
|
||||
|
||||
private void showIntro() {
|
||||
|
||||
System.out.println(" ".repeat(32) + "DIAMOND");
|
||||
System.out.println(" ".repeat(14) + "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY");
|
||||
System.out.println("\n\n");
|
||||
|
||||
} // End of method showIntro
|
||||
|
||||
|
||||
private void startGame() {
|
||||
|
||||
int body = 0;
|
||||
int column = 0;
|
||||
int end = 0;
|
||||
int fill = 0;
|
||||
int increment = 2;
|
||||
int numPerSide = 0;
|
||||
int prefixIndex = 0;
|
||||
int row = 0;
|
||||
int start = 1;
|
||||
int userNum = 0;
|
||||
|
||||
String lineContent = "";
|
||||
|
||||
// Get user input
|
||||
System.out.println("FOR A PRETTY DIAMOND PATTERN,");
|
||||
System.out.print("TYPE IN AN ODD NUMBER BETWEEN 5 AND 21? ");
|
||||
userNum = scan.nextInt();
|
||||
System.out.println("");
|
||||
|
||||
// Calcuate number of diamonds to be drawn on each side of screen
|
||||
numPerSide = (int) (LINE_WIDTH / userNum);
|
||||
|
||||
end = userNum;
|
||||
|
||||
// Begin loop through each row of diamonds
|
||||
for (row = 1; row <= numPerSide; row++) {
|
||||
|
||||
// Begin loop through top and bottom halves of each diamond
|
||||
for (body = start; increment < 0 ? body >= end : body <= end; body += increment) {
|
||||
|
||||
lineContent = "";
|
||||
|
||||
// Add whitespace
|
||||
while (lineContent.length() < ((userNum - body) / 2)) {
|
||||
lineContent += " ";
|
||||
}
|
||||
|
||||
// Begin loop through each column of diamonds
|
||||
for (column = 1; column <= numPerSide; column++) {
|
||||
|
||||
prefixIndex = 1;
|
||||
|
||||
// Begin loop that fills each diamond with characters
|
||||
for (fill = 1; fill <= body; fill++) {
|
||||
|
||||
// Right side of diamond
|
||||
if (prefixIndex > PREFIX.length()) {
|
||||
|
||||
lineContent += SYMBOL;
|
||||
|
||||
}
|
||||
// Left side of diamond
|
||||
else {
|
||||
|
||||
lineContent += PREFIX.charAt(prefixIndex - 1);
|
||||
prefixIndex++;
|
||||
|
||||
}
|
||||
|
||||
} // End loop that fills each diamond with characters
|
||||
|
||||
// Column finished
|
||||
if (column == numPerSide) {
|
||||
|
||||
break;
|
||||
|
||||
}
|
||||
// Column not finishd
|
||||
else {
|
||||
|
||||
// Add whitespace
|
||||
while (lineContent.length() < (userNum * column + (userNum - body) / 2)) {
|
||||
lineContent += " ";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} // End loop through each column of diamonds
|
||||
|
||||
System.out.println(lineContent);
|
||||
|
||||
} // End loop through top and bottom half of each diamond
|
||||
|
||||
if (start != 1) {
|
||||
|
||||
start = 1;
|
||||
end = userNum;
|
||||
increment = 2;
|
||||
|
||||
}
|
||||
else {
|
||||
|
||||
start = userNum - 2;
|
||||
end = 1;
|
||||
increment = -2;
|
||||
row--;
|
||||
|
||||
}
|
||||
|
||||
} // End loop through each row of diamonds
|
||||
|
||||
} // End of method startGame
|
||||
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
Diamond diamond = new Diamond();
|
||||
diamond.play();
|
||||
|
||||
} // End of method main
|
||||
|
||||
} // End of class Diamond
|
||||
42
33 Dice/perl/dice.pl
Normal file
42
33 Dice/perl/dice.pl
Normal file
@@ -0,0 +1,42 @@
|
||||
#!/usr/bin/perl
|
||||
use strict;
|
||||
|
||||
|
||||
print ' 'x 34 . "DICE\n";
|
||||
print ' 'x 15 . "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n";
|
||||
print "\n\n\n";
|
||||
my @F;
|
||||
|
||||
#REM DANNY FREIDUS;
|
||||
print "THIS PROGRAM SIMULATES THE ROLLING OF A\n";
|
||||
print "PAIR OF DICE.\n";
|
||||
print "YOU ENTER THE NUMBER OF TIMES YOU WANT THE COMPUTER TO\n";
|
||||
print "'ROLL' THE DICE. WATCH OUT, VERY LARGE NUMBERS TAKE\n";
|
||||
print "A LONG TIME. IN PARTICULAR, NUMBERS OVER 5000.\n";
|
||||
|
||||
my $X;
|
||||
my $Z;
|
||||
do {
|
||||
for (my $Q=1; $Q<=12; $Q++) {
|
||||
$F[$Q]=0;
|
||||
}
|
||||
print "\n"; print "HOW MANY ROLLS";
|
||||
print "? "; chomp($X = <STDIN>);
|
||||
for (my $S=1; $S<=$X; $S++) {
|
||||
my $A=int(6*rand(1)+1);
|
||||
my $B=int(6*rand(1)+1);
|
||||
my $R=$A+$B;
|
||||
$F[$R]=$F[$R]+1;
|
||||
}
|
||||
print "\n";
|
||||
print "TOTAL SPOTS\tNUMBER OF TIMES\n";
|
||||
for (my $V=2; $V<=12; $V++) {
|
||||
print "$V\t\t$F[$V]\n";
|
||||
}
|
||||
print "\n";
|
||||
print "\n"; print "TRY AGAIN";
|
||||
print "? "; chomp($Z = <STDIN>);
|
||||
} until (uc($Z) ne "YES");
|
||||
exit;
|
||||
|
||||
|
||||
BIN
37 Football/javascript/.DS_Store
vendored
Normal file
BIN
37 Football/javascript/.DS_Store
vendored
Normal file
Binary file not shown.
9
39 Golf/javascript/golf.html
Normal file
9
39 Golf/javascript/golf.html
Normal file
@@ -0,0 +1,9 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>GOLF</title>
|
||||
</head>
|
||||
<body>
|
||||
<pre id="output" style="font-size: 12pt;"></pre>
|
||||
<script src="golf.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
369
39 Golf/javascript/golf.js
Normal file
369
39 Golf/javascript/golf.js
Normal file
@@ -0,0 +1,369 @@
|
||||
// GOLF
|
||||
//
|
||||
// Converted from BASIC to Javascript by Oscar Toledo G. (nanochess)
|
||||
//
|
||||
|
||||
function print(str)
|
||||
{
|
||||
document.getElementById("output").appendChild(document.createTextNode(str));
|
||||
}
|
||||
|
||||
function input()
|
||||
{
|
||||
var input_element;
|
||||
var input_str;
|
||||
|
||||
return new Promise(function (resolve) {
|
||||
input_element = document.createElement("INPUT");
|
||||
|
||||
print("? ");
|
||||
input_element.setAttribute("type", "text");
|
||||
input_element.setAttribute("length", "50");
|
||||
document.getElementById("output").appendChild(input_element);
|
||||
input_element.focus();
|
||||
input_str = undefined;
|
||||
input_element.addEventListener("keydown", function (event) {
|
||||
if (event.keyCode == 13) {
|
||||
input_str = input_element.value;
|
||||
document.getElementById("output").removeChild(input_element);
|
||||
print(input_str);
|
||||
print("\n");
|
||||
resolve(input_str);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function tab(space)
|
||||
{
|
||||
var str = "";
|
||||
while (space-- > 0)
|
||||
str += " ";
|
||||
return str;
|
||||
}
|
||||
|
||||
var la = [];
|
||||
var f;
|
||||
var s1;
|
||||
var g2;
|
||||
var g3;
|
||||
var x;
|
||||
|
||||
var hole_data = [
|
||||
361,4,4,2,389,4,3,3,206,3,4,2,500,5,7,2,
|
||||
408,4,2,4,359,4,6,4,424,4,4,2,388,4,4,4,
|
||||
196,3,7,2,400,4,7,2,560,5,7,2,132,3,2,2,
|
||||
357,4,4,4,294,4,2,4,475,5,2,3,375,4,4,2,
|
||||
180,3,6,2,550,5,6,6,
|
||||
];
|
||||
|
||||
function show_obstacle()
|
||||
{
|
||||
switch (la[x]) {
|
||||
case 1:
|
||||
print("FAIRWAY.\n");
|
||||
break;
|
||||
case 2:
|
||||
print("ROUGH.\n");
|
||||
break;
|
||||
case 3:
|
||||
print("TREES.\n");
|
||||
break;
|
||||
case 4:
|
||||
print("ADJACENT FAIRWAY.\n");
|
||||
break;
|
||||
case 5:
|
||||
print("TRAP.\n");
|
||||
break;
|
||||
case 6:
|
||||
print("WATER.\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
function show_score()
|
||||
{
|
||||
g2 += s1;
|
||||
print("TOTAL PAR FOR " + (f - 1) + " HOLES IS " + g3 + " YOUR TOTAL IS " + g2 + "\n");
|
||||
}
|
||||
|
||||
// Main program
|
||||
async function main()
|
||||
{
|
||||
print(tab(34) + "GOLF\n");
|
||||
print(tab(15) + "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n");
|
||||
print("\n");
|
||||
print("\n");
|
||||
print("\n");
|
||||
print("WELCOME TO THE CREATIVE COMPUTING COUNTRY CLUB,\n");
|
||||
print("AN EIGHTEEN HOLE CHAMPIONSHIP LAYOUT LOCATED A SHORT\n");
|
||||
print("DISTANCE FROM SCENIC DOWNTOWN MORRISTOWN. THE\n");
|
||||
print("COMMENTATOR WILL EXPLAIN THE GAME AS YOU PLAY.\n");
|
||||
print("ENJOY YOUR GAME; SEE YOU AT THE 19TH HOLE...\n");
|
||||
print("\n");
|
||||
print("\n");
|
||||
next_hole = 0;
|
||||
g1 = 18;
|
||||
g2 = 0;
|
||||
g3 = 0;
|
||||
a = 0;
|
||||
n = 0.8;
|
||||
s2 = 0;
|
||||
f = 1;
|
||||
while (1) {
|
||||
print("WHAT IS YOUR HANDICAP");
|
||||
h = parseInt(await input());
|
||||
print("\n");
|
||||
if (h < 0 || h > 30) {
|
||||
print("PGA HANDICAPS RANGE FROM 0 TO 30.\n");
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
do {
|
||||
print("DIFFICULTIES AT GOLF INCLUDE:\n");
|
||||
print("0=HOOK, 1=SLICE, 2=POOR DISTANCE, 4=TRAP SHOTS, 5=PUTTING\n");
|
||||
print("WHICH ONE (ONLY ONE) IS YOUR WORST");
|
||||
t = parseInt(await input());
|
||||
print("\n");
|
||||
} while (t > 5) ;
|
||||
s1 = 0;
|
||||
first_routine = true;
|
||||
while (1) {
|
||||
if (first_routine) {
|
||||
la[0] = 0;
|
||||
j = 0;
|
||||
q = 0;
|
||||
s2++;
|
||||
k = 0;
|
||||
if (f != 1) {
|
||||
print("YOUR SCORE ON HOLE " + (f - 1) + " WAS " + s1 + "\n");
|
||||
show_score();
|
||||
if (g1 == f - 1) // Completed all holes?
|
||||
return; // Exit game
|
||||
if (s1 > p + 2) {
|
||||
print("KEEP YOUR HEAD DOWN.\n");
|
||||
} else if (s1 == p) {
|
||||
print("A PAR. NICE GOING.\n");
|
||||
} else if (s1 == p - 1) {
|
||||
print("A BIRDIE.\n");
|
||||
} else if (s1 == p - 2) {
|
||||
if (p != 3)
|
||||
print("A GREAT BIG EAGLE.\n");
|
||||
else
|
||||
print("A HOLE IN ONE.\n");
|
||||
}
|
||||
}
|
||||
if (f == 19) {
|
||||
print("\n");
|
||||
show_score();
|
||||
if (g1 == f - 1)
|
||||
return;
|
||||
}
|
||||
s1 = 0;
|
||||
print("\n");
|
||||
if (s1 != 0 && la[0] < 1)
|
||||
la[0] = 1;
|
||||
}
|
||||
if (s1 == 0) {
|
||||
d = hole_data[next_hole++];
|
||||
p = hole_data[next_hole++];
|
||||
la[1] = hole_data[next_hole++];
|
||||
la[2] = hole_data[next_hole++];
|
||||
print("\n");
|
||||
print("YOU ARE AT THE TEE OFF HOLE " + f + " DISTANCE " + d + " YARDS, PAR " + p + "\n");
|
||||
g3 += p;
|
||||
print("ON YOUR RIGHT IS ");
|
||||
x = 1;
|
||||
show_obstacle();
|
||||
print("ON YOUR LEFT IS ");
|
||||
x = 2
|
||||
show_obstacle();
|
||||
} else {
|
||||
x = 0;
|
||||
if (la[0] > 5) {
|
||||
if (la[0] > 6) {
|
||||
print("YOUR SHOT WENT OUT OF BOUNDS.\n");
|
||||
} else {
|
||||
print("YOUR SHOT WENT INTO THE WATER.\n");
|
||||
}
|
||||
s1++;
|
||||
print("PENALTY STROKE ASSESSED. HIT FROM PREVIOUS LOCATION.\n");
|
||||
j++;
|
||||
la[0] = 1;
|
||||
d = b;
|
||||
} else {
|
||||
print("SHOT WENT " + d1 + " YARDS. IT'S " + d2 + " YARDS FROM THE CUP.\n");
|
||||
print("BALL IS " + Math.floor(o) + " YARDS OFF LINE... IN ");
|
||||
show_obstacle();
|
||||
}
|
||||
}
|
||||
|
||||
while (1) {
|
||||
if (a != 1) {
|
||||
print("SELECTION OF CLUBS\n");
|
||||
print("YARDAGE DESIRED SUGGESTED CLUBS\n");
|
||||
print("200 TO 280 YARDS 1 TO 4\n");
|
||||
print("100 TO 200 YARDS 19 TO 13\n");
|
||||
print(" 0 TO 100 YARDS 29 TO 23\n");
|
||||
a = 1;
|
||||
}
|
||||
print("WHAT CLUB DO YOU CHOOSE");
|
||||
c = parseInt(await input());
|
||||
print("\n");
|
||||
if (c >= 1 && c <= 29 && (c < 5 || c >= 12)) {
|
||||
if (c > 4)
|
||||
c -= 6;
|
||||
if (la[0] <= 5 || c == 14 || c == 23) {
|
||||
s1++;
|
||||
w = 1;
|
||||
if (c <= 13) {
|
||||
if (f % 3 == 0 && s2 + q + (10 * (f - 1) / 18) < (f - 1) * (72 + ((h + 1) / 0.85)) / 18) {
|
||||
q++;
|
||||
if (s1 % 2 != 0 && d >= 95) {
|
||||
print("BALL HIT TREE - BOUNCED INTO ROUGH " + (d - 75) + " YARDS FROM HOLE.\n");
|
||||
d -= 75;
|
||||
continue;
|
||||
}
|
||||
print("YOU DUBBED IT.\n");
|
||||
d1 = 35;
|
||||
second_routine = 1;
|
||||
break;
|
||||
} else if (c < 4 && la[0] == 2) {
|
||||
print("YOU DUBBED IT.\n");
|
||||
d1 = 35;
|
||||
second_routine = 1;
|
||||
break;
|
||||
} else {
|
||||
second_routine = 0;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
print("NOW GAUGE YOUR DISTANCE BY A PERCENTAGE (1 TO 100)\n");
|
||||
print("OF A FULL SWING");
|
||||
w = parseInt(await input());
|
||||
w /= 100;
|
||||
print("\n");
|
||||
if (w <= 1) {
|
||||
if (la[0] == 5) {
|
||||
if (t == 3) {
|
||||
if (Math.random() <= n) {
|
||||
n *= 0.2;
|
||||
print("SHOT DUBBED, STILL IN TRAP.\n");
|
||||
continue;
|
||||
}
|
||||
n = 0.8;
|
||||
}
|
||||
d2 = 1 + (3 * Math.floor((80 / (40 - h)) * Math.random()));
|
||||
second_routine = 2;
|
||||
break;
|
||||
}
|
||||
if (c != 14)
|
||||
c -= 10;
|
||||
second_routine = 0;
|
||||
break;
|
||||
}
|
||||
s1--;
|
||||
// Fall through to THAT CLUB IS NOT IN THE BAG.
|
||||
}
|
||||
}
|
||||
}
|
||||
print("THAT CLUB IS NOT IN THE BAG.\n");
|
||||
print("\n");
|
||||
}
|
||||
if (second_routine == 0) {
|
||||
if (s1 > 7 && d < 200) {
|
||||
d2 = 1 + (3 * Math.floor((80 / (40 - h)) * Math.random()));
|
||||
second_routine = 2;
|
||||
} else {
|
||||
d1 = Math.floor(((30 - h) * 2.5 + 187 - ((30 - h) * 0.25 + 15) * c / 2) + 25 * Math.random());
|
||||
d1 = Math.floor(d1 * w);
|
||||
if (t == 2)
|
||||
d1 = Math.floor(d1 * 0.85);
|
||||
}
|
||||
}
|
||||
if (second_routine <= 1) {
|
||||
o = (Math.random() / 0.8) * (2 * h + 16) * Math.abs(Math.tan(d1 * 0.0035));
|
||||
d2 = Math.floor(Math.sqrt(Math.pow(o, 2) + Math.pow(Math.abs(d - d1), 2)));
|
||||
if (d - d1 < 0) {
|
||||
if (d2 >= 20)
|
||||
print("TOO MUCH CLUB, YOU'RE PAST THE HOLE.\n");
|
||||
}
|
||||
b = d;
|
||||
d = d2;
|
||||
if (d2 > 27) {
|
||||
if (o < 30 || j > 0) {
|
||||
la[0] = 1;
|
||||
} else {
|
||||
if (t <= 0) {
|
||||
s9 = (s2 + 1) / 15;
|
||||
if (Math.floor(s9) == s9) {
|
||||
print("YOU SLICED- ");
|
||||
la[0] = la[1];
|
||||
} else {
|
||||
print("YOU HOOKED- ");
|
||||
la[0] = la[2];
|
||||
}
|
||||
} else {
|
||||
s9 = (s2 + 1) / 15;
|
||||
if (Math.floor(s9) == s9) {
|
||||
print("YOU HOOKED- ");
|
||||
la[0] = la[2];
|
||||
} else {
|
||||
print("YOU SLICED- ");
|
||||
la[0] = la[1];
|
||||
}
|
||||
}
|
||||
if (o > 45)
|
||||
print("BADLY.\n");
|
||||
}
|
||||
first_routine = false;
|
||||
} else if (d2 > 20) {
|
||||
la[0] = 5;
|
||||
first_routine = false;
|
||||
} else if (d2 > 0.5) {
|
||||
la[0] = 8;
|
||||
d2 = Math.floor(d2 * 3);
|
||||
second_routine = 2;
|
||||
} else {
|
||||
la[0] = 9;
|
||||
print("YOU HOLED IT.\n");
|
||||
print("\n");
|
||||
f++;
|
||||
first_routine = true;
|
||||
}
|
||||
}
|
||||
if (second_routine == 2) {
|
||||
while (1) {
|
||||
print("ON GREEN, " + d2 + " FEET FROM THE PIN.\n");
|
||||
print("CHOOSE YOUR PUTT POTENCY (1 TO 13):");
|
||||
i = parseInt(await input());
|
||||
s1++;
|
||||
if (s1 + 1 - p <= (h * 0.072) + 2 && k <= 2) {
|
||||
k++;
|
||||
if (t == 4)
|
||||
d2 -= i * (4 + 1 * Math.random()) + 1;
|
||||
else
|
||||
d2 -= i * (4 + 2 * Math.random()) + 1.5;
|
||||
if (d2 < -2) {
|
||||
print("PASSED BY CUP.\n");
|
||||
d2 = Math.floor(-d2);
|
||||
continue;
|
||||
}
|
||||
if (d2 > 2) {
|
||||
print("PUTT SHORT.\n");
|
||||
d2 = Math.floor(d2);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
print("YOU HOLED IT.\n");
|
||||
print("\n");
|
||||
f++;
|
||||
break;
|
||||
}
|
||||
first_routine = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
main();
|
||||
216
45 Hello/java/Hello.java
Normal file
216
45 Hello/java/Hello.java
Normal file
@@ -0,0 +1,216 @@
|
||||
import java.util.Scanner;
|
||||
|
||||
/**
|
||||
* Game of Hello
|
||||
* <p>
|
||||
* Based on the BASIC game of Hello here
|
||||
* https://github.com/coding-horror/basic-computer-games/blob/main/45%20Hello/hello.bas
|
||||
* <p>
|
||||
* Note: The idea was to create a version of the 1970's BASIC game in Java, without introducing
|
||||
* new features - no additional text, error checking, etc has been added.
|
||||
*
|
||||
* Converted from BASIC to Java by Darren Cardenas.
|
||||
*/
|
||||
|
||||
public class Hello {
|
||||
|
||||
private static final int MONEY_WAIT_MS = 3000;
|
||||
|
||||
private final boolean goodEnding = false;
|
||||
|
||||
private final Scanner scan; // For user input
|
||||
|
||||
public Hello() {
|
||||
|
||||
scan = new Scanner(System.in);
|
||||
|
||||
} // End of constructor Hello
|
||||
|
||||
public void play() {
|
||||
|
||||
showIntro();
|
||||
startGame();
|
||||
|
||||
} // End of method play
|
||||
|
||||
private static void showIntro() {
|
||||
|
||||
System.out.println(" ".repeat(32) + "HELLO");
|
||||
System.out.println(" ".repeat(14) + "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY");
|
||||
System.out.println("\n\n");
|
||||
|
||||
} // End of method showIntro
|
||||
|
||||
private void startGame() {
|
||||
|
||||
boolean moreProblems = true;
|
||||
|
||||
String userCategory = "";
|
||||
String userName = "";
|
||||
String userResponse = "";
|
||||
|
||||
// Name question
|
||||
System.out.println("HELLO. MY NAME IS CREATIVE COMPUTER.\n\n");
|
||||
System.out.print("WHAT'S YOUR NAME? ");
|
||||
userName = scan.nextLine();
|
||||
System.out.println("");
|
||||
|
||||
// Enjoyment question
|
||||
System.out.print("HI THERE, " + userName + ", ARE YOU ENJOYING YOURSELF HERE? ");
|
||||
|
||||
while (true) {
|
||||
userResponse = scan.nextLine();
|
||||
System.out.println("");
|
||||
|
||||
if (userResponse.toUpperCase().equals("YES")) {
|
||||
System.out.println("I'M GLAD TO HEAR THAT, " + userName + ".\n");
|
||||
break;
|
||||
}
|
||||
else if (userResponse.toUpperCase().equals("NO")) {
|
||||
System.out.println("OH, I'M SORRY TO HEAR THAT, " + userName + ". MAYBE WE CAN");
|
||||
System.out.println("BRIGHTEN UP YOUR VISIT A BIT.");
|
||||
break;
|
||||
}
|
||||
else {
|
||||
System.out.println(userName + ", I DON'T UNDERSTAND YOUR ANSWER OF '" + userResponse + "'.");
|
||||
System.out.print("PLEASE ANSWER 'YES' OR 'NO'. DO YOU LIKE IT HERE? ");
|
||||
}
|
||||
}
|
||||
|
||||
// Category question
|
||||
System.out.println("");
|
||||
System.out.println("SAY, " + userName + ", I CAN SOLVE ALL KINDS OF PROBLEMS EXCEPT");
|
||||
System.out.println("THOSE DEALING WITH GREECE. WHAT KIND OF PROBLEMS DO");
|
||||
System.out.print("YOU HAVE (ANSWER SEX, HEALTH, MONEY, OR JOB)? ");
|
||||
|
||||
while (moreProblems) {
|
||||
userCategory = scan.nextLine();
|
||||
System.out.println("");
|
||||
|
||||
// Sex advice
|
||||
if (userCategory.toUpperCase().equals("SEX")) {
|
||||
System.out.print("IS YOUR PROBLEM TOO MUCH OR TOO LITTLE? ");
|
||||
userResponse = scan.nextLine();
|
||||
System.out.println("");
|
||||
|
||||
while (true) {
|
||||
if (userResponse.toUpperCase().equals("TOO MUCH")) {
|
||||
System.out.println("YOU CALL THAT A PROBLEM?!! I SHOULD HAVE SUCH PROBLEMS!");
|
||||
System.out.println("IF IT BOTHERS YOU, " + userName + ", TAKE A COLD SHOWER.");
|
||||
break;
|
||||
}
|
||||
else if (userResponse.toUpperCase().equals("TOO LITTLE")) {
|
||||
System.out.println("WHY ARE YOU HERE IN SUFFERN, " + userName + "? YOU SHOULD BE");
|
||||
System.out.println("IN TOKYO OR NEW YORK OR AMSTERDAM OR SOMEPLACE WITH SOME");
|
||||
System.out.println("REAL ACTION.");
|
||||
break;
|
||||
}
|
||||
else {
|
||||
System.out.println("DON'T GET ALL SHOOK, " + userName + ", JUST ANSWER THE QUESTION");
|
||||
System.out.print("WITH 'TOO MUCH' OR 'TOO LITTLE'. WHICH IS IT? ");
|
||||
userResponse = scan.nextLine();
|
||||
}
|
||||
}
|
||||
}
|
||||
// Health advice
|
||||
else if (userCategory.toUpperCase().equals("HEALTH")) {
|
||||
System.out.println("MY ADVICE TO YOU " + userName + " IS:");
|
||||
System.out.println(" 1. TAKE TWO ASPRIN");
|
||||
System.out.println(" 2. DRINK PLENTY OF FLUIDS (ORANGE JUICE, NOT BEER!)");
|
||||
System.out.println(" 3. GO TO BED (ALONE)");
|
||||
}
|
||||
// Money advice
|
||||
else if (userCategory.toUpperCase().equals("MONEY")) {
|
||||
System.out.println("SORRY, " + userName + ", I'M BROKE TOO. WHY DON'T YOU SELL");
|
||||
System.out.println("ENCYCLOPEADIAS OR MARRY SOMEONE RICH OR STOP EATING");
|
||||
System.out.println("SO YOU WON'T NEED SO MUCH MONEY?");
|
||||
}
|
||||
// Job advice
|
||||
else if (userCategory.toUpperCase().equals("JOB")) {
|
||||
System.out.println("I CAN SYMPATHIZE WITH YOU " + userName + ". I HAVE TO WORK");
|
||||
System.out.println("VERY LONG HOURS FOR NO PAY -- AND SOME OF MY BOSSES");
|
||||
System.out.println("REALLY BEAT ON MY KEYBOARD. MY ADVICE TO YOU, " + userName + ",");
|
||||
System.out.println("IS TO OPEN A RETAIL COMPUTER STORE. IT'S GREAT FUN.");
|
||||
}
|
||||
else {
|
||||
System.out.println("OH, " + userName + ", YOUR ANSWER OF " + userCategory + " IS GREEK TO ME.");
|
||||
}
|
||||
|
||||
// More problems question
|
||||
while (true) {
|
||||
System.out.println("");
|
||||
System.out.print("ANY MORE PROBLEMS YOU WANT SOLVED, " + userName + "? ");
|
||||
userResponse = scan.nextLine();
|
||||
System.out.println("");
|
||||
|
||||
if (userResponse.toUpperCase().equals("YES")) {
|
||||
System.out.print("WHAT KIND (SEX, MONEY, HEALTH, JOB)? ");
|
||||
break;
|
||||
}
|
||||
else if (userResponse.toUpperCase().equals("NO")) {
|
||||
moreProblems = false;
|
||||
break;
|
||||
}
|
||||
else {
|
||||
System.out.println("JUST A SIMPLE 'YES' OR 'NO' PLEASE, " + userName + ".");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Payment question
|
||||
System.out.println("");
|
||||
System.out.println("THAT WILL BE $5.00 FOR THE ADVICE, " + userName + ".");
|
||||
System.out.println("PLEASE LEAVE THE MONEY ON THE TERMINAL.");
|
||||
|
||||
// Pause
|
||||
try {
|
||||
Thread.sleep(MONEY_WAIT_MS);
|
||||
} catch (Exception e) {
|
||||
System.out.println("Caught Exception: " + e.getMessage());
|
||||
}
|
||||
|
||||
System.out.println("\n\n");
|
||||
|
||||
while (true) {
|
||||
System.out.print("DID YOU LEAVE THE MONEY? ");
|
||||
userResponse = scan.nextLine();
|
||||
System.out.println("");
|
||||
|
||||
if (userResponse.toUpperCase().equals("YES")) {
|
||||
System.out.println("HEY, " + userName + "??? YOU LEFT NO MONEY AT ALL!");
|
||||
System.out.println("YOU ARE CHEATING ME OUT OF MY HARD-EARNED LIVING.");
|
||||
System.out.println("");
|
||||
System.out.println("WHAT A RIP OFF, " + userName + "!!!\n");
|
||||
break;
|
||||
}
|
||||
else if (userResponse.toUpperCase().equals("NO")) {
|
||||
System.out.println("THAT'S HONEST, " + userName + ", BUT HOW DO YOU EXPECT");
|
||||
System.out.println("ME TO GO ON WITH MY PSYCHOLOGY STUDIES IF MY PATIENTS");
|
||||
System.out.println("DON'T PAY THEIR BILLS?");
|
||||
break;
|
||||
}
|
||||
else {
|
||||
System.out.println("YOUR ANSWER OF '" + userResponse + "' CONFUSES ME, " + userName + ".");
|
||||
System.out.println("PLEASE RESPOND WITH 'YES' OR 'NO'.");
|
||||
}
|
||||
}
|
||||
|
||||
// Legacy included unreachable code
|
||||
if (goodEnding) {
|
||||
System.out.println("NICE MEETING YOU, " + userName + ", HAVE A NICE DAY.");
|
||||
}
|
||||
else {
|
||||
System.out.println("");
|
||||
System.out.println("TAKE A WALK, " + userName + ".\n");
|
||||
}
|
||||
|
||||
} // End of method startGame
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
Hello hello = new Hello();
|
||||
hello.play();
|
||||
|
||||
} // End of method main
|
||||
|
||||
} // End of class Hello
|
||||
45
47 Hi-Lo/perl/hi-lo.pl
Normal file
45
47 Hi-Lo/perl/hi-lo.pl
Normal file
@@ -0,0 +1,45 @@
|
||||
#!/usr/bin/perl
|
||||
use strict;
|
||||
|
||||
|
||||
print ' 'x 34 . "HI LO\n";
|
||||
print ' 'x 15 . "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n";
|
||||
print "\n"; print "\n"; print "\n";
|
||||
print "THIS IS THE GAME OF HI LO.\n"; print "\n";
|
||||
print "YOU WILL HAVE 6 TRIES TO GUESS THE AMOUNT OF MONEY IN THE\n";
|
||||
print "HI LO JACKPOT, WHICH IS BETWEEN 1 AND 100 DOLLARS. IF YOU\n";
|
||||
print "GUESS THE AMOUNT, YOU WIN ALL THE MONEY IN THE JACKPOT!\n";
|
||||
print "THEN YOU GET ANOTHER CHANCE TO WIN MORE MONEY. HOWEVER,\n";
|
||||
print "IF YOU DO NOT GUESS THE AMOUNT, THE GAME ENDS.\n"; print "\n";
|
||||
my $R=0;
|
||||
my $A;
|
||||
do {
|
||||
print "\n";
|
||||
my $Y=int(100*rand(1));
|
||||
foreach (1..6) {
|
||||
print "YOUR GUESS $Y";
|
||||
print "? "; chomp($A = <STDIN>);
|
||||
if ($A eq $Y) { last; }
|
||||
if ($A>$Y) {
|
||||
print "YOUR GUESS IS TOO HIGH.\n";
|
||||
} else {
|
||||
print "YOUR GUESS IS TOO LOW.\n";
|
||||
}
|
||||
print "\n";
|
||||
}
|
||||
|
||||
if ($A==$Y) {
|
||||
$R=$R+$Y;
|
||||
print "GOT IT!!!!!!!!!! YOU WIN $Y DOLLARS.\n";
|
||||
print "YOUR TOTAL WINNINGS ARE NOW $R DOLLARS.\n";
|
||||
} else {
|
||||
$R=0;
|
||||
print "YOU BLEW IT...TOO BAD...THE NUMBER WAS $Y"
|
||||
}
|
||||
print "\n"; print "PLAY AGAIN (YES OR NO)";
|
||||
print "? "; chomp($A = <STDIN>);
|
||||
} until (uc($A) ne "YES");
|
||||
print "\n"; print "SO LONG. HOPE YOU ENJOYED YOURSELF!!!\n";
|
||||
exit;
|
||||
|
||||
|
||||
53
52 Kinema/perl/kinema.pl
Normal file
53
52 Kinema/perl/kinema.pl
Normal file
@@ -0,0 +1,53 @@
|
||||
#!/usr/bin/perl
|
||||
use strict;
|
||||
|
||||
|
||||
print ' 'x 33 . "KINEMA\n";
|
||||
print ' 'x 15 . "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n";
|
||||
print "\n\n\n";
|
||||
|
||||
while (1) {
|
||||
print "\n";
|
||||
print "\n";
|
||||
my $Q=0;
|
||||
my $V=5+int(35*rand(1));
|
||||
print "A BALL IS THROWN UPWARDS AT $V METERS PER SECOND.\n";
|
||||
print "\n";
|
||||
|
||||
my $A=.05*$V^2;
|
||||
print "HOW HIGH WILL IT GO (IN METERS)";
|
||||
$Q+= &Input($A);
|
||||
|
||||
$A=$V/5;
|
||||
print "HOW LONG UNTIL IT RETURNS (IN SECONDS)";
|
||||
$Q+= &Input($A);
|
||||
|
||||
my $T=1+int(2*$V*rand(1))/10;
|
||||
$A=$V-10*$T;
|
||||
print "WHAT WILL ITS VELOCITY BE AFTER $T SECONDS";
|
||||
$Q+= &Input($A);
|
||||
|
||||
print "\n";
|
||||
print "$Q RIGHT OUT OF 3.";
|
||||
if ($Q<2) { next; }
|
||||
print " NOT BAD.\n";
|
||||
}
|
||||
|
||||
exit;
|
||||
|
||||
|
||||
#Line500:
|
||||
sub Input {
|
||||
my ($A)= @_;
|
||||
my $Point=0;
|
||||
print "? "; chomp(my $G = <STDIN>);
|
||||
if (abs(($G-$A)/$A)<.15) {
|
||||
print "CLOSE ENOUGH.\n";
|
||||
$Point=1;
|
||||
} else {
|
||||
print "NOT EVEN CLOSE....\n";
|
||||
}
|
||||
print "CORRECT ANSWER IS $A\n";
|
||||
print "\n";
|
||||
return $Point;
|
||||
}
|
||||
9
56 Life for Two/javascript/lifefortwo.html
Normal file
9
56 Life for Two/javascript/lifefortwo.html
Normal file
@@ -0,0 +1,9 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>LIFE FOR TWO</title>
|
||||
</head>
|
||||
<body>
|
||||
<pre id="output" style="font-size: 12pt;"></pre>
|
||||
<script src="lifefortwo.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
209
56 Life for Two/javascript/lifefortwo.js
Normal file
209
56 Life for Two/javascript/lifefortwo.js
Normal file
@@ -0,0 +1,209 @@
|
||||
// LIFE FOR TWO
|
||||
//
|
||||
// Converted from BASIC to Javascript by Oscar Toledo G. (nanochess)
|
||||
//
|
||||
|
||||
function print(str)
|
||||
{
|
||||
document.getElementById("output").appendChild(document.createTextNode(str));
|
||||
}
|
||||
|
||||
function input()
|
||||
{
|
||||
var input_element;
|
||||
var input_str;
|
||||
|
||||
return new Promise(function (resolve) {
|
||||
input_element = document.createElement("INPUT");
|
||||
|
||||
print("? ");
|
||||
input_element.setAttribute("type", "text");
|
||||
input_element.setAttribute("length", "50");
|
||||
document.getElementById("output").appendChild(input_element);
|
||||
input_element.focus();
|
||||
input_str = undefined;
|
||||
input_element.addEventListener("keydown", function (event) {
|
||||
if (event.keyCode == 13) {
|
||||
input_str = input_element.value;
|
||||
document.getElementById("output").removeChild(input_element);
|
||||
print(input_str);
|
||||
print("\n");
|
||||
resolve(input_str);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function tab(space)
|
||||
{
|
||||
var str = "";
|
||||
while (space-- > 0)
|
||||
str += " ";
|
||||
return str;
|
||||
}
|
||||
|
||||
var na = [];
|
||||
var ka = [, 3,102,103,120,130,121,112,111,12,
|
||||
21,30,1020,1030,1011,1021,1003,1002,1012];
|
||||
var aa = [,-1,0,1,0,0,-1,0,1,-1,-1,1,-1,-1,1,1,1];
|
||||
var xa = [];
|
||||
var ya = [];
|
||||
var j;
|
||||
var k;
|
||||
var m2;
|
||||
var m3;
|
||||
|
||||
function show_data()
|
||||
{
|
||||
k = 0;
|
||||
m2 = 0;
|
||||
m3 = 0;
|
||||
for (j = 0; j <= 6; j++) {
|
||||
print("\n");
|
||||
for (k = 0; k <= 6; k++) {
|
||||
if (j == 0 || j == 6) {
|
||||
if (k == 6)
|
||||
print(" 0 ");
|
||||
else
|
||||
print(" " + k + " ");
|
||||
} else if (k == 0 || k == 6) {
|
||||
if (j == 6)
|
||||
print(" 0\n");
|
||||
else
|
||||
print(" " + j + " ");
|
||||
} else {
|
||||
if (na[j][k] >= 3) {
|
||||
for (o1 = 1; o1 <= 18; o1++) {
|
||||
if (na[j][k] == ka[o1])
|
||||
break;
|
||||
}
|
||||
if (o1 <= 18) {
|
||||
if (o1 <= 9) {
|
||||
na[j][k] = 100;
|
||||
m2++;
|
||||
print(" * ");
|
||||
} else {
|
||||
na[j][k] = 1000;
|
||||
m3++;
|
||||
print(" # ");
|
||||
}
|
||||
} else {
|
||||
na[j][k] = 0;
|
||||
print(" ");
|
||||
}
|
||||
} else {
|
||||
na[j][k] = 0;
|
||||
print(" ");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function process_board()
|
||||
{
|
||||
for (j = 1; j <= 5; j++) {
|
||||
for (k = 1; k <= 5; k++) {
|
||||
if (na[j][k] > 99) {
|
||||
b = 1;
|
||||
if (na[j][k] > 999)
|
||||
b = 10;
|
||||
for (o1 = 1; o1 <= 15; o1 += 2) {
|
||||
na[j + aa[o1]][k + aa[o1 + 1]] = na[j + aa[o1]][k + aa[o1 + 1]] + b;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
show_data();
|
||||
}
|
||||
|
||||
// Main program
|
||||
async function main()
|
||||
{
|
||||
print(tab(33) + "LIFE2\n");
|
||||
print(tab(15) + "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n");
|
||||
print("\n");
|
||||
print("\n");
|
||||
print("\n");
|
||||
print(tab(10) + "U.B. LIFE GAME\n");
|
||||
m2 = 0;
|
||||
m3 = 0;
|
||||
for (j = 0; j <= 6; j++) {
|
||||
na[j] = [];
|
||||
for (k = 0; k <= 6; k++)
|
||||
na[j][k] = 0;
|
||||
}
|
||||
for (b = 1; b <= 2; b++) {
|
||||
p1 = (b == 2) ? 30 : 3;
|
||||
print("\n");
|
||||
print("PLAYER " + b + " - 3 LIVE PIECES.\n");
|
||||
for (k1 = 1; k1 <= 3; k1++) {
|
||||
while (1) {
|
||||
print("X,Y\n");
|
||||
str = await input();
|
||||
ya[b] = parseInt(str);
|
||||
xa[b] = parseInt(str.substr(str.indexOf(",") + 1));
|
||||
if (xa[b] > 0 && xa[b] < 6 && ya[b] > 0 && ya[b] < 5 && na[xa[b]][ya[b]] == 0)
|
||||
break;
|
||||
print("ILLEGAL COORDS. RETYPE\n");
|
||||
}
|
||||
if (b != 1) {
|
||||
if (xa[1] == xa[2] && ya[1] == ya[2]) {
|
||||
print("SAME COORD. SET TO 0\n");
|
||||
na[xa[b] + 1][ya[b] + 1] = 0;
|
||||
b = 99;
|
||||
}
|
||||
}
|
||||
na[xa[b]][ya[b]] = p1;
|
||||
}
|
||||
}
|
||||
show_data();
|
||||
while (1) {
|
||||
print("\n");
|
||||
process_board();
|
||||
if (m2 == 0 && m3 == 0) {
|
||||
print("\n");
|
||||
print("A DRAW\n");
|
||||
break;
|
||||
}
|
||||
if (m3 == 0) {
|
||||
print("\n");
|
||||
print("PLAYER 1 IS THE WINNER\n");
|
||||
break;
|
||||
}
|
||||
if (m2 == 0) {
|
||||
print("\n");
|
||||
print("PLAYER 2 IS THE WINNER\n");
|
||||
break;
|
||||
}
|
||||
for (b = 1; b <= 2; b++) {
|
||||
print("\n");
|
||||
print("\n");
|
||||
print("PLAYER " + b + " ");
|
||||
while (1) {
|
||||
print("X,Y\n");
|
||||
str = await input();
|
||||
ya[b] = parseInt(str);
|
||||
xa[b] = parseInt(str.substr(str.indexOf(",") + 1));
|
||||
if (xa[b] > 0 && xa[b] < 6 && ya[b] > 0 && ya[b] < 5 && na[xa[b]][ya[b]] == 0)
|
||||
break;
|
||||
print("ILLEGAL COORDS. RETYPE\n");
|
||||
}
|
||||
if (b != 1) {
|
||||
if (xa[1] == xa[2] && ya[1] == ya[2]) {
|
||||
print("SAME COORD. SET TO 0\n");
|
||||
na[xa[b] + 1][ya[b] + 1] = 0;
|
||||
b = 99;
|
||||
}
|
||||
}
|
||||
if (b == 99)
|
||||
break;
|
||||
}
|
||||
if (b <= 2) {
|
||||
na[x[1]][y[1]] = 100;
|
||||
na[x[2]][y[2]] = 1000;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
main();
|
||||
54
58 Love/perl/love.pl
Normal file
54
58 Love/perl/love.pl
Normal file
@@ -0,0 +1,54 @@
|
||||
#!/usr/bin/perl
|
||||
use strict;
|
||||
|
||||
|
||||
print ' 'x 33 . "LOVE\n";
|
||||
print ' 'x 15 . "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n";
|
||||
print "\n\n\n";
|
||||
print "A TRIBUTE TO THE GREAT AMERICAN ARTIST, ROBERT INDIANA.\n";
|
||||
print "HIS GREATEST WORK WILL BE REPRODUCED WITH A MESSAGE OF\n";
|
||||
print "YOUR CHOICE UP TO 60 CHARACTERS. IF YOU CAN'T THINK OF\n";
|
||||
print "A MESSAGE, SIMPLE TYPE THE WORD 'LOVE'\n"; print "\n";
|
||||
print "YOUR MESSAGE, PLEASE? "; chomp(my $A = <STDIN>);
|
||||
my $L= length($A);
|
||||
|
||||
|
||||
#Original logic too fuzzy, remaked.
|
||||
my $Width= 60;
|
||||
my $Text= substr($A x ($Width/$L+1), 0, $Width);
|
||||
for (my $I=1; $I<10; $I++) { print "\n"; }
|
||||
|
||||
my @Data= (
|
||||
60,1,12,26,9,12,3,8,24,17,8,4,6,23,21,6,4,6,22,12,5,6,5,
|
||||
4,6,21,11,8,6,4,4,6,21,10,10,5,4,4,6,21,9,11,5,4,
|
||||
4,6,21,8,11,6,4,4,6,21,7,11,7,4,4,6,21,6,11,8,4,
|
||||
4,6,19,1,1,5,11,9,4,4,6,19,1,1,5,10,10,4,4,6,18,2,1,6,8,11,4,
|
||||
4,6,17,3,1,7,5,13,4,4,6,15,5,2,23,5,1,29,5,17,8,
|
||||
1,29,9,9,12,1,13,5,40,1,1,13,5,40,1,4,6,13,3,10,6,12,5,1,
|
||||
5,6,11,3,11,6,14,3,1,5,6,11,3,11,6,15,2,1,
|
||||
6,6,9,3,12,6,16,1,1,6,6,9,3,12,6,7,1,10,
|
||||
7,6,7,3,13,6,6,2,10,7,6,7,3,13,14,10,8,6,5,3,14,6,6,2,10,
|
||||
8,6,5,3,14,6,7,1,10,9,6,3,3,15,6,16,1,1,
|
||||
9,6,3,3,15,6,15,2,1,10,6,1,3,16,6,14,3,1,10,10,16,6,12,5,1,
|
||||
11,8,13,27,1,11,8,13,27,1,60
|
||||
);
|
||||
|
||||
|
||||
my $Pos=0;
|
||||
my $Toggle=1;
|
||||
foreach my $Size (@Data) {
|
||||
my $Chunk= $Toggle ? substr($Text, $Pos, $Size) : " " x $Size;
|
||||
print $Chunk;
|
||||
$Pos+= $Size;
|
||||
$Toggle= !$Toggle;
|
||||
if ($Pos>= $Width) {
|
||||
print "\n";
|
||||
$Toggle=1;
|
||||
$Pos=0;
|
||||
}
|
||||
}
|
||||
|
||||
for (my $I=1; $I<10; $I++) { print "\n"; }
|
||||
exit;
|
||||
|
||||
|
||||
9
60 Mastermind/javascript/mastermind.html
Normal file
9
60 Mastermind/javascript/mastermind.html
Normal file
@@ -0,0 +1,9 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>MASTERMIND</title>
|
||||
</head>
|
||||
<body>
|
||||
<pre id="output" style="font-size: 12pt;"></pre>
|
||||
<script src="mastermind.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
361
60 Mastermind/javascript/mastermind.js
Normal file
361
60 Mastermind/javascript/mastermind.js
Normal file
@@ -0,0 +1,361 @@
|
||||
// MASTERMIND
|
||||
//
|
||||
// Converted from BASIC to Javascript by Oscar Toledo G. (nanochess)
|
||||
//
|
||||
|
||||
function print(str)
|
||||
{
|
||||
document.getElementById("output").appendChild(document.createTextNode(str));
|
||||
}
|
||||
|
||||
function input()
|
||||
{
|
||||
var input_element;
|
||||
var input_str;
|
||||
|
||||
return new Promise(function (resolve) {
|
||||
input_element = document.createElement("INPUT");
|
||||
|
||||
print("? ");
|
||||
input_element.setAttribute("type", "text");
|
||||
input_element.setAttribute("length", "50");
|
||||
document.getElementById("output").appendChild(input_element);
|
||||
input_element.focus();
|
||||
input_str = undefined;
|
||||
input_element.addEventListener("keydown", function (event) {
|
||||
if (event.keyCode == 13) {
|
||||
input_str = input_element.value;
|
||||
document.getElementById("output").removeChild(input_element);
|
||||
print(input_str);
|
||||
print("\n");
|
||||
resolve(input_str);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function tab(space)
|
||||
{
|
||||
var str = "";
|
||||
while (space-- > 0)
|
||||
str += " ";
|
||||
return str;
|
||||
}
|
||||
|
||||
var p9;
|
||||
var c9;
|
||||
var b;
|
||||
var w;
|
||||
var f;
|
||||
var m;
|
||||
|
||||
var qa;
|
||||
var sa;
|
||||
var ss;
|
||||
var as;
|
||||
var gs;
|
||||
var hs;
|
||||
|
||||
function initialize_qa()
|
||||
{
|
||||
for (s = 1; s <= p9; s++)
|
||||
qa[s] = 0;
|
||||
}
|
||||
|
||||
function increment_qa()
|
||||
{
|
||||
if (qa[1] <= 0) {
|
||||
// If zero, this is our firt increment: make all ones
|
||||
for (s = 1; s <= p9; s++)
|
||||
qa[s] = 1;
|
||||
} else {
|
||||
q = 1;
|
||||
while (1) {
|
||||
qa[q] = qa[q] + 1;
|
||||
if (qa[q] <= c9)
|
||||
return;
|
||||
qa[q] = 1;
|
||||
q++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function convert_qa()
|
||||
{
|
||||
for (s = 1; s <= p9; s++) {
|
||||
as[s] = ls.substr(qa[s] - 1, 1);
|
||||
}
|
||||
}
|
||||
|
||||
function get_number()
|
||||
{
|
||||
b = 0;
|
||||
w = 0;
|
||||
f = 0;
|
||||
for (s = 1; s <= p9; s++) {
|
||||
if (gs[s] == as[s]) {
|
||||
b++;
|
||||
gs[s] = String.fromCharCode(f);
|
||||
as[s] = String.fromCharCode(f + 1);
|
||||
f += 2;
|
||||
} else {
|
||||
for (t = 1; t <= p9; t++) {
|
||||
if (gs[s] == as[t] && gs[t] != as[t]) {
|
||||
w++;
|
||||
as[t] = String.fromCharCode(f);
|
||||
gs[s] = String.fromCharCode(f + 1);
|
||||
f += 2;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function convert_qa_hs()
|
||||
{
|
||||
for (s = 1; s <= p9; s++) {
|
||||
hs[s] = ls.substr(qa[s] - 1, 1);
|
||||
}
|
||||
}
|
||||
|
||||
function copy_hs()
|
||||
{
|
||||
for (s = 1; s <= p9; s++) {
|
||||
gs[s] = hs[s];
|
||||
}
|
||||
}
|
||||
|
||||
function board_printout()
|
||||
{
|
||||
print("\n");
|
||||
print("BOARD\n");
|
||||
print("MOVE GUESS BLACK WHITE\n");
|
||||
for (z = 1; z <= m - 1; z++) {
|
||||
str = " " + z + " ";
|
||||
while (str.length < 9)
|
||||
str += " ";
|
||||
str += ss[z];
|
||||
while (str.length < 25)
|
||||
str += " ";
|
||||
str += sa[z][1];
|
||||
while (str.length < 35)
|
||||
str += " ";
|
||||
str += sa[z][2];
|
||||
print(str + "\n");
|
||||
}
|
||||
print("\n");
|
||||
}
|
||||
|
||||
function quit()
|
||||
{
|
||||
print("QUITTER! MY COMBINATION WAS: ");
|
||||
convert_qa();
|
||||
for (x = 1; x <= p9; x++) {
|
||||
print(as[x]);
|
||||
}
|
||||
print("\n");
|
||||
print("GOOD BYE\n");
|
||||
}
|
||||
|
||||
function show_score()
|
||||
{
|
||||
print("SCORE:\n");
|
||||
show_points();
|
||||
}
|
||||
|
||||
function show_points()
|
||||
{
|
||||
print(" COMPUTER " + c + "\n");
|
||||
print(" HUMAN " + h + "\n");
|
||||
print("\n");
|
||||
}
|
||||
|
||||
var color = ["BLACK", "WHITE", "RED", "GREEN",
|
||||
"ORANGE", "YELLOW", "PURPLE", "TAN"];
|
||||
|
||||
// Main program
|
||||
async function main()
|
||||
{
|
||||
print(tab(30) + "MASTERMIND\n");
|
||||
print(tab(15) + "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n");
|
||||
print("\n");
|
||||
print("\n");
|
||||
print("\n");
|
||||
//
|
||||
// MASTERMIND II
|
||||
// STEVE NORTH
|
||||
// CREATIVE COMPUTING
|
||||
// PO BOX 789-M MORRISTOWN NEW JERSEY 07960
|
||||
//
|
||||
//
|
||||
while (1) {
|
||||
print("NUMBER OF COLORS");
|
||||
c9 = parseInt(await input());
|
||||
if (c9 <= 8)
|
||||
break;
|
||||
print("NO MORE THAN 8, PLEASE!\n");
|
||||
}
|
||||
print("NUMBER OF POSITIONS");
|
||||
p9 = parseInt(await input());
|
||||
print("NUMBER OF ROUNDS");
|
||||
r9 = parseInt(await input());
|
||||
p = Math.pow(c9, p9);
|
||||
print("TOTAL POSSIBILITIES = " + p + "\n");
|
||||
h = 0;
|
||||
c = 0;
|
||||
qa = [];
|
||||
sa = [];
|
||||
ss = [];
|
||||
as = [];
|
||||
gs = [];
|
||||
ia = [];
|
||||
hs = [];
|
||||
ls = "BWRGOYPT";
|
||||
print("\n");
|
||||
print("\n");
|
||||
print("COLOR LETTER\n");
|
||||
print("===== ======\n");
|
||||
for (x = 1; x <= c9; x++) {
|
||||
str = color[x - 1];
|
||||
while (str.length < 13)
|
||||
str += " ";
|
||||
str += ls.substr(x - 1, 1);
|
||||
print(str + "\n");
|
||||
}
|
||||
print("\n");
|
||||
for (r = 1; r <= r9; r++) {
|
||||
print("\n");
|
||||
print("ROUND NUMBER " + r + " ----\n");
|
||||
print("\n");
|
||||
print("GUESS MY COMBINATION.\n");
|
||||
print("\n");
|
||||
// Get a combination
|
||||
a = Math.floor(p * Math.random() + 1);
|
||||
initialize_qa();
|
||||
for (x = 1; x <= a; x++) {
|
||||
increment_qa();
|
||||
}
|
||||
for (m = 1; m <= 10; m++) {
|
||||
while (1) {
|
||||
print("MOVE # " + m + " GUESS ");
|
||||
str = await input();
|
||||
if (str == "BOARD") {
|
||||
board_printout();
|
||||
} else if (str == "QUIT") {
|
||||
quit();
|
||||
return;
|
||||
} else if (str.length != p9) {
|
||||
print("BAD NUMBER OF POSITIONS.\n");
|
||||
} else {
|
||||
// Unpack str into gs(1-p9)
|
||||
for (x = 1; x <= p9; x++) {
|
||||
y = ls.indexOf(str.substr(x - 1, 1));
|
||||
if (y < 0) {
|
||||
print("'" + str.substr(x - 1, 1) + "' IS UNRECOGNIZED.\n");
|
||||
break;
|
||||
}
|
||||
gs[x] = str.substr(x - 1, 1);
|
||||
}
|
||||
if (x > p9)
|
||||
break;
|
||||
}
|
||||
}
|
||||
// Now we convert qa(1-p9) into as(1-p9) [ACTUAL GUESS]
|
||||
convert_qa();
|
||||
// And get number of blacks and white
|
||||
get_number();
|
||||
if (b == p9) {
|
||||
print("YOU GUESSED IT IN " + m + " MOVES!\n");
|
||||
break;
|
||||
}
|
||||
// Save all this stuff for board printout later
|
||||
ss[m] = str;
|
||||
sa[m] = [];
|
||||
sa[m][1] = b;
|
||||
sa[m][2] = w;
|
||||
}
|
||||
if (m > 10) {
|
||||
print("YOU RAN OUT OF MOVES! THAT'S ALL YOU GET!\n");
|
||||
}
|
||||
h += m;
|
||||
show_score();
|
||||
|
||||
//
|
||||
// Now computer guesses
|
||||
//
|
||||
for (x = 1; x <= p; x++)
|
||||
ia[x] = 1;
|
||||
print("NOW I GUESS. THINK OF A COMBINATION.\n");
|
||||
print("HIT RETURN WHEN READY:");
|
||||
str = await input();
|
||||
for (m = 1; m <= 10; m++) {
|
||||
initialize_qa();
|
||||
// Find a guess
|
||||
g = Math.floor(p * Math.random() + 1);
|
||||
if (ia[g] != 1) {
|
||||
for (x = g; x <= p; x++) {
|
||||
if (ia[x] == 1)
|
||||
break;
|
||||
}
|
||||
if (x > p) {
|
||||
for (x = 1; x <= g; x++) {
|
||||
if (ia[x] == 1)
|
||||
break;
|
||||
}
|
||||
if (x > g) {
|
||||
print("YOU HAVE GIVEN ME INCONSISTENT INFORMATION.\n");
|
||||
print("TRY AGAIN, AND THIS TIME PLEASE BE MORE CAREFUL.\n");
|
||||
for (x = 1; x <= p; x++)
|
||||
ia[x] = 1;
|
||||
print("NOW I GUESS. THINK OF A COMBINATION.\n");
|
||||
print("HIT RETURN WHEN READY:");
|
||||
str = await input();
|
||||
m = 0;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
g = x;
|
||||
}
|
||||
// Now we convert guess #g into gs
|
||||
for (x = 1; x <= g; x++) {
|
||||
increment_qa();
|
||||
}
|
||||
convert_qa_hs();
|
||||
print("MY GUESS IS: ");
|
||||
for (x = 1; x <= p9; x++) {
|
||||
print(hs[x]);
|
||||
}
|
||||
print(" BLACKS, WHITES ");
|
||||
str = await input();
|
||||
b1 = parseInt(str);
|
||||
w1 = parseInt(str.substr(str.indexOf(",") + 1));
|
||||
if (b1 == p9) {
|
||||
print("I GOT IT IN " + m + " MOVES!\n");
|
||||
break;
|
||||
}
|
||||
initialize_qa();
|
||||
for (x = 1; x <= p; x++) {
|
||||
increment_qa();
|
||||
if (ia[x] != 0) {
|
||||
copy_hs();
|
||||
convert_qa();
|
||||
get_number();
|
||||
if (b1 != b || w1 != w)
|
||||
ia[x] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (m > 10) {
|
||||
print("I USED UP ALL MY MOVES!\n");
|
||||
print("I GUESS MY CPU I JUST HAVING AN OFF DAY.\n");
|
||||
}
|
||||
c += m;
|
||||
show_score();
|
||||
}
|
||||
print("GAME OVER\n");
|
||||
print("FINAL SCORE:\n");
|
||||
show_points();
|
||||
}
|
||||
|
||||
main();
|
||||
69
66 Number/java/main.class
Normal file
69
66 Number/java/main.class
Normal file
@@ -0,0 +1,69 @@
|
||||
|
||||
import java.time.temporal.ValueRange;
|
||||
import java.util.Arrays;
|
||||
import java.util.Random;
|
||||
import java.util.Scanner;
|
||||
|
||||
public class Number {
|
||||
|
||||
public static int points = 0;
|
||||
|
||||
public static void printempty() { System.out.println(" "); }
|
||||
|
||||
public static void print(String toprint) { System.out.println(toprint); }
|
||||
|
||||
public static void main(String[] args) {
|
||||
print("YOU HAVE 100 POINTS. BY GUESSING NUMBERS FROM 1 TO 5, YOU");
|
||||
print("CAN GAIN OR LOSE POINTS DEPENDING UPON HOW CLOSE YOU GET TO");
|
||||
print("A RANDOM NUMBER SELECTED BY THE COMPUTER.");
|
||||
printempty();
|
||||
print("YOU OCCASIONALLY WILL GET A JACKPOT WHICH WILL DOUBLE(!)");
|
||||
print("YOUR POINT COUNT. YOU WIN WHEN YOU GET 500 POINTS.");
|
||||
printempty();
|
||||
|
||||
try {
|
||||
while (true) {
|
||||
print("GUESS A NUMBER FROM 1 TO 5");
|
||||
|
||||
|
||||
Scanner numbersc = new Scanner(System.in);
|
||||
String numberstring = numbersc.nextLine();
|
||||
|
||||
int number = Integer.parseInt(numberstring);
|
||||
|
||||
if (!(number < 1| number > 5)) {
|
||||
|
||||
Random rand = new Random();
|
||||
|
||||
int randomNum = rand.nextInt((5 - 1) + 1) + 1;
|
||||
|
||||
if (randomNum == number) {
|
||||
print("YOU HIT THE JACKPOT!!!");
|
||||
points = points * 2;
|
||||
} else if(ValueRange.of(randomNum, randomNum + 1).isValidIntValue(number)) {
|
||||
print("+5");
|
||||
points = points + 5;
|
||||
} else if(ValueRange.of(randomNum - 1, randomNum + 2).isValidIntValue(number)) {
|
||||
print("+1");
|
||||
points = points + 1;
|
||||
} else if(ValueRange.of(randomNum - 3, randomNum + 1).isValidIntValue(number)) {
|
||||
print("-1");
|
||||
points = points - 1;
|
||||
} else {
|
||||
print("-half");
|
||||
points = (int) (points * 0.5);
|
||||
}
|
||||
|
||||
print("YOU HAVE " + points + " POINTS.");
|
||||
}
|
||||
|
||||
if (points >= 500) {
|
||||
print("!!!!YOU WIN!!!! WITH " + points + " POINTS.");
|
||||
return;
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
56
74 Rock Scissors Paper/perl/rockscissors.pl
Normal file
56
74 Rock Scissors Paper/perl/rockscissors.pl
Normal file
@@ -0,0 +1,56 @@
|
||||
#!/usr/bin/perl
|
||||
use strict;
|
||||
|
||||
|
||||
print ' 'x 21 . "GAME OF ROCK, SCISSORS, PAPER\n";
|
||||
print ' 'x 15 . "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY\n";
|
||||
print "\n\n\n";
|
||||
|
||||
|
||||
my $Q=0;
|
||||
my $C=0;
|
||||
my $H=0;
|
||||
|
||||
do {
|
||||
print "HOW MANY GAMES? "; chomp($Q = <STDIN>);
|
||||
if ($Q>10) { print "SORRY, BUT WE AREN'T ALLOWED TO PLAY THAT MANY.\n"; }
|
||||
} until ($Q<11);
|
||||
|
||||
for (my $G=1; $G<=$Q; $G++) {
|
||||
print "\n"; print "GAME NUMBER $G\n";
|
||||
my $X=int(rand(1)*3+1);
|
||||
|
||||
my $K=0;
|
||||
do {
|
||||
print "3=ROCK...2=SCISSORS...1=PAPER\n";
|
||||
print "1...2...3...WHAT'S YOUR CHOICE? "; chomp($K = <STDIN>);
|
||||
if (($K-1)*($K-2)*($K-3)!=0) { print "INVALID.\n"; $K=0; }
|
||||
} until ($K!=0);
|
||||
|
||||
|
||||
print "THIS IS MY CHOICE...\n";
|
||||
if ($X==1) { print "...PAPER\n"; }
|
||||
if ($X==2) { print "...SCISSORS\n"; }
|
||||
if ($X==3) { print "...ROCK\n"; }
|
||||
|
||||
#Original logic too complex...
|
||||
if ($X==$K) { print "TIE GAME. NO WINNER.\n"; next; }
|
||||
my $Who=0;
|
||||
if ($X==1 && $K==3) { $Who=1; } #Paper wins over rock.
|
||||
if ($X==2 && $K==1) { $Who=1; } #Scissors wins over paper.
|
||||
if ($X==3 && $K==2) { $Who=1; } #Rock wins over scissors.
|
||||
if ($Who==1) {
|
||||
print "WOW! I WIN!!!\n"; $C=$C+1;
|
||||
} else {
|
||||
print "YOU WIN!!!\n"; $H=$H+1;
|
||||
}
|
||||
}
|
||||
|
||||
print "\n"; print "HERE IS THE FINAL GAME SCORE:\n";
|
||||
print "I HAVE WON $C GAME(S).\n";
|
||||
print "YOU HAVE WON $H GAME(S).\n";
|
||||
print "AND ".($Q-($C+$H))." GAME(S) ENDED IN A TIE.\n";
|
||||
print "\n"; print "THANKS FOR PLAYING!!\n";
|
||||
exit;
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
using System.ComponentModel;
|
||||
|
||||
namespace SuperStarTrek
|
||||
namespace SuperStarTrek.Commands
|
||||
{
|
||||
internal enum Command
|
||||
{
|
||||
@@ -1,7 +1,7 @@
|
||||
using System.Reflection;
|
||||
using System.ComponentModel;
|
||||
|
||||
namespace SuperStarTrek
|
||||
namespace SuperStarTrek.Commands
|
||||
{
|
||||
internal static class CommandExtensions
|
||||
{
|
||||
23
84 Super Star Trek/csharp/Commands/CommandResult.cs
Normal file
23
84 Super Star Trek/csharp/Commands/CommandResult.cs
Normal file
@@ -0,0 +1,23 @@
|
||||
namespace SuperStarTrek.Commands
|
||||
{
|
||||
internal class CommandResult
|
||||
{
|
||||
public static readonly CommandResult Ok = new(false);
|
||||
public static readonly CommandResult GameOver = new(true);
|
||||
|
||||
private CommandResult(bool isGameOver)
|
||||
{
|
||||
IsGameOver = isGameOver;
|
||||
}
|
||||
|
||||
private CommandResult(float timeElapsed)
|
||||
{
|
||||
TimeElapsed = timeElapsed;
|
||||
}
|
||||
|
||||
public bool IsGameOver { get; }
|
||||
public float TimeElapsed { get; }
|
||||
|
||||
public static CommandResult Elapsed(float timeElapsed) => new(timeElapsed);
|
||||
}
|
||||
}
|
||||
@@ -3,6 +3,7 @@ using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
using SuperStarTrek.Systems;
|
||||
using SuperStarTrek.Systems.ComputerFunctions;
|
||||
using static System.StringComparison;
|
||||
|
||||
namespace SuperStarTrek
|
||||
@@ -11,12 +12,12 @@ namespace SuperStarTrek
|
||||
{
|
||||
private readonly Output _output;
|
||||
private readonly Input _input;
|
||||
private readonly Random _random;
|
||||
|
||||
private int _initialStardate;
|
||||
private int _finalStarDate;
|
||||
private double _currentStardate;
|
||||
private float _currentStardate;
|
||||
private Coordinates _currentQuadrant;
|
||||
private Coordinates _currentSector;
|
||||
private Galaxy _galaxy;
|
||||
private int _initialKlingonCount;
|
||||
private Enterprise _enterprise;
|
||||
@@ -25,19 +26,17 @@ namespace SuperStarTrek
|
||||
{
|
||||
_output = new Output();
|
||||
_input = new Input(_output);
|
||||
_random = new Random();
|
||||
}
|
||||
|
||||
public double Stardate => _currentStardate;
|
||||
public float Stardate => _currentStardate;
|
||||
public float StardatesRemaining => _finalStarDate - _currentStardate;
|
||||
|
||||
public void DoIntroduction()
|
||||
{
|
||||
_output.Write(Strings.Title);
|
||||
|
||||
_output.Write("Do you need instructions (Y/N)? ");
|
||||
var response = Console.ReadLine();
|
||||
_output.WriteLine();
|
||||
|
||||
if (!response.Equals("N", InvariantCultureIgnoreCase))
|
||||
if (_input.GetYesNo("Do you need instructions", Input.YesNoMode.FalseOnN))
|
||||
{
|
||||
_output.Write(Strings.Instructions);
|
||||
|
||||
@@ -47,8 +46,61 @@ namespace SuperStarTrek
|
||||
|
||||
public void Play()
|
||||
{
|
||||
var quadrant = Initialise();
|
||||
Initialise();
|
||||
var gameOver = false;
|
||||
var newQuadrantText = Strings.StartText;
|
||||
|
||||
while (!gameOver)
|
||||
{
|
||||
_enterprise.Quadrant.Display(Strings.NowEntering);
|
||||
|
||||
var command = _input.GetCommand();
|
||||
|
||||
var result = _enterprise.Execute(command);
|
||||
|
||||
gameOver = result.IsGameOver || CheckIfStranded();
|
||||
_currentStardate += result.TimeElapsed;
|
||||
gameOver |= _currentStardate > _finalStarDate;
|
||||
}
|
||||
|
||||
if (_galaxy.KlingonCount > 0)
|
||||
{
|
||||
_output.Write(Strings.EndOfMission, _currentStardate, _galaxy.KlingonCount);
|
||||
}
|
||||
else
|
||||
{
|
||||
_output.Write(Strings.Congratulations, GetEfficiency());
|
||||
}
|
||||
}
|
||||
|
||||
private void Initialise()
|
||||
{
|
||||
_currentStardate = _initialStardate = _random.GetInt(20, 40) * 100;
|
||||
_finalStarDate = _initialStardate + _random.GetInt(25, 35);
|
||||
|
||||
_currentQuadrant = _random.GetCoordinate();
|
||||
|
||||
_galaxy = new Galaxy(_random);
|
||||
_initialKlingonCount = _galaxy.KlingonCount;
|
||||
|
||||
_enterprise = new Enterprise(3000, _random.GetCoordinate(), _output, _random, _input);
|
||||
_enterprise
|
||||
.Add(new WarpEngines(_enterprise, _output, _input))
|
||||
.Add(new ShortRangeSensors(_enterprise, _galaxy, this, _output))
|
||||
.Add(new LongRangeSensors(_galaxy, _output))
|
||||
.Add(new PhaserControl(_enterprise, _output, _input, _random))
|
||||
.Add(new PhotonTubes(10, _enterprise, _output, _input))
|
||||
.Add(new ShieldControl(_enterprise, _output, _input))
|
||||
.Add(new DamageControl(_enterprise, _output))
|
||||
.Add(new LibraryComputer(
|
||||
_output,
|
||||
_input,
|
||||
new CumulativeGalacticRecord(_output, _galaxy),
|
||||
new StatusReport(this, _galaxy, _enterprise, _output),
|
||||
new TorpedoDataCalculator(_enterprise, _output),
|
||||
new StarbaseDataCalculator(_enterprise, _output),
|
||||
new DirectionDistanceCalculator(_enterprise, _output, _input),
|
||||
new GalaxyRegionMap(_output, _galaxy)));
|
||||
|
||||
_output.Write(Strings.Enterprise);
|
||||
_output.Write(
|
||||
@@ -62,36 +114,21 @@ namespace SuperStarTrek
|
||||
|
||||
_input.WaitForAnyKeyButEnter("when ready to accept command");
|
||||
|
||||
_enterprise.Enter(quadrant, Strings.StartText);
|
||||
|
||||
while (!gameOver)
|
||||
{
|
||||
var command = _input.GetCommand();
|
||||
|
||||
gameOver = command == Command.XXX || _enterprise.Execute(command);
|
||||
}
|
||||
_enterprise.StartIn(BuildCurrentQuadrant());
|
||||
}
|
||||
|
||||
private Quadrant Initialise()
|
||||
{
|
||||
var random = new Random();
|
||||
|
||||
_currentStardate = _initialStardate = random.GetInt(20, 40) * 100;
|
||||
_finalStarDate = _initialStardate + random.GetInt(25, 35);
|
||||
|
||||
_currentQuadrant = random.GetCoordinate();
|
||||
_currentSector = random.GetCoordinate();
|
||||
|
||||
_galaxy = new Galaxy();
|
||||
_initialKlingonCount = _galaxy.KlingonCount;
|
||||
|
||||
_enterprise = new Enterprise(3000, random.GetCoordinate());
|
||||
_enterprise.Add(new ShortRangeSensors(_enterprise, _galaxy, this, _output))
|
||||
.Add(new ShieldControl(_enterprise, _output, _input));
|
||||
|
||||
return new Quadrant(_galaxy[_currentQuadrant], _enterprise);
|
||||
}
|
||||
private Quadrant BuildCurrentQuadrant() =>
|
||||
new Quadrant(_galaxy[_currentQuadrant], _enterprise, _random, _galaxy, _input, _output);
|
||||
|
||||
public bool Replay() => _galaxy.StarbaseCount > 0 && _input.GetString(Strings.ReplayPrompt, "Aye");
|
||||
|
||||
private bool CheckIfStranded()
|
||||
{
|
||||
if (_enterprise.IsStranded) { _output.Write(Strings.Stranded); }
|
||||
return _enterprise.IsStranded;
|
||||
}
|
||||
|
||||
private float GetEfficiency() =>
|
||||
1000 * (float)Math.Pow(_initialKlingonCount / (_currentStardate - _initialStardate), 2);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Space;
|
||||
using static System.StringComparison;
|
||||
|
||||
namespace SuperStarTrek
|
||||
@@ -25,14 +27,14 @@ namespace SuperStarTrek
|
||||
return Console.ReadLine();
|
||||
}
|
||||
|
||||
public double GetNumber(string prompt)
|
||||
public float GetNumber(string prompt)
|
||||
{
|
||||
_output.Prompt(prompt);
|
||||
|
||||
while (true)
|
||||
{
|
||||
var response = Console.ReadLine();
|
||||
if (double.TryParse(response, out var value))
|
||||
if (float.TryParse(response, out var value))
|
||||
{
|
||||
return value;
|
||||
}
|
||||
@@ -42,7 +44,14 @@ namespace SuperStarTrek
|
||||
}
|
||||
}
|
||||
|
||||
public bool TryGetNumber(string prompt, double minValue, double maxValue, out double value)
|
||||
public (float X, float Y) GetCoordinates(string prompt)
|
||||
{
|
||||
_output.Prompt($"{prompt} (X,Y)");
|
||||
var responses = ReadNumbers(2);
|
||||
return (responses[0], responses[1]);
|
||||
}
|
||||
|
||||
public bool TryGetNumber(string prompt, float minValue, float maxValue, out float value)
|
||||
{
|
||||
value = GetNumber($"{prompt} ({minValue}-{maxValue})");
|
||||
|
||||
@@ -58,7 +67,7 @@ namespace SuperStarTrek
|
||||
{
|
||||
var response = GetString("Command");
|
||||
|
||||
if (response != "" &&
|
||||
if (response.Length >= 3 &&
|
||||
Enum.TryParse(response.Substring(0, 3), ignoreCase: true, out Command parsedCommand))
|
||||
{
|
||||
return parsedCommand;
|
||||
@@ -72,5 +81,79 @@ namespace SuperStarTrek
|
||||
_output.WriteLine();
|
||||
}
|
||||
}
|
||||
|
||||
public bool TryGetCourse(string prompt, string officer, out Course course)
|
||||
{
|
||||
if (!TryGetNumber(prompt, 1, 9, out var direction))
|
||||
{
|
||||
_output.WriteLine($"{officer} reports, 'Incorrect course data, sir!'");
|
||||
course = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
course = new Course(direction);
|
||||
return true;
|
||||
}
|
||||
|
||||
public bool GetYesNo(string prompt, YesNoMode mode)
|
||||
{
|
||||
_output.Prompt($"{prompt} (Y/N)");
|
||||
var response = Console.ReadLine().ToUpperInvariant();
|
||||
|
||||
return (mode, response) switch
|
||||
{
|
||||
(YesNoMode.FalseOnN, "N") => false,
|
||||
(YesNoMode.FalseOnN, _) => true,
|
||||
(YesNoMode.TrueOnY, "Y") => true,
|
||||
(YesNoMode.TrueOnY, _) => false,
|
||||
_ => throw new ArgumentOutOfRangeException(nameof(mode), mode, "Invalid value")
|
||||
};
|
||||
}
|
||||
|
||||
private float[] ReadNumbers(int quantity)
|
||||
{
|
||||
var numbers = new float[quantity];
|
||||
var index = 0;
|
||||
bool tryAgain;
|
||||
|
||||
do
|
||||
{
|
||||
tryAgain = false;
|
||||
var responses = Console.ReadLine().Split(',');
|
||||
if (responses.Length > quantity)
|
||||
{
|
||||
_output.WriteLine("!Extra input ingored");
|
||||
}
|
||||
|
||||
for (; index < responses.Length; index++)
|
||||
{
|
||||
if (!float.TryParse(responses[index], out numbers[index]))
|
||||
{
|
||||
_output.WriteLine("!Number expected - retry input line");
|
||||
_output.Prompt();
|
||||
tryAgain = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
} while (tryAgain);
|
||||
|
||||
if (index < quantity)
|
||||
{
|
||||
_output.Prompt("?");
|
||||
var responses = ReadNumbers(quantity - index);
|
||||
for (int i = 0; i < responses.Length; i++, index++)
|
||||
{
|
||||
numbers[index] = responses[i];
|
||||
}
|
||||
}
|
||||
|
||||
return numbers;
|
||||
}
|
||||
|
||||
public enum YesNoMode
|
||||
{
|
||||
TrueOnY,
|
||||
FalseOnN
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
using SuperStarTrek.Systems;
|
||||
@@ -10,84 +12,71 @@ namespace SuperStarTrek.Objects
|
||||
internal class Enterprise
|
||||
{
|
||||
private readonly int _maxEnergy;
|
||||
private readonly Output _output;
|
||||
private readonly List<Subsystem> _systems;
|
||||
private readonly Dictionary<Command, Subsystem> _commandExecutors;
|
||||
private readonly Random _random;
|
||||
private readonly Input _input;
|
||||
private Quadrant _quadrant;
|
||||
private ShieldControl _shieldControl;
|
||||
|
||||
public Enterprise(int maxEnergy, Coordinates sector)
|
||||
public Enterprise(int maxEnergy, Coordinates sector, Output output, Random random, Input input)
|
||||
{
|
||||
Sector = sector;
|
||||
SectorCoordinates = sector;
|
||||
TotalEnergy = _maxEnergy = maxEnergy;
|
||||
|
||||
_systems = new List<Subsystem>();
|
||||
_commandExecutors = new Dictionary<Command, Subsystem>();
|
||||
_output = output;
|
||||
_random = random;
|
||||
_input = input;
|
||||
}
|
||||
|
||||
public Coordinates Quadrant => _quadrant.Coordinates;
|
||||
public Coordinates Sector { get; }
|
||||
public string Condition => GetCondition();
|
||||
public double Shields => _shieldControl.Energy;
|
||||
public double Energy => TotalEnergy - Shields;
|
||||
public double TotalEnergy { get; private set; }
|
||||
public int TorpedoCount { get; }
|
||||
public Quadrant Quadrant => _quadrant;
|
||||
public Coordinates QuadrantCoordinates => _quadrant.Coordinates;
|
||||
public Coordinates SectorCoordinates { get; private set; }
|
||||
|
||||
public bool IsDocked { get; private set; }
|
||||
public string Condition => GetCondition();
|
||||
public LibraryComputer Computer => (LibraryComputer)_commandExecutors[Command.COM];
|
||||
public ShieldControl ShieldControl => (ShieldControl)_commandExecutors[Command.SHE];
|
||||
public float Energy => TotalEnergy - ShieldControl.ShieldEnergy;
|
||||
public float TotalEnergy { get; private set; }
|
||||
public int DamagedSystemCount => _systems.Count(s => s.IsDamaged);
|
||||
public IEnumerable<Subsystem> Systems => _systems;
|
||||
public PhotonTubes PhotonTubes => (PhotonTubes)_commandExecutors[Command.TOR];
|
||||
public bool IsDocked => _quadrant.EnterpriseIsNextToStarbase;
|
||||
public bool IsStranded => TotalEnergy < 10 || Energy < 10 && ShieldControl.IsDamaged;
|
||||
|
||||
public Enterprise Add(Subsystem system)
|
||||
{
|
||||
_systems.Add(system);
|
||||
_commandExecutors[system.Command] = system;
|
||||
|
||||
if (system is ShieldControl shieldControl) { _shieldControl = shieldControl; }
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
public string GetDamageReport()
|
||||
{
|
||||
var report = new StringBuilder();
|
||||
report.AppendLine().AppendLine().AppendLine("Device State of Repair");
|
||||
foreach (var system in _systems)
|
||||
{
|
||||
report.Append(system.Name.PadRight(25)).AppendLine(system.Condition.ToString(" 0.00;-0.00"));
|
||||
}
|
||||
report.AppendLine();
|
||||
return report.ToString();
|
||||
}
|
||||
|
||||
public void Enter(Quadrant quadrant, string entryTextFormat)
|
||||
public void StartIn(Quadrant quadrant)
|
||||
{
|
||||
_quadrant = quadrant;
|
||||
|
||||
var _output = new Output();
|
||||
_output.Write(entryTextFormat, quadrant);
|
||||
|
||||
if (quadrant.HasKlingons)
|
||||
{
|
||||
_output.Write(Strings.CombatArea);
|
||||
if (Shields <= 200) { _output.Write(Strings.LowShields); }
|
||||
}
|
||||
|
||||
IsDocked = quadrant.EnterpriseIsNextToStarbase;
|
||||
|
||||
Execute(Command.SRS);
|
||||
quadrant.Display(Strings.StartText);
|
||||
}
|
||||
|
||||
private string GetCondition() =>
|
||||
(_quadrant.HasKlingons, Energy / _maxEnergy) switch
|
||||
{
|
||||
(true, _) => "*Red*",
|
||||
(_, < 0.1) => "Yellow",
|
||||
(_, < 0.1f) => "Yellow",
|
||||
_ => "Green"
|
||||
};
|
||||
|
||||
public bool Execute(Command command)
|
||||
public CommandResult Execute(Command command)
|
||||
{
|
||||
_commandExecutors[command].ExecuteCommand(_quadrant);
|
||||
return false;
|
||||
if (command == Command.XXX) { return CommandResult.GameOver; }
|
||||
|
||||
return _commandExecutors[command].ExecuteCommand(_quadrant);
|
||||
}
|
||||
|
||||
public void Refuel() => TotalEnergy = _maxEnergy;
|
||||
|
||||
internal bool Recognises(string command)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
@@ -99,5 +88,143 @@ namespace SuperStarTrek.Objects
|
||||
}
|
||||
|
||||
public override string ToString() => "<*>";
|
||||
|
||||
internal void UseEnergy(float amountUsed)
|
||||
{
|
||||
TotalEnergy -= amountUsed;
|
||||
}
|
||||
|
||||
internal CommandResult TakeHit(Coordinates sector, int hitStrength)
|
||||
{
|
||||
_output.WriteLine($"{hitStrength} unit hit on Enterprise from sector {sector}");
|
||||
ShieldControl.AbsorbHit(hitStrength);
|
||||
|
||||
if (ShieldControl.ShieldEnergy <= 0)
|
||||
{
|
||||
_output.WriteLine(Strings.Destroyed);
|
||||
return CommandResult.GameOver;
|
||||
}
|
||||
|
||||
_output.WriteLine($" <Shields down to {ShieldControl.ShieldEnergy} units>");
|
||||
|
||||
if (hitStrength >= 20)
|
||||
{
|
||||
TakeDamage(hitStrength);
|
||||
}
|
||||
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
private void TakeDamage(float hitStrength)
|
||||
{
|
||||
var hitShieldRatio = hitStrength / ShieldControl.ShieldEnergy;
|
||||
if (_random.GetFloat() > 0.6 || hitShieldRatio <= 0.02f)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var system = _systems[_random.Get1To8Inclusive() - 1];
|
||||
system.TakeDamage(hitShieldRatio + 0.5f * _random.GetFloat());
|
||||
_output.WriteLine($"Damage Control reports, '{system.Name} damaged by the hit.'");
|
||||
}
|
||||
|
||||
internal void RepairSystems(float repairWorkDone)
|
||||
{
|
||||
var repairedSystems = new List<string>();
|
||||
|
||||
foreach (var system in _systems.Where(s => s.IsDamaged))
|
||||
{
|
||||
if (system.Repair(repairWorkDone))
|
||||
{
|
||||
repairedSystems.Add(system.Name);
|
||||
}
|
||||
}
|
||||
|
||||
if (repairedSystems.Any())
|
||||
{
|
||||
_output.WriteLine("Damage Control report:");
|
||||
foreach (var systemName in repairedSystems)
|
||||
{
|
||||
_output.WriteLine($" {systemName} repair completed.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
internal void VaryConditionOfRandomSystem()
|
||||
{
|
||||
if (_random.GetFloat() > 0.2f) { return; }
|
||||
|
||||
var system = _systems[_random.Get1To8Inclusive() - 1];
|
||||
_output.Write($"Damage Control report: {system.Name} ");
|
||||
if (_random.GetFloat() >= 0.6)
|
||||
{
|
||||
system.Repair(_random.GetFloat() * 3 + 1);
|
||||
_output.WriteLine("state of repair improved");
|
||||
}
|
||||
else
|
||||
{
|
||||
system.TakeDamage(_random.GetFloat() * 5 + 1);
|
||||
_output.WriteLine("damaged");
|
||||
}
|
||||
}
|
||||
|
||||
internal float Move(Course course, float warpFactor, int distance)
|
||||
{
|
||||
var (quadrant, sector) = MoveWithinQuadrant(course, distance) ?? MoveBeyondQuadrant(course, distance);
|
||||
|
||||
if (quadrant != _quadrant.Coordinates)
|
||||
{
|
||||
_quadrant = new Quadrant(_quadrant.Galaxy[quadrant], this, _random, _quadrant.Galaxy, _input, _output);
|
||||
}
|
||||
_quadrant.SetEnterpriseSector(sector);
|
||||
SectorCoordinates = sector;
|
||||
|
||||
TotalEnergy -= distance + 10;
|
||||
if (Energy < 0)
|
||||
{
|
||||
_output.WriteLine("Shield Control supplies energy to complete the maneuver.");
|
||||
ShieldControl.ShieldEnergy = Math.Max(0, TotalEnergy);
|
||||
}
|
||||
|
||||
return GetTimeElapsed(quadrant, warpFactor);
|
||||
}
|
||||
|
||||
private (Coordinates, Coordinates)? MoveWithinQuadrant(Course course, int distance)
|
||||
{
|
||||
var currentSector = SectorCoordinates;
|
||||
foreach (var (sector, index) in course.GetSectorsFrom(SectorCoordinates).Select((s, i) => (s, i)))
|
||||
{
|
||||
if (distance == 0) { break; }
|
||||
|
||||
if (_quadrant.HasObjectAt(sector))
|
||||
{
|
||||
_output.WriteLine($"Warp engines shut down at sector {currentSector} dues to bad navigation");
|
||||
distance = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
currentSector = sector;
|
||||
distance -= 1;
|
||||
}
|
||||
|
||||
return distance == 0 ? (_quadrant.Coordinates, currentSector) : null;
|
||||
}
|
||||
|
||||
private (Coordinates, Coordinates) MoveBeyondQuadrant(Course course, int distance)
|
||||
{
|
||||
var (complete, quadrant, sector) = course.GetDestination(QuadrantCoordinates, SectorCoordinates, distance);
|
||||
|
||||
if (!complete)
|
||||
{
|
||||
_output.Write(Strings.PermissionDenied, sector, quadrant);
|
||||
}
|
||||
|
||||
return (quadrant, sector);
|
||||
}
|
||||
|
||||
private float GetTimeElapsed(Coordinates finalQuadrant, float warpFactor) =>
|
||||
finalQuadrant == _quadrant.Coordinates
|
||||
? Math.Min(1, (float)Math.Round(warpFactor, 1, MidpointRounding.ToZero))
|
||||
: 1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,14 +1,42 @@
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Objects
|
||||
{
|
||||
internal class Klingon
|
||||
{
|
||||
private double _energy;
|
||||
private readonly Random _random;
|
||||
|
||||
public Klingon()
|
||||
public Klingon(Coordinates sector, Random random)
|
||||
{
|
||||
_energy = new Random().GetDouble(100, 300);
|
||||
Sector = sector;
|
||||
_random = random;
|
||||
Energy = _random.GetFloat(100, 300);
|
||||
}
|
||||
|
||||
public float Energy { get; private set; }
|
||||
public Coordinates Sector { get; private set; }
|
||||
|
||||
public override string ToString() => "+K+";
|
||||
|
||||
public CommandResult FireOn(Enterprise enterprise)
|
||||
{
|
||||
var attackStrength = _random.GetFloat();
|
||||
var distanceToEnterprise = Sector.GetDistanceTo(enterprise.SectorCoordinates);
|
||||
var hitStrength = (int)(Energy * (2 + attackStrength) / distanceToEnterprise);
|
||||
Energy /= 3 + attackStrength;
|
||||
|
||||
return enterprise.TakeHit(Sector, hitStrength);
|
||||
}
|
||||
|
||||
internal bool TakeHit(int hitStrength)
|
||||
{
|
||||
if (hitStrength < 0.15 * Energy) { return false; }
|
||||
|
||||
Energy -= hitStrength;
|
||||
return true;
|
||||
}
|
||||
|
||||
internal void MoveTo(Coordinates newSector) => Sector = newSector;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,7 +1,44 @@
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Objects
|
||||
{
|
||||
internal class Starbase
|
||||
{
|
||||
private readonly Input _input;
|
||||
private readonly Output _output;
|
||||
private readonly float _repairDelay;
|
||||
|
||||
public Starbase(Coordinates sector, Random random, Input input, Output output)
|
||||
{
|
||||
Sector = sector;
|
||||
_repairDelay = random.GetFloat() * 0.5f;
|
||||
_input = input;
|
||||
_output = output;
|
||||
}
|
||||
|
||||
internal Coordinates Sector { get; }
|
||||
public override string ToString() => ">!<";
|
||||
|
||||
internal bool TryRepair(Enterprise enterprise, out float repairTime)
|
||||
{
|
||||
repairTime = enterprise.DamagedSystemCount * 0.1f + _repairDelay;
|
||||
if (repairTime >= 1) { repairTime = 0.9f; }
|
||||
|
||||
_output.Write(Strings.RepairEstimate, repairTime);
|
||||
if (_input.GetYesNo(Strings.RepairPrompt, Input.YesNoMode.TrueOnY))
|
||||
{
|
||||
foreach (var system in enterprise.Systems)
|
||||
{
|
||||
system.Repair();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
repairTime = 0;
|
||||
return false;
|
||||
}
|
||||
|
||||
internal void ProtectEnterprise() => _output.WriteLine(Strings.Protected);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,12 +4,37 @@ namespace SuperStarTrek
|
||||
{
|
||||
internal class Output
|
||||
{
|
||||
public void Write(string text) => Console.Write(text);
|
||||
public void Write(string format, params object[] args) => Console.Write(format, args);
|
||||
public void WriteLine(string text = "") => Console.WriteLine(text);
|
||||
public Output Write(string text)
|
||||
{
|
||||
Console.Write(text);
|
||||
return this;
|
||||
}
|
||||
|
||||
public void NextLine() => Console.WriteLine();
|
||||
public Output Write(string format, params object[] args)
|
||||
{
|
||||
Console.Write(format, args);
|
||||
return this;
|
||||
}
|
||||
|
||||
public Output WriteLine(string text = "")
|
||||
{
|
||||
Console.WriteLine(text);
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||
public Output NextLine()
|
||||
{
|
||||
Console.WriteLine();
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||
public Output Prompt(string text = "")
|
||||
{
|
||||
Console.Write($"{text}? ");
|
||||
return this;
|
||||
}
|
||||
|
||||
public void Prompt(string text = "") => Console.Write($"{text}? ");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,6 +29,7 @@ namespace SuperStarTrek
|
||||
{
|
||||
static void Main()
|
||||
{
|
||||
var foo = Utils.DirectionAndDistance.From(1,1).To(4,5);
|
||||
var game = new Game();
|
||||
|
||||
game.DoIntroduction();
|
||||
|
||||
@@ -6,20 +6,20 @@ namespace SuperStarTrek
|
||||
{
|
||||
private static readonly System.Random _random = new();
|
||||
|
||||
public Coordinates GetCoordinate() => new Coordinates(Get1To8Inclusive(), Get1To8Inclusive());
|
||||
public Coordinates GetCoordinate() => new Coordinates(Get1To8Inclusive() - 1, Get1To8Inclusive() - 1);
|
||||
|
||||
// Duplicates the algorithm used in the original code to get an integer value from 1 to 8, inclusive:
|
||||
// 475 DEF FNR(R)=INT(RND(R)*7.98+1.01)
|
||||
// Returns a value from 1 to 8, inclusive.
|
||||
// Note there's a slight bias away from the extreme values, 1 and 8.
|
||||
public int Get1To8Inclusive() => (int)(_random.NextDouble() * 7.98 + 1.01);
|
||||
public int Get1To8Inclusive() => (int)(GetFloat() * 7.98 + 1.01);
|
||||
|
||||
public int GetInt(int inclusiveMinValue, int exclusiveMaxValue) =>
|
||||
_random.Next(inclusiveMinValue, exclusiveMaxValue);
|
||||
|
||||
public double GetDouble() => _random.NextDouble();
|
||||
public float GetFloat() => (float)_random.NextDouble();
|
||||
|
||||
public double GetDouble(double inclusiveMinValue, double exclusiveMaxValue)
|
||||
=> _random.NextDouble() * (exclusiveMaxValue - inclusiveMinValue) + inclusiveMinValue;
|
||||
public float GetFloat(float inclusiveMinValue, float exclusiveMaxValue)
|
||||
=> GetFloat() * (exclusiveMaxValue - inclusiveMinValue) + inclusiveMinValue;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
|
||||
Functions available from Library-Computer:
|
||||
0 = Cumulative galactic record
|
||||
1 = Status report
|
||||
2 = Photon torpedo data
|
||||
3 = Starbase nav data
|
||||
4 = Direction/distance calculator
|
||||
5 = Galaxy 'region name' map
|
||||
|
||||
4
84 Super Star Trek/csharp/Resources/Congratulations.txt
Normal file
4
84 Super Star Trek/csharp/Resources/Congratulations.txt
Normal file
@@ -0,0 +1,4 @@
|
||||
Congratulations, Captain! The last Klingon battle cruiser
|
||||
menacing the Federation has been destroyed.
|
||||
|
||||
Your efficiency rating is {0}.
|
||||
3
84 Super Star Trek/csharp/Resources/CourtMartial.txt
Normal file
3
84 Super Star Trek/csharp/Resources/CourtMartial.txt
Normal file
@@ -0,0 +1,3 @@
|
||||
|
||||
Starfleet Command reviewing your record to consider
|
||||
court martial!
|
||||
1
84 Super Star Trek/csharp/Resources/Destroyed.txt
Normal file
1
84 Super Star Trek/csharp/Resources/Destroyed.txt
Normal file
@@ -0,0 +1 @@
|
||||
The Enterprise has been destroyed. The Federation will be conquered.
|
||||
3
84 Super Star Trek/csharp/Resources/EndOfMission.txt
Normal file
3
84 Super Star Trek/csharp/Resources/EndOfMission.txt
Normal file
@@ -0,0 +1,3 @@
|
||||
Is is stardate {0}.
|
||||
There were {1} Klingon battle cruisers left at
|
||||
the end of your mission.
|
||||
@@ -1,3 +1,4 @@
|
||||
|
||||
INSTRUCTIONS FOR 'SUPER STAR TREK'
|
||||
|
||||
1. When you see "Command ?" printed, enter one of the legal
|
||||
|
||||
2
84 Super Star Trek/csharp/Resources/NoEnemyShips.txt
Normal file
2
84 Super Star Trek/csharp/Resources/NoEnemyShips.txt
Normal file
@@ -0,0 +1,2 @@
|
||||
Science Officer Spock reports, 'Sensors show no enemy ships
|
||||
in this quadrant'
|
||||
1
84 Super Star Trek/csharp/Resources/NoStarbase.txt
Normal file
1
84 Super Star Trek/csharp/Resources/NoStarbase.txt
Normal file
@@ -0,0 +1 @@
|
||||
Mr. Spock reports, 'Sensors show no starbases in this quadrant.'
|
||||
2
84 Super Star Trek/csharp/Resources/NowEntering.txt
Normal file
2
84 Super Star Trek/csharp/Resources/NowEntering.txt
Normal file
@@ -0,0 +1,2 @@
|
||||
Now entering {0} quadrant . . .
|
||||
|
||||
5
84 Super Star Trek/csharp/Resources/PermissionDenied.txt
Normal file
5
84 Super Star Trek/csharp/Resources/PermissionDenied.txt
Normal file
@@ -0,0 +1,5 @@
|
||||
Lt. Uhura report message from Starfleet Command:
|
||||
'Permission to attempt crossing of galactic perimeter
|
||||
is hereby *Denied*. Shut down your engines.'
|
||||
Chief Engineer Scott reports, 'Warp engines shut down
|
||||
at sector {0} of quadrant {1}.'
|
||||
1
84 Super Star Trek/csharp/Resources/Protected.txt
Normal file
1
84 Super Star Trek/csharp/Resources/Protected.txt
Normal file
@@ -0,0 +1 @@
|
||||
Starbase shields protect the Enterprise
|
||||
8
84 Super Star Trek/csharp/Resources/RegionNames.txt
Normal file
8
84 Super Star Trek/csharp/Resources/RegionNames.txt
Normal file
@@ -0,0 +1,8 @@
|
||||
Antares Sirius
|
||||
Rigel Deneb
|
||||
Procyon Capella
|
||||
Vega Betelgeuse
|
||||
Canopus Aldebaran
|
||||
Altair Regulus
|
||||
Sagittarius Arcturus
|
||||
Pollux Spica
|
||||
@@ -0,0 +1,3 @@
|
||||
|
||||
That does it, Captain!! You are hereby relieved of command
|
||||
and sentenced to 99 stardates at hard labor on Cygnus 12!!
|
||||
2
84 Super Star Trek/csharp/Resources/RepairEstimate.txt
Normal file
2
84 Super Star Trek/csharp/Resources/RepairEstimate.txt
Normal file
@@ -0,0 +1,2 @@
|
||||
Technicians standing by to effect repairs to your ship;
|
||||
Estimated time to repair: {0} stardates.
|
||||
1
84 Super Star Trek/csharp/Resources/RepairPrompt.txt
Normal file
1
84 Super Star Trek/csharp/Resources/RepairPrompt.txt
Normal file
@@ -0,0 +1 @@
|
||||
Will you authorize the repair order (Y/N)
|
||||
@@ -1,3 +1,5 @@
|
||||
|
||||
|
||||
The Federation is in need of a new starship commander
|
||||
for a similar mission -- if there is a volunteer
|
||||
let him step forward and enter 'Aye'
|
||||
3
84 Super Star Trek/csharp/Resources/Stranded.txt
Normal file
3
84 Super Star Trek/csharp/Resources/Stranded.txt
Normal file
@@ -0,0 +1,3 @@
|
||||
** FATAL ERROR ** You've just stranded your ship in space
|
||||
You have insufficient maneuvering energy, and shield control
|
||||
is presently incapable of cross-circuiting to engine room!!
|
||||
@@ -7,14 +7,29 @@ namespace SuperStarTrek.Resources
|
||||
internal static class Strings
|
||||
{
|
||||
public static string CombatArea => GetResource();
|
||||
public static string ComputerFunctions => GetResource();
|
||||
public static string Congratulations => GetResource();
|
||||
public static string CourtMartial => GetResource();
|
||||
public static string Destroyed => GetResource();
|
||||
public static string EndOfMission => GetResource();
|
||||
public static string Enterprise => GetResource();
|
||||
public static string Instructions => GetResource();
|
||||
public static string LowShields => GetResource();
|
||||
public static string NoEnemyShips => GetResource();
|
||||
public static string NoStarbase => GetResource();
|
||||
public static string NowEntering => GetResource();
|
||||
public static string Orders => GetResource();
|
||||
public static string PermissionDenied => GetResource();
|
||||
public static string Protected => GetResource();
|
||||
public static string RegionNames => GetResource();
|
||||
public static string RelievedOfCommand => GetResource();
|
||||
public static string RepairEstimate => GetResource();
|
||||
public static string RepairPrompt => GetResource();
|
||||
public static string ReplayPrompt => GetResource();
|
||||
public static string ShieldsDropped => GetResource();
|
||||
public static string ShortRangeSensorsOut => GetResource();
|
||||
public static string StartText => GetResource();
|
||||
public static string Stranded => GetResource();
|
||||
public static string Title => GetResource();
|
||||
|
||||
private static string GetResource([CallerMemberName] string name = "")
|
||||
|
||||
@@ -1,27 +0,0 @@
|
||||
using System;
|
||||
|
||||
namespace SuperStarTrek.Space
|
||||
{
|
||||
// Represents the corrdintate of a quadrant in the galaxy, or a sector in a quadrant.
|
||||
// Note that the origin is top-left, x increase downwards, and y increases to the right.
|
||||
internal record Coordinates
|
||||
{
|
||||
public Coordinates(int x, int y)
|
||||
{
|
||||
X = Validated(x, nameof(x));
|
||||
Y = Validated(y, nameof(y));
|
||||
}
|
||||
|
||||
public int X { get; }
|
||||
public int Y { get; }
|
||||
|
||||
private int Validated(int value, string argumentName)
|
||||
{
|
||||
if (value >= 1 && value <= 8) { return value; }
|
||||
|
||||
throw new ArgumentOutOfRangeException(argumentName, value, "Must be 1 to 8 inclusive");
|
||||
}
|
||||
|
||||
public override string ToString() => $"{X} , {Y}";
|
||||
}
|
||||
}
|
||||
67
84 Super Star Trek/csharp/Space/Coordinates.cs
Normal file
67
84 Super Star Trek/csharp/Space/Coordinates.cs
Normal file
@@ -0,0 +1,67 @@
|
||||
using System;
|
||||
using SuperStarTrek.Utils;
|
||||
|
||||
namespace SuperStarTrek.Space
|
||||
{
|
||||
// Represents the corrdintate of a quadrant in the galaxy, or a sector in a quadrant.
|
||||
// Note that the origin is top-left, x increase downwards, and y increases to the right.
|
||||
internal record Coordinates
|
||||
{
|
||||
public Coordinates(int x, int y)
|
||||
{
|
||||
X = Validated(x, nameof(x));
|
||||
Y = Validated(y, nameof(y));
|
||||
|
||||
RegionIndex = (X << 1) + (Y >> 2);
|
||||
SubRegionIndex = Y % 4;
|
||||
}
|
||||
|
||||
public int X { get; }
|
||||
public int Y { get; }
|
||||
public int RegionIndex { get; }
|
||||
public int SubRegionIndex { get; }
|
||||
|
||||
private int Validated(int value, string argumentName)
|
||||
{
|
||||
if (value >= 0 && value <= 7) { return value; }
|
||||
|
||||
throw new ArgumentOutOfRangeException(argumentName, value, "Must be 0 to 7 inclusive");
|
||||
}
|
||||
|
||||
private static bool IsValid(int value) => value >= 0 && value <= 7;
|
||||
|
||||
public override string ToString() => $"{X+1} , {Y+1}";
|
||||
|
||||
internal void Deconstruct(out int x, out int y)
|
||||
{
|
||||
x = X;
|
||||
y = Y;
|
||||
}
|
||||
|
||||
internal static bool TryCreate(float x, float y, out Coordinates coordinates)
|
||||
{
|
||||
var roundedX = Round(x);
|
||||
var roundedY = Round(y);
|
||||
|
||||
if (IsValid(roundedX) && IsValid(roundedY))
|
||||
{
|
||||
coordinates = new Coordinates(roundedX, roundedY);
|
||||
return true;
|
||||
}
|
||||
|
||||
coordinates = default;
|
||||
return false;
|
||||
|
||||
static int Round(float value) => (int)Math.Round(value, MidpointRounding.AwayFromZero);
|
||||
}
|
||||
|
||||
internal (float Direction, float Distance) GetDirectionAndDistanceTo(Coordinates destination) =>
|
||||
DirectionAndDistance.From(this).To(destination);
|
||||
|
||||
internal float GetDistanceTo(Coordinates destination)
|
||||
{
|
||||
var (_, distance) = GetDirectionAndDistanceTo(destination);
|
||||
return distance;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace SuperStarTrek.Space
|
||||
{
|
||||
@@ -24,7 +25,7 @@ namespace SuperStarTrek.Space
|
||||
(0, 1)
|
||||
};
|
||||
|
||||
public Course(double direction)
|
||||
internal Course(float direction)
|
||||
{
|
||||
if (direction < 1 || direction > 9)
|
||||
{
|
||||
@@ -44,7 +45,53 @@ namespace SuperStarTrek.Space
|
||||
DeltaY = baseCardinal.DeltaY + (nextCardinal.DeltaY - baseCardinal.DeltaY) * fractionalDirection;
|
||||
}
|
||||
|
||||
public double DeltaX { get; }
|
||||
public double DeltaY { get; }
|
||||
internal float DeltaX { get; }
|
||||
internal float DeltaY { get; }
|
||||
|
||||
internal IEnumerable<Coordinates> GetSectorsFrom(Coordinates start)
|
||||
{
|
||||
(float x, float y) = start;
|
||||
|
||||
while(true)
|
||||
{
|
||||
x += DeltaX;
|
||||
y += DeltaY;
|
||||
|
||||
if (!Coordinates.TryCreate(x, y, out var coordinates))
|
||||
{
|
||||
yield break;
|
||||
}
|
||||
|
||||
yield return coordinates;
|
||||
}
|
||||
}
|
||||
|
||||
internal (bool, Coordinates, Coordinates) GetDestination(Coordinates quadrant, Coordinates sector, int distance)
|
||||
{
|
||||
var (xComplete, quadrantX, sectorX) = GetNewCoordinate(quadrant.X, sector.X, DeltaX * distance);
|
||||
var (yComplete, quadrantY, sectorY) = GetNewCoordinate(quadrant.Y, sector.Y, DeltaY * distance);
|
||||
|
||||
return (xComplete && yComplete, new Coordinates(quadrantX, quadrantY), new Coordinates(sectorX, sectorY));
|
||||
}
|
||||
|
||||
private (bool, int, int) GetNewCoordinate(int quadrant, int sector, float sectorsTravelled)
|
||||
{
|
||||
var galacticCoordinate = quadrant * 8 + sector + sectorsTravelled;
|
||||
var newQuadrant = (int)(galacticCoordinate / 8);
|
||||
var newSector = (int)(galacticCoordinate - newQuadrant * 8);
|
||||
|
||||
if (newSector == -1)
|
||||
{
|
||||
newQuadrant -= 1;
|
||||
newSector = 7;
|
||||
}
|
||||
|
||||
return newQuadrant switch
|
||||
{
|
||||
< 0 => (false, 0, 0),
|
||||
> 7 => (false, 7, 7),
|
||||
_ => (true, newQuadrant, newSector)
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,17 +1,37 @@
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
|
||||
using static System.StringSplitOptions;
|
||||
|
||||
namespace SuperStarTrek.Space
|
||||
{
|
||||
internal class Galaxy
|
||||
{
|
||||
private static readonly string[] _regionNames;
|
||||
private static readonly string[] _subRegionIdentifiers;
|
||||
private readonly QuadrantInfo[][] _quadrants;
|
||||
private readonly Random _random;
|
||||
|
||||
public Galaxy()
|
||||
static Galaxy()
|
||||
{
|
||||
var random = new Random();
|
||||
_regionNames = Strings.RegionNames.Split(new[] { ' ', '\n' }, RemoveEmptyEntries | TrimEntries);
|
||||
_subRegionIdentifiers = new[] { "I", "II", "III", "IV" };
|
||||
}
|
||||
|
||||
_quadrants = Enumerable.Range(1, 8).Select(x =>
|
||||
Enumerable.Range(1, 8).Select(y => QuadrantInfo.Create(new Coordinates(x, y), "")).ToArray())
|
||||
public Galaxy(Random random)
|
||||
{
|
||||
_random = random;
|
||||
|
||||
_quadrants = Enumerable
|
||||
.Range(0, 8)
|
||||
.Select(x => Enumerable
|
||||
.Range(0, 8)
|
||||
.Select(y => new Coordinates(x, y))
|
||||
.Select(c => QuadrantInfo.Create(c, GetQuadrantName(c)))
|
||||
.ToArray())
|
||||
.ToArray();
|
||||
|
||||
if (StarbaseCount == 0)
|
||||
@@ -26,9 +46,22 @@ namespace SuperStarTrek.Space
|
||||
}
|
||||
}
|
||||
|
||||
public QuadrantInfo this[Coordinates coordinate] => _quadrants[coordinate.X - 1][coordinate.Y - 1];
|
||||
public QuadrantInfo this[Coordinates coordinate] => _quadrants[coordinate.X][coordinate.Y];
|
||||
|
||||
public int KlingonCount => _quadrants.SelectMany(q => q).Sum(q => q.KlingonCount);
|
||||
public int StarbaseCount => _quadrants.SelectMany(q => q).Count(q => q.HasStarbase);
|
||||
public IEnumerable<IEnumerable<QuadrantInfo>> Quadrants => _quadrants;
|
||||
|
||||
private static string GetQuadrantName(Coordinates coordinates) =>
|
||||
$"{_regionNames[coordinates.RegionIndex]} {_subRegionIdentifiers[coordinates.SubRegionIndex]}";
|
||||
|
||||
public IEnumerable<IEnumerable<QuadrantInfo>> GetNeighborhood(Quadrant quadrant) =>
|
||||
Enumerable.Range(-1, 3)
|
||||
.Select(dx => dx + quadrant.Coordinates.X)
|
||||
.Select(x => GetNeighborhoodRow(quadrant, x));
|
||||
private IEnumerable<QuadrantInfo> GetNeighborhoodRow(Quadrant quadrant, int x) =>
|
||||
Enumerable.Range(-1, 3)
|
||||
.Select(dy => dy + quadrant.Coordinates.Y)
|
||||
.Select(y => y < 0 || y > 7 || x < 0 || x > 7 ? null : _quadrants[x][y]);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
|
||||
namespace SuperStarTrek.Space
|
||||
{
|
||||
@@ -10,42 +12,56 @@ namespace SuperStarTrek.Space
|
||||
private readonly QuadrantInfo _info;
|
||||
private readonly Random _random;
|
||||
private readonly Dictionary<Coordinates, object> _sectors;
|
||||
private readonly Coordinates _enterpriseSector;
|
||||
private readonly Coordinates _starbaseSector;
|
||||
private readonly Enterprise _enterprise;
|
||||
private readonly Output _output;
|
||||
private bool _displayed = false;
|
||||
|
||||
public Quadrant(QuadrantInfo info, Enterprise enterprise)
|
||||
public Quadrant(
|
||||
QuadrantInfo info,
|
||||
Enterprise enterprise,
|
||||
Random random,
|
||||
Galaxy galaxy,
|
||||
Input input,
|
||||
Output output)
|
||||
{
|
||||
_info = info;
|
||||
_random = new Random();
|
||||
_random = random;
|
||||
_output = output;
|
||||
Galaxy = galaxy;
|
||||
|
||||
_enterpriseSector = enterprise.Sector;
|
||||
_sectors = new Dictionary<Coordinates, object> { [enterprise.Sector] = enterprise };
|
||||
PositionObject(() => new Klingon(), _info.KlingonCount);
|
||||
info.MarkAsKnown();
|
||||
_sectors = new() { [enterprise.SectorCoordinates] = _enterprise = enterprise };
|
||||
PositionObject(sector => new Klingon(sector, _random), _info.KlingonCount);
|
||||
if (_info.HasStarbase)
|
||||
{
|
||||
_starbaseSector = PositionObject(() => new Starbase());
|
||||
Starbase = PositionObject(sector => new Starbase(sector, _random, input, output));
|
||||
}
|
||||
PositionObject(() => new Star(), _info.StarCount);
|
||||
PositionObject(_ => new Star(), _info.StarCount);
|
||||
}
|
||||
|
||||
public Coordinates Coordinates => _info.Coordinates;
|
||||
public bool HasKlingons => _info.KlingonCount > 0;
|
||||
public int KlingonCount => _info.KlingonCount;
|
||||
public bool HasStarbase => _info.HasStarbase;
|
||||
public Starbase Starbase { get; }
|
||||
internal Galaxy Galaxy { get; }
|
||||
public bool EnterpriseIsNextToStarbase =>
|
||||
_info.HasStarbase &&
|
||||
Math.Abs(_enterpriseSector.X - _starbaseSector.X) <= 1 &&
|
||||
Math.Abs(_enterpriseSector.Y - _starbaseSector.Y) <= 1;
|
||||
Math.Abs(_enterprise.SectorCoordinates.X - Starbase.Sector.X) <= 1 &&
|
||||
Math.Abs(_enterprise.SectorCoordinates.Y - Starbase.Sector.Y) <= 1;
|
||||
|
||||
internal IEnumerable<Klingon> Klingons => _sectors.Values.OfType<Klingon>();
|
||||
|
||||
public override string ToString() => _info.Name;
|
||||
|
||||
private Coordinates PositionObject(Func<object> objectFactory)
|
||||
private T PositionObject<T>(Func<Coordinates, T> objectFactory)
|
||||
{
|
||||
var sector = GetRandomEmptySector();
|
||||
_sectors[sector] = objectFactory.Invoke();
|
||||
return sector;
|
||||
_sectors[sector] = objectFactory.Invoke(sector);
|
||||
return (T)_sectors[sector];
|
||||
}
|
||||
|
||||
private void PositionObject(Func<object> objectFactory, int count)
|
||||
private void PositionObject(Func<Coordinates, object> objectFactory, int count)
|
||||
{
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
@@ -53,6 +69,91 @@ namespace SuperStarTrek.Space
|
||||
}
|
||||
}
|
||||
|
||||
internal void Display(string textFormat)
|
||||
{
|
||||
if (_displayed) { return; }
|
||||
|
||||
_output.Write(textFormat, this);
|
||||
|
||||
if (_info.KlingonCount > 0)
|
||||
{
|
||||
_output.Write(Strings.CombatArea);
|
||||
if (_enterprise.ShieldControl.ShieldEnergy <= 200) { _output.Write(Strings.LowShields); }
|
||||
}
|
||||
|
||||
_enterprise.Execute(Command.SRS);
|
||||
|
||||
_displayed = true;
|
||||
}
|
||||
|
||||
internal bool HasObjectAt(Coordinates coordinates) => _sectors.ContainsKey(coordinates);
|
||||
|
||||
internal bool TorpedoCollisionAt(Coordinates coordinates, out string message, out bool gameOver)
|
||||
{
|
||||
gameOver = false;
|
||||
message = default;
|
||||
|
||||
switch (_sectors.GetValueOrDefault(coordinates))
|
||||
{
|
||||
case Klingon klingon:
|
||||
message = Remove(klingon);
|
||||
gameOver = Galaxy.KlingonCount == 0;
|
||||
return true;
|
||||
|
||||
case Star _:
|
||||
message = $"Star at {coordinates} absorbed torpedo energy.";
|
||||
return true;
|
||||
|
||||
case Starbase _:
|
||||
_sectors.Remove(coordinates);
|
||||
_info.RemoveStarbase();
|
||||
message = "*** Starbase destroyed ***" +
|
||||
(Galaxy.StarbaseCount > 0 ? Strings.CourtMartial : Strings.RelievedOfCommand);
|
||||
gameOver = Galaxy.StarbaseCount == 0;
|
||||
return true;
|
||||
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
internal string Remove(Klingon klingon)
|
||||
{
|
||||
_sectors.Remove(klingon.Sector);
|
||||
_info.RemoveKlingon();
|
||||
return "*** Klingon destroyed ***";
|
||||
}
|
||||
|
||||
internal CommandResult KlingonsMoveAndFire()
|
||||
{
|
||||
foreach (var klingon in Klingons.ToList())
|
||||
{
|
||||
var newSector = GetRandomEmptySector();
|
||||
_sectors.Remove(klingon.Sector);
|
||||
_sectors[newSector] = klingon;
|
||||
klingon.MoveTo(newSector);
|
||||
}
|
||||
|
||||
return KlingonsFireOnEnterprise();
|
||||
}
|
||||
|
||||
internal CommandResult KlingonsFireOnEnterprise()
|
||||
{
|
||||
if (EnterpriseIsNextToStarbase && Klingons.Any())
|
||||
{
|
||||
Starbase.ProtectEnterprise();
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
foreach (var klingon in Klingons)
|
||||
{
|
||||
var result = klingon.FireOn(_enterprise);
|
||||
if (result.IsGameOver) { return result; }
|
||||
}
|
||||
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
private Coordinates GetRandomEmptySector()
|
||||
{
|
||||
while (true)
|
||||
@@ -65,15 +166,21 @@ namespace SuperStarTrek.Space
|
||||
}
|
||||
}
|
||||
|
||||
public IEnumerable<string> GetDisplayLines() => Enumerable.Range(1, 8).Select(x => GetDisplayLine(x));
|
||||
public IEnumerable<string> GetDisplayLines() => Enumerable.Range(0, 8).Select(x => GetDisplayLine(x));
|
||||
|
||||
private string GetDisplayLine(int x)
|
||||
=> string.Join(
|
||||
" ",
|
||||
Enumerable
|
||||
.Range(1, 8)
|
||||
.Range(0, 8)
|
||||
.Select(y => new Coordinates(x, y))
|
||||
.Select(c => _sectors.GetValueOrDefault(c))
|
||||
.Select(o => o?.ToString() ?? " "));
|
||||
|
||||
internal void SetEnterpriseSector(Coordinates sector)
|
||||
{
|
||||
_sectors.Remove(_enterprise.SectorCoordinates);
|
||||
_sectors[sector] = _enterprise;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,7 +1,11 @@
|
||||
using SuperStarTrek.Objects;
|
||||
|
||||
namespace SuperStarTrek.Space
|
||||
{
|
||||
internal class QuadrantInfo
|
||||
{
|
||||
private bool _isKnown;
|
||||
|
||||
private QuadrantInfo(Coordinates coordinates, string name, int klingonCount, int starCount, bool hasStarbase)
|
||||
{
|
||||
Coordinates = coordinates;
|
||||
@@ -20,14 +24,14 @@ namespace SuperStarTrek.Space
|
||||
public static QuadrantInfo Create(Coordinates coordinates, string name)
|
||||
{
|
||||
var random = new Random();
|
||||
var klingonCount = random.GetDouble() switch
|
||||
var klingonCount = random.GetFloat() switch
|
||||
{
|
||||
> 0.98 => 3,
|
||||
> 0.95 => 2,
|
||||
> 0.80 => 1,
|
||||
> 0.98f => 3,
|
||||
> 0.95f => 2,
|
||||
> 0.80f => 1,
|
||||
_ => 0
|
||||
};
|
||||
var hasStarbase = random.GetDouble() > 0.96;
|
||||
var hasStarbase = random.GetFloat() > 0.96f;
|
||||
var starCount = random.Get1To8Inclusive();
|
||||
|
||||
return new QuadrantInfo(coordinates, name, klingonCount, starCount, hasStarbase);
|
||||
@@ -36,5 +40,25 @@ namespace SuperStarTrek.Space
|
||||
internal void AddKlingon() => KlingonCount += 1;
|
||||
|
||||
internal void AddStarbase() => HasStarbase = true;
|
||||
|
||||
internal void MarkAsKnown() => _isKnown = true;
|
||||
|
||||
internal string Scan()
|
||||
{
|
||||
_isKnown = true;
|
||||
return ToString();
|
||||
}
|
||||
|
||||
public override string ToString() => _isKnown ? $"{KlingonCount}{(HasStarbase ? 1 : 0)}{StarCount}" : "***";
|
||||
|
||||
internal void RemoveKlingon()
|
||||
{
|
||||
if (KlingonCount > 0)
|
||||
{
|
||||
KlingonCount -= 1;
|
||||
}
|
||||
}
|
||||
|
||||
internal void RemoveStarbase() => HasStarbase = false;
|
||||
}
|
||||
}
|
||||
|
||||
7
84 Super Star Trek/csharp/StringExtensions.cs
Normal file
7
84 Super Star Trek/csharp/StringExtensions.cs
Normal file
@@ -0,0 +1,7 @@
|
||||
namespace SuperStarTrek
|
||||
{
|
||||
internal static class StringExtensions
|
||||
{
|
||||
internal static string Pluralize(this string singular, int quantity) => singular + (quantity > 1 ? "s" : "");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal abstract class ComputerFunction
|
||||
{
|
||||
protected ComputerFunction(string description, Output output)
|
||||
{
|
||||
Description = description;
|
||||
Output = output;
|
||||
}
|
||||
|
||||
internal string Description { get; }
|
||||
protected Output Output { get; }
|
||||
|
||||
internal abstract void Execute(Quadrant quadrant);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal class CumulativeGalacticRecord : GalacticReport
|
||||
{
|
||||
internal CumulativeGalacticRecord(Output output, Galaxy galaxy)
|
||||
: base("Cumulative galactic record", output, galaxy)
|
||||
{
|
||||
}
|
||||
|
||||
protected override void WriteHeader(Quadrant quadrant) =>
|
||||
Output.NextLine().WriteLine($"Computer record of galaxy for quadrant {quadrant.Coordinates}").NextLine();
|
||||
|
||||
protected override IEnumerable<string> GetRowData() =>
|
||||
Galaxy.Quadrants.Select(row => " " + string.Join(" ", row));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal class DirectionDistanceCalculator : NavigationCalculator
|
||||
{
|
||||
private readonly Enterprise _enterprise;
|
||||
private readonly Input _input;
|
||||
|
||||
public DirectionDistanceCalculator(Enterprise enterprise, Output output, Input input)
|
||||
: base("Starbase nav data", output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
_input = input;
|
||||
}
|
||||
|
||||
internal override void Execute(Quadrant quadrant)
|
||||
{
|
||||
Output.WriteLine("Direction/distance calculator:")
|
||||
.Write($"You are at quadrant {_enterprise.QuadrantCoordinates}")
|
||||
.WriteLine($" sector {_enterprise.SectorCoordinates}")
|
||||
.WriteLine("Please enter");
|
||||
|
||||
WriteDirectionAndDistance(
|
||||
_input.GetCoordinates(" Initial coordinates"),
|
||||
_input.GetCoordinates(" Final coordinates"));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal abstract class GalacticReport : ComputerFunction
|
||||
{
|
||||
public GalacticReport(string description, Output output, Galaxy galaxy)
|
||||
: base(description, output)
|
||||
{
|
||||
Galaxy = galaxy;
|
||||
}
|
||||
|
||||
protected Galaxy Galaxy { get; }
|
||||
|
||||
protected abstract void WriteHeader(Quadrant quadrant);
|
||||
|
||||
protected abstract IEnumerable<string> GetRowData();
|
||||
|
||||
internal sealed override void Execute(Quadrant quadrant)
|
||||
{
|
||||
WriteHeader(quadrant);
|
||||
Output.WriteLine(" 1 2 3 4 5 6 7 8")
|
||||
.WriteLine(" ----- ----- ----- ----- ----- ----- ----- -----");
|
||||
|
||||
foreach (var (row, index) in GetRowData().Select((r, i) => (r, i)))
|
||||
{
|
||||
Output.WriteLine($" {index+1} {row}")
|
||||
.WriteLine(" ----- ----- ----- ----- ----- ----- ----- -----");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal class GalaxyRegionMap : GalacticReport
|
||||
{
|
||||
internal GalaxyRegionMap(Output output, Galaxy galaxy)
|
||||
: base("Galaxy 'region name' map", output, galaxy)
|
||||
{
|
||||
}
|
||||
|
||||
protected override void WriteHeader(Quadrant quadrant) =>
|
||||
Output.WriteLine(" The Galaxy");
|
||||
|
||||
protected override IEnumerable<string> GetRowData() =>
|
||||
Strings.RegionNames.Split('\n').Select(n => n.TrimEnd('\r'));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
using SuperStarTrek.Space;
|
||||
using SuperStarTrek.Utils;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal abstract class NavigationCalculator : ComputerFunction
|
||||
{
|
||||
protected NavigationCalculator(string description, Output output)
|
||||
: base(description, output)
|
||||
{
|
||||
}
|
||||
|
||||
protected void WriteDirectionAndDistance(Coordinates from, Coordinates to)
|
||||
{
|
||||
var (direction, distance) = from.GetDirectionAndDistanceTo(to);
|
||||
Write(direction, distance);
|
||||
}
|
||||
|
||||
protected void WriteDirectionAndDistance((float X, float Y) from, (float X, float Y) to)
|
||||
{
|
||||
var (direction, distance) = DirectionAndDistance.From(from.X, from.Y).To(to.X, to.Y);
|
||||
Write(direction, distance);
|
||||
}
|
||||
|
||||
private void Write(float direction, float distance) =>
|
||||
Output.WriteLine($"Direction = {direction}")
|
||||
.WriteLine($"Distance = {distance}");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal class StarbaseDataCalculator : NavigationCalculator
|
||||
{
|
||||
private readonly Enterprise _enterprise;
|
||||
|
||||
public StarbaseDataCalculator(Enterprise enterprise, Output output)
|
||||
: base("Starbase nav data", output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
}
|
||||
|
||||
internal override void Execute(Quadrant quadrant)
|
||||
{
|
||||
if (!quadrant.HasStarbase)
|
||||
{
|
||||
Output.WriteLine(Strings.NoStarbase);
|
||||
return;
|
||||
}
|
||||
|
||||
Output.WriteLine("From Enterprise to Starbase:");
|
||||
|
||||
WriteDirectionAndDistance(_enterprise.SectorCoordinates, quadrant.Starbase.Sector);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal class StatusReport : ComputerFunction
|
||||
{
|
||||
private readonly Game _game;
|
||||
private readonly Galaxy _galaxy;
|
||||
private readonly Enterprise _enterprise;
|
||||
|
||||
public StatusReport(Game game, Galaxy galaxy, Enterprise enterprise, Output output)
|
||||
: base("Status report", output)
|
||||
{
|
||||
_game = game;
|
||||
_galaxy = galaxy;
|
||||
_enterprise = enterprise;
|
||||
}
|
||||
|
||||
internal override void Execute(Quadrant quadrant)
|
||||
{
|
||||
Output.WriteLine(" Status report:")
|
||||
.Write("Klingon".Pluralize(_galaxy.KlingonCount)).WriteLine($" left: {_galaxy.KlingonCount}")
|
||||
.WriteLine($"Mission must be completed in {_game.StardatesRemaining:0.#} stardates.");
|
||||
|
||||
if (_galaxy.StarbaseCount > 0)
|
||||
{
|
||||
Output.Write($"The Federation is maintaining {_galaxy.StarbaseCount} ")
|
||||
.Write("starbase".Pluralize(_galaxy.StarbaseCount)).WriteLine(" in the galaxy.");
|
||||
}
|
||||
else
|
||||
{
|
||||
Output.WriteLine("Your stupidity has left you on your own in")
|
||||
.WriteLine(" the galaxy -- you have no starbases left!");
|
||||
}
|
||||
|
||||
_enterprise.Execute(Command.DAM);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems.ComputerFunctions
|
||||
{
|
||||
internal class TorpedoDataCalculator : NavigationCalculator
|
||||
{
|
||||
private readonly Enterprise _enterprise;
|
||||
|
||||
public TorpedoDataCalculator(Enterprise enterprise, Output output)
|
||||
: base("Photon torpedo data", output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
}
|
||||
|
||||
internal override void Execute(Quadrant quadrant)
|
||||
{
|
||||
if (!quadrant.HasKlingons)
|
||||
{
|
||||
Output.WriteLine(Strings.NoEnemyShips);
|
||||
return;
|
||||
}
|
||||
|
||||
Output.WriteLine("From Enterprise to Klingon battle cruiser".Pluralize(quadrant.KlingonCount));
|
||||
|
||||
foreach (var klingon in quadrant.Klingons)
|
||||
{
|
||||
WriteDirectionAndDistance(_enterprise.SectorCoordinates, klingon.Sector);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
54
84 Super Star Trek/csharp/Systems/DamageControl.cs
Normal file
54
84 Super Star Trek/csharp/Systems/DamageControl.cs
Normal file
@@ -0,0 +1,54 @@
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems
|
||||
{
|
||||
internal class DamageControl : Subsystem
|
||||
{
|
||||
private readonly Enterprise _enterprise;
|
||||
private readonly Output _output;
|
||||
|
||||
public DamageControl(Enterprise enterprise, Output output)
|
||||
: base("Damage Control", Command.DAM, output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
_output = output;
|
||||
}
|
||||
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
if (IsDamaged)
|
||||
{
|
||||
_output.WriteLine("Damage Control report not available");
|
||||
}
|
||||
else
|
||||
{
|
||||
_output.NextLine();
|
||||
WriteDamageReport();
|
||||
}
|
||||
|
||||
if (_enterprise.DamagedSystemCount > 0 && _enterprise.IsDocked)
|
||||
{
|
||||
if (quadrant.Starbase.TryRepair(_enterprise, out var repairTime))
|
||||
{
|
||||
WriteDamageReport();
|
||||
return CommandResult.Elapsed(repairTime);
|
||||
}
|
||||
}
|
||||
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
public void WriteDamageReport()
|
||||
{
|
||||
_output.NextLine().WriteLine("Device State of Repair");
|
||||
foreach (var system in _enterprise.Systems)
|
||||
{
|
||||
_output.Write(system.Name.PadRight(25))
|
||||
.WriteLine(((int)(system.Condition * 100) * 0.01).ToString(" 0.##;-0.##"));
|
||||
}
|
||||
_output.NextLine();
|
||||
}
|
||||
}
|
||||
}
|
||||
47
84 Super Star Trek/csharp/Systems/LibraryComputer.cs
Normal file
47
84 Super Star Trek/csharp/Systems/LibraryComputer.cs
Normal file
@@ -0,0 +1,47 @@
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Space;
|
||||
using SuperStarTrek.Systems.ComputerFunctions;
|
||||
|
||||
namespace SuperStarTrek.Systems
|
||||
{
|
||||
internal class LibraryComputer : Subsystem
|
||||
{
|
||||
private readonly Output _output;
|
||||
private readonly Input _input;
|
||||
private readonly ComputerFunction[] _functions;
|
||||
|
||||
public LibraryComputer(Output output, Input input, params ComputerFunction[] functions)
|
||||
: base("Library-Computer", Command.COM, output)
|
||||
{
|
||||
_output = output;
|
||||
_input = input;
|
||||
_functions = functions;
|
||||
}
|
||||
|
||||
protected override bool CanExecuteCommand() => IsOperational("Computer disabled");
|
||||
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
var index = GetFunctionIndex();
|
||||
_output.NextLine();
|
||||
|
||||
_functions[index].Execute(quadrant);
|
||||
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
private int GetFunctionIndex()
|
||||
{
|
||||
while (true)
|
||||
{
|
||||
var index = (int)_input.GetNumber("Computer active and waiting command");
|
||||
if (index >= 0 && index <= 5) { return index; }
|
||||
|
||||
for (int i = 0; i < _functions.Length; i++)
|
||||
{
|
||||
_output.WriteLine($" {i} = {_functions[i].Description}");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
39
84 Super Star Trek/csharp/Systems/LongRangeSensors.cs
Normal file
39
84 Super Star Trek/csharp/Systems/LongRangeSensors.cs
Normal file
@@ -0,0 +1,39 @@
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems
|
||||
{
|
||||
internal class LongRangeSensors : Subsystem
|
||||
{
|
||||
private readonly Galaxy _galaxy;
|
||||
private readonly Output _output;
|
||||
|
||||
public LongRangeSensors(Galaxy galaxy, Output output)
|
||||
: base("Long Range Sensors", Command.LRS, output)
|
||||
{
|
||||
_galaxy = galaxy;
|
||||
_output = output;
|
||||
}
|
||||
|
||||
protected override bool CanExecuteCommand() => IsOperational("{name} are inoperable");
|
||||
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
_output.WriteLine($"Long range scan for quadrant {quadrant.Coordinates}");
|
||||
_output.WriteLine("-------------------");
|
||||
foreach (var quadrants in _galaxy.GetNeighborhood(quadrant))
|
||||
{
|
||||
_output.WriteLine(": " + string.Join(" : ", quadrants.Select(q => q?.Scan() ?? "***")) + " :");
|
||||
_output.WriteLine("-------------------");
|
||||
}
|
||||
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
}
|
||||
}
|
||||
97
84 Super Star Trek/csharp/Systems/PhaserControl.cs
Normal file
97
84 Super Star Trek/csharp/Systems/PhaserControl.cs
Normal file
@@ -0,0 +1,97 @@
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems
|
||||
{
|
||||
internal class PhaserControl : Subsystem
|
||||
{
|
||||
private readonly Enterprise _enterprise;
|
||||
private readonly Output _output;
|
||||
private readonly Input _input;
|
||||
private readonly Random _random;
|
||||
|
||||
public PhaserControl(Enterprise enterprise, Output output, Input input, Random random)
|
||||
: base("Phaser Control", Command.PHA, output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
_output = output;
|
||||
_input = input;
|
||||
_random = random;
|
||||
}
|
||||
|
||||
protected override bool CanExecuteCommand() => IsOperational("Phasers inoperative");
|
||||
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
if (!quadrant.HasKlingons)
|
||||
{
|
||||
_output.WriteLine(Strings.NoEnemyShips);
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
if (_enterprise.Computer.IsDamaged)
|
||||
{
|
||||
_output.WriteLine("Computer failure hampers accuracy");
|
||||
}
|
||||
|
||||
_output.Write($"Phasers locked on target; ");
|
||||
|
||||
var phaserStrength = GetPhaserStrength();
|
||||
if (phaserStrength < 0) { return CommandResult.Ok; }
|
||||
|
||||
_enterprise.UseEnergy(phaserStrength);
|
||||
|
||||
var perEnemyStrength = GetPerTargetPhaserStrength(phaserStrength, quadrant.KlingonCount);
|
||||
|
||||
foreach (var klingon in quadrant.Klingons.ToList())
|
||||
{
|
||||
ResolveHitOn(klingon, perEnemyStrength, quadrant);
|
||||
}
|
||||
|
||||
return quadrant.KlingonsFireOnEnterprise();
|
||||
}
|
||||
|
||||
private float GetPhaserStrength()
|
||||
{
|
||||
while (true)
|
||||
{
|
||||
_output.WriteLine($"Energy available = {_enterprise.Energy} units");
|
||||
var phaserStrength = _input.GetNumber("Number of units to fire");
|
||||
|
||||
if (phaserStrength <= _enterprise.Energy) { return phaserStrength; }
|
||||
}
|
||||
}
|
||||
|
||||
private float GetPerTargetPhaserStrength(float phaserStrength, int targetCount)
|
||||
{
|
||||
if (_enterprise.Computer.IsDamaged)
|
||||
{
|
||||
phaserStrength *= _random.GetFloat();
|
||||
}
|
||||
|
||||
return phaserStrength / targetCount;
|
||||
}
|
||||
|
||||
private void ResolveHitOn(Klingon klingon, float perEnemyStrength, Quadrant quadrant)
|
||||
{
|
||||
var distance = _enterprise.SectorCoordinates.GetDistanceTo(klingon.Sector);
|
||||
var hitStrength = (int)(perEnemyStrength / distance * (2 + _random.GetFloat()));
|
||||
|
||||
if (klingon.TakeHit(hitStrength))
|
||||
{
|
||||
_output.WriteLine($"{hitStrength} unit hit on Klingon at sector {klingon.Sector}");
|
||||
_output.WriteLine(
|
||||
klingon.Energy <= 0
|
||||
? quadrant.Remove(klingon)
|
||||
: $" (sensors show {klingon.Energy} units remaining)");
|
||||
}
|
||||
else
|
||||
{
|
||||
_output.WriteLine($"Sensors show no damage to enemy at {klingon.Sector}");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
66
84 Super Star Trek/csharp/Systems/PhotonTubes.cs
Normal file
66
84 Super Star Trek/csharp/Systems/PhotonTubes.cs
Normal file
@@ -0,0 +1,66 @@
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems
|
||||
{
|
||||
internal class PhotonTubes : Subsystem
|
||||
{
|
||||
private readonly int _tubeCount;
|
||||
private readonly Enterprise _enterprise;
|
||||
private readonly Output _output;
|
||||
private readonly Input _input;
|
||||
|
||||
public PhotonTubes(int tubeCount, Enterprise enterprise, Output output, Input input)
|
||||
: base("Photon Tubes", Command.TOR, output)
|
||||
{
|
||||
TorpedoCount = _tubeCount = tubeCount;
|
||||
_enterprise = enterprise;
|
||||
_output = output;
|
||||
_input = input;
|
||||
}
|
||||
|
||||
public int TorpedoCount { get; private set; }
|
||||
|
||||
protected override bool CanExecuteCommand() => HasTorpedoes() && IsOperational("{name} are not operational");
|
||||
|
||||
private bool HasTorpedoes()
|
||||
{
|
||||
if (TorpedoCount > 0) { return true; }
|
||||
|
||||
_output.WriteLine("All photon torpedoes expended");
|
||||
return false;
|
||||
}
|
||||
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
if (!_input.TryGetCourse("Photon torpedo course", "Ensign Chekov", out var course))
|
||||
{
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
TorpedoCount -= 1;
|
||||
|
||||
var isHit = false;
|
||||
_output.WriteLine("Torpedo track:");
|
||||
foreach (var sector in course.GetSectorsFrom(_enterprise.SectorCoordinates))
|
||||
{
|
||||
_output.WriteLine($" {sector}");
|
||||
|
||||
if (quadrant.TorpedoCollisionAt(sector, out var message, out var gameOver))
|
||||
{
|
||||
_output.WriteLine(message);
|
||||
isHit = true;
|
||||
if (gameOver) { return CommandResult.GameOver; }
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!isHit) { _output.WriteLine("Torpedo missed!"); }
|
||||
|
||||
return quadrant.KlingonsFireOnEnterprise();
|
||||
}
|
||||
|
||||
internal void ReplenishTorpedoes() => TorpedoCount = _tubeCount;
|
||||
}
|
||||
}
|
||||
@@ -1,3 +1,4 @@
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
@@ -10,36 +11,35 @@ namespace SuperStarTrek.Systems
|
||||
private readonly Input _input;
|
||||
|
||||
public ShieldControl(Enterprise enterprise, Output output, Input input)
|
||||
: base("Shield Control", Command.SHE)
|
||||
: base("Shield Control", Command.SHE, output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
_output = output;
|
||||
_input = input;
|
||||
}
|
||||
|
||||
public double Energy { get; private set; }
|
||||
public float ShieldEnergy { get; set; }
|
||||
|
||||
public override void ExecuteCommand(Quadrant quadrant)
|
||||
protected override bool CanExecuteCommand() => IsOperational("{name} inoperable");
|
||||
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
if (Condition < 0)
|
||||
{
|
||||
_output.WriteLine("Shield Control inoperable");
|
||||
return;
|
||||
}
|
||||
|
||||
_output.WriteLine($"Energy available = {_enterprise.TotalEnergy}");
|
||||
var requested = _input.GetNumber($"Number of units to shields");
|
||||
|
||||
if (Validate(requested))
|
||||
{
|
||||
Energy = requested;
|
||||
return;
|
||||
ShieldEnergy = requested;
|
||||
}
|
||||
else
|
||||
{
|
||||
_output.WriteLine("<SHIELDS UNCHANGED>");
|
||||
}
|
||||
|
||||
_output.WriteLine("<SHIELDS UNCHANGED>");
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
private bool Validate(double requested)
|
||||
private bool Validate(float requested)
|
||||
{
|
||||
if (requested > _enterprise.TotalEnergy)
|
||||
{
|
||||
@@ -47,7 +47,11 @@ namespace SuperStarTrek.Systems
|
||||
return false;
|
||||
}
|
||||
|
||||
return requested >= 0 && requested != Energy;
|
||||
return requested >= 0 && requested != ShieldEnergy;
|
||||
}
|
||||
|
||||
internal void AbsorbHit(int hitStrength) => ShieldEnergy -= hitStrength;
|
||||
|
||||
internal void DropShields() => ShieldEnergy = 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Resources;
|
||||
using SuperStarTrek.Space;
|
||||
@@ -16,7 +17,7 @@ namespace SuperStarTrek.Systems
|
||||
private readonly Output _output;
|
||||
|
||||
public ShortRangeSensors(Enterprise enterprise, Galaxy galaxy, Game game, Output output)
|
||||
: base("Short Range Sensors", Command.SRS)
|
||||
: base("Short Range Sensors", Command.SRS, output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
_galaxy = galaxy;
|
||||
@@ -24,7 +25,7 @@ namespace SuperStarTrek.Systems
|
||||
_output = output;
|
||||
}
|
||||
|
||||
public override void ExecuteCommand(Quadrant quadrant)
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
if (_enterprise.IsDocked)
|
||||
{
|
||||
@@ -42,17 +43,19 @@ namespace SuperStarTrek.Systems
|
||||
.ToList()
|
||||
.ForEach(l => _output.WriteLine(l));
|
||||
_output.WriteLine("---------------------------------");
|
||||
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
public IEnumerable<string> GetStatusLines()
|
||||
{
|
||||
yield return $"Stardate {_game.Stardate}";
|
||||
yield return $"Condition {_enterprise.Condition}";
|
||||
yield return $"Quadrant {_enterprise.Quadrant}";
|
||||
yield return $"Sector {_enterprise.Sector}";
|
||||
yield return $"Photon torpedoes {_enterprise.TorpedoCount}";
|
||||
yield return $"Total energy {Math.Ceiling(_enterprise.Energy)}";
|
||||
yield return $"Shields {(int)_enterprise.Shields}";
|
||||
yield return $"Quadrant {_enterprise.QuadrantCoordinates}";
|
||||
yield return $"Sector {_enterprise.SectorCoordinates}";
|
||||
yield return $"Photon torpedoes {_enterprise.PhotonTubes.TorpedoCount}";
|
||||
yield return $"Total energy {Math.Ceiling(_enterprise.TotalEnergy)}";
|
||||
yield return $"Shields {(int)_enterprise.ShieldControl.ShieldEnergy}";
|
||||
yield return $"Klingons remaining {_galaxy.KlingonCount}";
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,20 +1,66 @@
|
||||
using System;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems
|
||||
{
|
||||
internal abstract class Subsystem
|
||||
{
|
||||
protected Subsystem(string name, Command command)
|
||||
private readonly Output _output;
|
||||
|
||||
protected Subsystem(string name, Command command, Output output)
|
||||
{
|
||||
Name = name;
|
||||
Command = command;
|
||||
Condition = 0;
|
||||
_output = output;
|
||||
}
|
||||
|
||||
public string Name { get; }
|
||||
public double Condition { get; }
|
||||
public float Condition { get; private set; }
|
||||
public bool IsDamaged => Condition < 0;
|
||||
public Command Command { get; }
|
||||
|
||||
public abstract void ExecuteCommand(Quadrant quadrant);
|
||||
protected virtual bool CanExecuteCommand() => true;
|
||||
|
||||
protected bool IsOperational(string notOperationalMessage)
|
||||
{
|
||||
if (IsDamaged)
|
||||
{
|
||||
_output.WriteLine(notOperationalMessage.Replace("{name}", Name));
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public CommandResult ExecuteCommand(Quadrant quadrant)
|
||||
=> CanExecuteCommand() ? ExecuteCommandCore(quadrant) : CommandResult.Ok;
|
||||
|
||||
protected abstract CommandResult ExecuteCommandCore(Quadrant quadrant);
|
||||
|
||||
public virtual void Repair()
|
||||
{
|
||||
if (IsDamaged)
|
||||
{
|
||||
Condition = 0;
|
||||
}
|
||||
}
|
||||
|
||||
public virtual bool Repair(float repairWorkDone)
|
||||
{
|
||||
if (IsDamaged)
|
||||
{
|
||||
Condition += repairWorkDone;
|
||||
if (Condition > -0.1f && Condition < 0)
|
||||
{
|
||||
Condition = -0.1f;
|
||||
}
|
||||
}
|
||||
|
||||
return !IsDamaged;
|
||||
}
|
||||
|
||||
internal void TakeDamage(float damage) => Condition -= damage;
|
||||
}
|
||||
}
|
||||
|
||||
82
84 Super Star Trek/csharp/Systems/WarpEngines.cs
Normal file
82
84 Super Star Trek/csharp/Systems/WarpEngines.cs
Normal file
@@ -0,0 +1,82 @@
|
||||
using System;
|
||||
using SuperStarTrek.Commands;
|
||||
using SuperStarTrek.Objects;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Systems
|
||||
{
|
||||
internal class WarpEngines : Subsystem
|
||||
{
|
||||
private readonly Enterprise _enterprise;
|
||||
private readonly Output _output;
|
||||
private readonly Input _input;
|
||||
|
||||
public WarpEngines(Enterprise enterprise, Output output, Input input)
|
||||
: base("Warp Engines", Command.NAV, output)
|
||||
{
|
||||
_enterprise = enterprise;
|
||||
_output = output;
|
||||
_input = input;
|
||||
}
|
||||
|
||||
protected override CommandResult ExecuteCommandCore(Quadrant quadrant)
|
||||
{
|
||||
if (_input.TryGetCourse("Course", " Lt. Sulu", out var course) &&
|
||||
TryGetWarpFactor(out var warpFactor) &&
|
||||
TryGetDistanceToMove(warpFactor, out var distanceToMove))
|
||||
{
|
||||
var result = quadrant.KlingonsMoveAndFire();
|
||||
if (result.IsGameOver) { return result; }
|
||||
|
||||
_enterprise.RepairSystems(warpFactor);
|
||||
_enterprise.VaryConditionOfRandomSystem();
|
||||
var timeElapsed = _enterprise.Move(course, warpFactor, distanceToMove);
|
||||
|
||||
if (_enterprise.IsDocked)
|
||||
{
|
||||
_enterprise.ShieldControl.DropShields();
|
||||
_enterprise.Refuel();
|
||||
_enterprise.PhotonTubes.ReplenishTorpedoes();
|
||||
}
|
||||
|
||||
return CommandResult.Elapsed(timeElapsed);
|
||||
}
|
||||
|
||||
return CommandResult.Ok;
|
||||
}
|
||||
|
||||
private bool TryGetWarpFactor(out float warpFactor)
|
||||
{
|
||||
var maximumWarp = IsDamaged ? 0.2f : 8;
|
||||
if (_input.TryGetNumber("Warp Factor", 0, maximumWarp, out warpFactor))
|
||||
{
|
||||
return warpFactor > 0;
|
||||
}
|
||||
|
||||
_output.WriteLine(
|
||||
IsDamaged && warpFactor > maximumWarp
|
||||
? "Warp engines are damaged. Maximum speed = warp 0.2"
|
||||
: $" Chief Engineer Scott reports, 'The engines won't take warp {warpFactor} !'");
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private bool TryGetDistanceToMove(float warpFactor, out int distanceToTravel)
|
||||
{
|
||||
distanceToTravel = (int)Math.Round(warpFactor * 8, MidpointRounding.AwayFromZero);
|
||||
if (distanceToTravel <= _enterprise.Energy) { return true; }
|
||||
|
||||
_output.WriteLine("Engineering reports, 'Insufficient energy available")
|
||||
.WriteLine($" for maneuvering at warp {warpFactor} !'");
|
||||
|
||||
if (distanceToTravel <= _enterprise.TotalEnergy && !_enterprise.ShieldControl.IsDamaged)
|
||||
{
|
||||
_output.Write($"Deflector control room acknowledges {_enterprise.ShieldControl.ShieldEnergy} ")
|
||||
.WriteLine("units of energy")
|
||||
.WriteLine(" presently deployed to shields.");
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
65
84 Super Star Trek/csharp/Utils/DirectionAndDistance.cs
Normal file
65
84 Super Star Trek/csharp/Utils/DirectionAndDistance.cs
Normal file
@@ -0,0 +1,65 @@
|
||||
using System;
|
||||
using SuperStarTrek.Space;
|
||||
|
||||
namespace SuperStarTrek.Utils
|
||||
{
|
||||
internal class DirectionAndDistance
|
||||
{
|
||||
private readonly float _fromX;
|
||||
private readonly float _fromY;
|
||||
|
||||
private DirectionAndDistance(float fromX, float fromY)
|
||||
{
|
||||
_fromX = fromX;
|
||||
_fromY = fromY;
|
||||
}
|
||||
|
||||
public static DirectionAndDistance From(Coordinates coordinates) => From(coordinates.X, coordinates.Y);
|
||||
|
||||
public static DirectionAndDistance From(float x, float y) => new DirectionAndDistance(x, y);
|
||||
|
||||
public (float Direction, float Distance) To(Coordinates coordinates) => To(coordinates.X, coordinates.Y);
|
||||
|
||||
public (float Direction, float Distance) To(float x, float y)
|
||||
{
|
||||
var deltaX = x - _fromX;
|
||||
var deltaY = y - _fromY;
|
||||
|
||||
return (GetDirection(deltaX, deltaY), GetDistance(deltaX, deltaY));
|
||||
}
|
||||
|
||||
// The algorithm here is mathematically equivalent to the following code in the original,
|
||||
// where X is deltaY and A is deltaX
|
||||
// 8220 X=X-A:A=C1-W1:IFX<0THEN8350
|
||||
// 8250 IFA<0THEN8410
|
||||
// 8260 IFX>0THEN8280
|
||||
// 8270 IFA=0THENC1=5:GOTO8290
|
||||
// 8280 C1=1
|
||||
// 8290 IFABS(A)<=ABS(X)THEN8330
|
||||
// 8310 PRINT"DIRECTION =";C1+(((ABS(A)-ABS(X))+ABS(A))/ABS(A)):GOTO8460
|
||||
// 8330 PRINT"DIRECTION =";C1+(ABS(A)/ABS(X)):GOTO8460
|
||||
// 8350 IFA>0THENC1=3:GOTO8420
|
||||
// 8360 IFX<>0THENC1=5:GOTO8290
|
||||
// 8410 C1=7
|
||||
// 8420 IFABS(A)>=ABS(X)THEN8450
|
||||
// 8430 PRINT"DIRECTION =";C1+(((ABS(X)-ABS(A))+ABS(X))/ABS(X)):GOTO8460
|
||||
// 8450 PRINT"DIRECTION =";C1+(ABS(X)/ABS(A))
|
||||
// 8460 PRINT"DISTANCE =";SQR(X^2+A^2):IFH8=1THEN1990
|
||||
private float GetDirection(float deltaX, float deltaY)
|
||||
{
|
||||
var deltaXDominant = Math.Abs(deltaX) > Math.Abs(deltaY);
|
||||
var fractionalPart = deltaXDominant ? deltaY / deltaX : -deltaX / deltaY;
|
||||
var nearestCardinal = deltaXDominant switch
|
||||
{
|
||||
true => deltaX > 0 ? 7 : 3,
|
||||
false => deltaY > 0 ? 1 : 5
|
||||
};
|
||||
|
||||
var direction = nearestCardinal + fractionalPart;
|
||||
return direction < 1 ? direction + 8 : direction;
|
||||
}
|
||||
|
||||
private float GetDistance(float deltaX, float deltaY) =>
|
||||
(float)Math.Sqrt(Math.Pow(deltaX, 2) + Math.Pow(deltaY, 2));
|
||||
}
|
||||
}
|
||||
97
87 3-D Plot/java/Plot3D.java
Normal file
97
87 3-D Plot/java/Plot3D.java
Normal file
@@ -0,0 +1,97 @@
|
||||
import java.lang.Math;
|
||||
|
||||
/**
|
||||
* Game of 3-D Plot
|
||||
* <p>
|
||||
* Based on the BASIC game of 3-D Plot here
|
||||
* https://github.com/coding-horror/basic-computer-games/blob/main/87%203-D%20Plot/3dplot.bas
|
||||
* <p>
|
||||
* Note: The idea was to create a version of the 1970's BASIC game in Java, without introducing
|
||||
* new features - no additional text, error checking, etc has been added.
|
||||
*
|
||||
* Converted from BASIC to Java by Darren Cardenas.
|
||||
*/
|
||||
|
||||
// Java class names cannot begin with a letter, so class name 3dplot cannot be used
|
||||
public class Plot3D {
|
||||
|
||||
|
||||
public void play() {
|
||||
|
||||
showIntro();
|
||||
startGame();
|
||||
|
||||
} // End of method play
|
||||
|
||||
|
||||
private void showIntro() {
|
||||
|
||||
System.out.println(" ".repeat(31) + "3D PLOT");
|
||||
System.out.println(" ".repeat(14) + "CREATIVE COMPUTING MORRISTOWN, NEW JERSEY");
|
||||
System.out.println("\n\n\n");
|
||||
|
||||
} // End of method showIntro
|
||||
|
||||
|
||||
private void startGame() {
|
||||
|
||||
float row = 0;
|
||||
int column = 0;
|
||||
int limit = 0;
|
||||
int plotVal = 0;
|
||||
int root = 0;
|
||||
|
||||
String lineContent = "";
|
||||
|
||||
// Begin loop through all rows
|
||||
for (row = -30; row <= 30; row += 1.5) {
|
||||
|
||||
limit = 0;
|
||||
|
||||
root = 5 * (int) Math.floor((Math.sqrt(900 - row * row) / 5));
|
||||
|
||||
// Begin loop through all columns
|
||||
for (column = root; column >= -root; column += -5) {
|
||||
|
||||
plotVal = 25 + (int) Math.floor(func(Math.sqrt(row * row + column * column)) - 0.7 * column);
|
||||
|
||||
if (plotVal > limit) {
|
||||
|
||||
limit = plotVal;
|
||||
|
||||
// Add whitespace
|
||||
while (lineContent.length() < (plotVal-1)) {
|
||||
lineContent += " ";
|
||||
}
|
||||
|
||||
lineContent += "*";
|
||||
|
||||
}
|
||||
|
||||
} // End loop through all columns
|
||||
|
||||
System.out.println(lineContent);
|
||||
|
||||
lineContent = "";
|
||||
|
||||
} // End loop through all rows
|
||||
|
||||
} // End of method startGame
|
||||
|
||||
|
||||
// Function to be plotted
|
||||
public double func(double inputVal) {
|
||||
|
||||
return (30 * Math.exp(-inputVal * inputVal / 100));
|
||||
|
||||
}
|
||||
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
Plot3D plot = new Plot3D();
|
||||
plot.play();
|
||||
|
||||
} // End of method main
|
||||
|
||||
} // End of class Plot3D
|
||||
280
95 Weekday/java/Weekday.java
Normal file
280
95 Weekday/java/Weekday.java
Normal file
@@ -0,0 +1,280 @@
|
||||
import java.util.Scanner;
|
||||
|
||||
/**
|
||||
* WEEKDAY
|
||||
*
|
||||
* Converted from BASIC to Java by Aldrin Misquitta (@aldrinm)
|
||||
*
|
||||
*/
|
||||
public class Weekday {
|
||||
|
||||
//TABLE OF VALUES FOR THE MONTHS TO BE USED IN CALCULATIONS.
|
||||
//Dummy value added at index 0, so we can reference directly by the month number value
|
||||
private final static int[] t = new int[]{-1, 0, 3, 3, 6, 1, 4, 6, 2, 5, 0, 3, 5};
|
||||
|
||||
public static void main(String[] args) {
|
||||
printIntro();
|
||||
|
||||
Scanner scanner = new Scanner(System.in);
|
||||
System.out.print("ENTER TODAY'S DATE IN THE FORM: 3,24,1979 ");
|
||||
DateStruct todaysDate = readDate(scanner);
|
||||
|
||||
System.out.print("ENTER DAY OF BIRTH (OR OTHER DAY OF INTEREST) ");
|
||||
DateStruct dateOfInterest = readDate(scanner);
|
||||
|
||||
int I1 = (dateOfInterest.year - 1500) / 100;
|
||||
//TEST FOR DATE BEFORE CURRENT CALENDAR.
|
||||
if ((dateOfInterest.year - 1582) >= 0) {
|
||||
int A = I1 * 5 + (I1 + 3) / 4;
|
||||
int I2 = (A - b(A) * 7);
|
||||
int Y2 = (dateOfInterest.year / 100);
|
||||
int Y3 = (dateOfInterest.year - Y2 * 100);
|
||||
A = Y3 / 4 + Y3 + dateOfInterest.day + t[dateOfInterest.month] + I2;
|
||||
calculateAndPrintDayOfWeek(I1, A, todaysDate, dateOfInterest, Y3);
|
||||
|
||||
if ((todaysDate.year * 12 + todaysDate.month) * 31 + todaysDate.day
|
||||
== (dateOfInterest.year * 12 + dateOfInterest.month) * 31 + dateOfInterest.day) {
|
||||
return; //stop the program
|
||||
}
|
||||
|
||||
int I5 = todaysDate.year - dateOfInterest.year;
|
||||
System.out.print("\n");
|
||||
int I6 = todaysDate.month - dateOfInterest.month;
|
||||
int I7 = todaysDate.day - dateOfInterest.day;
|
||||
if (I7 < 0) {
|
||||
I6 = I6 - 1;
|
||||
I7 = I7 + 30;
|
||||
}
|
||||
if (I6 < 0) {
|
||||
I5 = I5 - 1;
|
||||
I6 = I6 + 12;
|
||||
}
|
||||
if (I5 < 0) {
|
||||
return; //do nothing. end the program
|
||||
} else {
|
||||
if (I7 != 0) {
|
||||
printHeadersAndAge(I5, I6, I7);
|
||||
} else {
|
||||
if (I6 != 0) {
|
||||
printHeadersAndAge(I5, I6, I7);
|
||||
} else {
|
||||
System.out.println("***HAPPY BIRTHDAY***");
|
||||
printHeadersAndAge(I5, I6, I7);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int A8 = (I5 * 365) + (I6 * 30) + I7 + (I6 / 2);
|
||||
int K5 = I5;
|
||||
int K6 = I6;
|
||||
int K7 = I7;
|
||||
//CALCULATE RETIREMENT DATE.
|
||||
int E = dateOfInterest.year + 65;
|
||||
// CALCULATE TIME SPENT IN THE FOLLOWING FUNCTIONS.
|
||||
float F = 0.35f;
|
||||
System.out.printf("%-28s", "YOU HAVE SLEPT");
|
||||
DateStruct scratchDate = new DateStruct(K6, K7, K5); //K5 is a temp year, K6 is month, K7 is day
|
||||
printStatisticRow(F, A8, scratchDate);
|
||||
K5 = scratchDate.year;
|
||||
K6 = scratchDate.month;
|
||||
K7 = scratchDate.day;
|
||||
|
||||
F = 0.17f;
|
||||
System.out.printf("%-28s", "YOU HAVE EATEN");
|
||||
|
||||
scratchDate = new DateStruct(K6, K7, K5);
|
||||
printStatisticRow(F, A8, scratchDate);
|
||||
K5 = scratchDate.year;
|
||||
K6 = scratchDate.month;
|
||||
K7 = scratchDate.day;
|
||||
|
||||
F = 0.23f;
|
||||
if (K5 > 3) {
|
||||
if (K5 > 9) {
|
||||
System.out.printf("%-28s", "YOU HAVE WORKED/PLAYED");
|
||||
} else {
|
||||
System.out.printf("%-28s", "YOU HAVE PLAYED/STUDIED");
|
||||
}
|
||||
} else {
|
||||
System.out.printf("%-28s", "YOU HAVE PLAYED");
|
||||
}
|
||||
|
||||
scratchDate = new DateStruct(K6, K7, K5);
|
||||
printStatisticRow(F, A8, scratchDate);
|
||||
K5 = scratchDate.year;
|
||||
K6 = scratchDate.month;
|
||||
K7 = scratchDate.day;
|
||||
|
||||
if (K6 == 12) {
|
||||
K5 = K5 + 1;
|
||||
K6 = 0;
|
||||
}
|
||||
System.out.printf("%-28s%14s%14s%14s%n", "YOU HAVE RELAXED", K5, K6, K7);
|
||||
System.out.printf("%16s*** YOU MAY RETIRE IN %s ***%n", " ", E);
|
||||
System.out.printf("%n%n%n%n%n");
|
||||
} else {
|
||||
System.out.println("NOT PREPARED TO GIVE DAY OF WEEK PRIOR TO MDLXXXII.");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static void printStatisticRow(float F, int A8, DateStruct scratchDate) {
|
||||
int K1 = (int) (F * A8);
|
||||
int I5 = K1 / 365;
|
||||
K1 = K1 - (I5 * 365);
|
||||
int I6 = K1 / 30;
|
||||
int I7 = K1 - (I6 * 30);
|
||||
int K5 = scratchDate.year - I5;
|
||||
int K6 = scratchDate.month - I6;
|
||||
int K7 = scratchDate.day - I7;
|
||||
if (K7 < 0) {
|
||||
K7 = K7 + 30;
|
||||
K6 = K6 - 1;
|
||||
}
|
||||
if (K6 <= 0) {
|
||||
K6 = K6 + 12;
|
||||
K5 = K5 - 1;
|
||||
}
|
||||
//to return the updated values of K5, K6, K7 we send them through the scratchDate
|
||||
scratchDate.year = K5;
|
||||
scratchDate.month = K6;
|
||||
scratchDate.day = K7;
|
||||
System.out.printf("%14s%14s%14s%n", I5, I6, I7);
|
||||
}
|
||||
|
||||
private static void printHeadersAndAge(int I5, int I6, int I7) {
|
||||
System.out.printf("%14s%14s%14s%14s%14s%n", " ", " ", "YEARS", "MONTHS", "DAYS");
|
||||
System.out.printf("%14s%14s%14s%14s%14s%n", " ", " ", "-----", "------", "----");
|
||||
System.out.printf("%-28s%14s%14s%14s%n", "YOUR AGE (IF BIRTHDATE)", I5, I6, I7);
|
||||
}
|
||||
|
||||
private static void calculateAndPrintDayOfWeek(int i1, int a, DateStruct dateStruct, DateStruct dateOfInterest, int y3) {
|
||||
int b = (a - b(a) * 7) + 1;
|
||||
if (dateOfInterest.month > 2) {
|
||||
printDayOfWeek(dateStruct, dateOfInterest, b);
|
||||
} else {
|
||||
if (y3 == 0) {
|
||||
int aa = i1 - 1;
|
||||
int t1 = aa - a(aa) * 4;
|
||||
if (t1 == 0) {
|
||||
if (b != 0) {
|
||||
b = b - 1;
|
||||
printDayOfWeek(dateStruct, dateOfInterest, b);
|
||||
} else {
|
||||
b = 6;
|
||||
b = b - 1;
|
||||
printDayOfWeek(dateStruct, dateOfInterest, b);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* PRINT THE DAY OF THE WEEK THE DATE FALLS ON.
|
||||
*/
|
||||
private static void printDayOfWeek(DateStruct dateStruct, DateStruct dateOfInterest, int b) {
|
||||
if (b == 0) {
|
||||
b = 7;
|
||||
}
|
||||
if ((dateStruct.year * 12 + dateStruct.month) * 31
|
||||
+ dateStruct.day
|
||||
<
|
||||
(dateOfInterest.year * 12
|
||||
+ dateOfInterest.month) * 31 + dateOfInterest.day) {
|
||||
System.out.printf("%s / %s / %s WILL BE A ", dateOfInterest.month, dateOfInterest.day, dateOfInterest.year);
|
||||
} else if ((dateStruct.year * 12 + dateStruct.month) * 31
|
||||
+ dateStruct.day == (dateOfInterest.year * 12 + dateOfInterest.month)
|
||||
* 31 + dateOfInterest.day) {
|
||||
System.out.printf("%s / %s / %s IS A ", dateOfInterest.month, dateOfInterest.day, dateOfInterest.year);
|
||||
} else {
|
||||
System.out.printf("%s / %s / %s WAS A ", dateOfInterest.month, dateOfInterest.day, dateOfInterest.year);
|
||||
}
|
||||
switch (b) {
|
||||
case 1:
|
||||
System.out.println("SUNDAY.");
|
||||
break;
|
||||
case 2:
|
||||
System.out.println("MONDAY.");
|
||||
break;
|
||||
case 3:
|
||||
System.out.println("TUESDAY.");
|
||||
break;
|
||||
case 4:
|
||||
System.out.println("WEDNESDAY.");
|
||||
break;
|
||||
case 5:
|
||||
System.out.println("THURSDAY.");
|
||||
break;
|
||||
case 6:
|
||||
if (dateOfInterest.day == 13) {
|
||||
System.out.println("FRIDAY THE THIRTEENTH---BEWARE!");
|
||||
} else {
|
||||
System.out.println("FRIDAY.");
|
||||
}
|
||||
break;
|
||||
case 7:
|
||||
System.out.println("SATURDAY.");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private static int a(int a) {
|
||||
return a / 4;
|
||||
}
|
||||
|
||||
private static int b(int a) {
|
||||
return a / 7;
|
||||
}
|
||||
|
||||
|
||||
private static void printIntro() {
|
||||
System.out.println(" WEEKDAY");
|
||||
System.out.println(" CREATIVE COMPUTING MORRISTOWN, NEW JERSEY");
|
||||
System.out.println("\n\n\n");
|
||||
System.out.println("WEEKDAY IS A COMPUTER DEMONSTRATION THAT");
|
||||
System.out.println("GIVES FACTS ABOUT A DATE OF INTEREST TO YOU.");
|
||||
System.out.println("\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* Read user input for a date, do some validation and return a simple date structure
|
||||
*/
|
||||
private static DateStruct readDate(Scanner scanner) {
|
||||
boolean done = false;
|
||||
int mm = 0, dd = 0, yyyy = 0;
|
||||
while (!done) {
|
||||
String input = scanner.next();
|
||||
String[] tokens = input.split(",");
|
||||
if (tokens.length < 3) {
|
||||
System.out.println("DATE EXPECTED IN FORM: 3,24,1979 - RETRY INPUT LINE");
|
||||
} else {
|
||||
try {
|
||||
mm = Integer.parseInt(tokens[0]);
|
||||
dd = Integer.parseInt(tokens[1]);
|
||||
yyyy = Integer.parseInt(tokens[2]);
|
||||
done = true;
|
||||
} catch (NumberFormatException nfe) {
|
||||
System.out.println("NUMBER EXPECTED - RETRY INPUT LINE");
|
||||
}
|
||||
}
|
||||
}
|
||||
return new DateStruct(mm, dd, yyyy);
|
||||
}
|
||||
|
||||
/**
|
||||
* Convenience date structure to hold user date input
|
||||
*/
|
||||
private static class DateStruct {
|
||||
int month;
|
||||
int day;
|
||||
int year;
|
||||
|
||||
public DateStruct(int month, int day, int year) {
|
||||
this.month = month;
|
||||
this.day = day;
|
||||
this.year = year;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user