diff options
Diffstat (limited to 'src/scalevalapokalypsi/UI/main.scala')
-rw-r--r-- | src/scalevalapokalypsi/UI/main.scala | 132 |
1 files changed, 132 insertions, 0 deletions
diff --git a/src/scalevalapokalypsi/UI/main.scala b/src/scalevalapokalypsi/UI/main.scala new file mode 100644 index 0000000..44ca0e4 --- /dev/null +++ b/src/scalevalapokalypsi/UI/main.scala @@ -0,0 +1,132 @@ +package scalevalapokalypsi.UI + +import scalevalapokalypsi.Client.{newClient, Client, GameEvent} +import scalevalapokalypsi.Server.Server +import scalevalapokalypsi.constants.* +import scalevalapokalypsi.utils.* +import java.lang.Thread.sleep +import scala.util.{Try,Success,Failure} +import scala.collection.immutable.LazyList + +import java.lang.Thread +import scala.io.StdIn.readLine + + +@main def main(): Unit = + + val option = getValidInput[Int]( + "Miten tahdot pelata?\n" + + s"1) Liity viralliselle palvelimelle ($DEFAULT_SERVER)\n" + + "2) Käynnistä palvelin laitteellasi ja liity sille\n" + + "3) Liity mielivaltaiselle palvelimelle", + s => s.toIntOption match + case None => + Left("Syötä kokonaisluku.") + case Some(i) => + if i < 1 || i > 3 then + Left("Syötä kokonaisluku väliltä [1,3].") + else + Right(i) + ) + + + val serverName = + if option == 3 then + readLine("Syötä palvelimen verkkotunnus.\n> ") + else if option == 2 then + "127.0.0.1" + else + DEFAULT_SERVER + + val serverPort = + if option == 1 then + DEFAULT_PORT + else + getValidInput[Int]( + s"Valitse portti palvelimelle. (Jätä tyhjäksi oletusta $DEFAULT_PORT varten)", + s => + if s == "" then + Right(DEFAULT_PORT) + else + s.toIntOption match + case None => + Left("Syötä kokonaisluku.") + case Some(i) => + if i > 0 && i <= 65535 then + Right(i) + else + Left("Syötä portti lailliselta väliltä.") + ) + + val maxClients = if option == 2 then + getValidInput[Int]( + "Kuinka monta pelaajaa pelissä saa olla samanaikaisesti?", + s => s.toIntOption match + case None => + Left("Syötä kokonaisluku.") + case Some(i) => + if i > 1000 then + println( + "Aika ison määrän valitsit, mutta olkoon menneeksi." + ) + if i > 0 then + Right(i) + else + Left("Syötä positiivinen kokonaisluku.") + ) + else + 0 + + val timeLimit = if option == 2 then + getValidInput[Int]( + s"Syötä vuorojen aikaraja yksiköttömänä sekunneissa odottelun vähentämiseksi. Syötä 0 aikarajan poistamiseksi. (Jätä tyhjäksi oletusta $DEFAULT_TURN_TIME_LIMIT varten)", + s => if s == "" then + Right(DEFAULT_TURN_TIME_LIMIT) + else + s.toIntOption + .toRight("Syötä kokonaisluku") + .filterOrElse( + _ >= 0, + "Syötä epänegatiivinen kokonaisluku." + ) + ) + else + 0 + + if option == 2 then + Thread(() => new Server(serverPort, maxClients, timeLimit, true).startServer()).start() + println("Palvelin käynnistetty taustalla.") + + val name = readLine("Valitse itsellesi pelin sisäinen alter ego.\n> ") + + Try(newClient(name, serverName, serverPort)) + .toOption + .flatten match + case Some(client) => + startClient(client) + case None => + println( + "Serverille liittyminen epäonnistui. Tarkista internet-yhteytesi. Jos yhteytesi on kunnossa ja liittyminen ei pian onnistu, ota yhteyttä Joel Kronqvistiin <joel.kronqvist@iki.fi> olettaen, ettei vuodesta 2024 ole kulunut kohtuuttomasti aikaa." + ) + + + +/** Client game loop. Handles output to and from the client in the eyes of the + * terminal. + */ +def startClient(client: Client): Unit = + var hasQuit = false + val stdinReader = StdinLineReader() + stdinReader.startReading() + while !hasQuit do + sleep(POLL_INTERVAL) + val line = stdinReader.newLine() + if line.map(_.length).getOrElse(0) > 1024 then + Printer.printLn("Virhe: Syötteesi oli liian pitkä.") + else if line == Some("quit") then + hasQuit = true + else + val gameEvent = client.clientStep(line) + Printer.printGameEvent(gameEvent) + + |