From eb7098161a732a4579bb1fa3cca5c09095ee7d82 Mon Sep 17 00:00:00 2001 From: JasterV Date: Fri, 27 Aug 2021 15:35:59 +0200 Subject: [PATCH] actor almost done --- commandslist.txt | 1 - src/actors/game/actor.rs | 141 +++++++++++++++++++++++++++++++----- src/actors/game/messages.rs | 2 - src/command.rs | 2 - src/entities/game.rs | 72 ++++++++---------- src/entities/player.rs | 19 +++-- 6 files changed, 165 insertions(+), 72 deletions(-) diff --git a/commandslist.txt b/commandslist.txt index 82b8191..0c95af5 100644 --- a/commandslist.txt +++ b/commandslist.txt @@ -4,5 +4,4 @@ start - start the game endgame - stop the game ask - ask someone for cards status - ask the bot to show the game general status -mystatus - ask the bot to send you your status help - display commands info \ No newline at end of file diff --git a/src/actors/game/actor.rs b/src/actors/game/actor.rs index 8993d4d..70e14a2 100644 --- a/src/actors/game/actor.rs +++ b/src/actors/game/actor.rs @@ -1,7 +1,8 @@ use super::messages::GameCommand; use crate::alias::Cx; use crate::entities::actor::AsyncActor; -use crate::entities::game::Action; +use crate::entities::game::{Action, GameResults, GameState, TurnEvent}; +use crate::entities::player::Player; use crate::templates::*; use crate::{actors::game::messages::Message, entities::game::Game}; use anyhow::Result; @@ -16,14 +17,14 @@ impl GameActor { Self { game: Game::new() } } - async fn start(&mut self, cx: Cx) -> Result<()> { + async fn start(&mut self, cx: &Cx) -> Result<()> { self.game.execute(Action::Start)?; cx.answer(GAME_STARTED).await?; - self.send_status_to_players(cx).await?; - Ok(()) + self.send_status_to_players(&cx, &self.game.players).await?; + self.check_game_state(&cx).await } - async fn join(&mut self, cx: Cx) -> Result<()> { + async fn join(&mut self, cx: &Cx) -> Result<()> { let user = cx.update.from().unwrap(); self.game.execute(Action::Join( @@ -40,25 +41,132 @@ impl GameActor { Ok(()) } - async fn ask(&mut self, cx: Cx, to: usize, card: usize) -> Result<()> { + async fn ask(&mut self, cx: &Cx, to: usize, card: usize) -> Result<()> { + let from = cx.update.from().unwrap(); + let events = self + .game + .execute(Action::Ask(format!("{}", from.id), to, card as u8))?; + for event in events { + match event { + TurnEvent::Took(quantity) => { + if quantity == 0 { + cx.answer(format!( + "{} had no cards with that number, lets draw!", + &self.game.players[to].name + )) + .await?; + } else { + cx.answer(format!( + "{} had {} cards with the number {}, keep asking!", + &self.game.players[to].name, quantity, card + )) + .await?; + self.send_asking_data(cx, &from.first_name).await?; + } + } + TurnEvent::Group(card) => { + cx.answer(format!( + "{} has made a group of four {}", + from.first_name, card + )) + .await?; + } + _ => {} + } + } + if let GameState::Drawing(_) = self.game.state { + self.draw(cx, card).await?; + } + self.check_game_state(&cx).await + } + + async fn draw(&mut self, cx: &Cx, card: usize) -> Result<()> { + let from = cx.update.from().unwrap(); + let events = self + .game + .execute(Action::Draw(format!("{}", from.id), card as u8))?; + for event in events { + match event { + TurnEvent::Drawn(drawn) => { + cx.answer(format!("{} has drawn a card", &from.first_name)) + .await?; + if drawn == (card as u8) { + cx.answer(format!( + "{} has drawn a {}!! Keep asking!", + &from.first_name, card + )) + .await?; + } + } + TurnEvent::DeckEmpty => { + cx.answer("The deck is empty!!!").await?; + } + TurnEvent::Group(card) => { + cx.answer(format!( + "{} has made a group of four {}", + from.first_name, card + )) + .await?; + } + _ => {} + } + } Ok(()) } - async fn status(&self, cx: Cx) -> Result<()> { + async fn status(&self, cx: &Cx) -> Result<()> { Ok(()) } - async fn my_status(&self, cx: Cx) -> Result<()> { + async fn end(&mut self, cx: &Cx) -> Result<()> { Ok(()) } - async fn end(&mut self, cx: Cx) -> Result<()> { + async fn check_game_state(&self, cx: &Cx) -> Result<()> { + match &self.game.state { + GameState::Waiting => Ok(()), + GameState::Drawing(_) => Ok(()), + GameState::Asking(index) => { + self.send_asking_data(&cx, &self.game.players[*index].name) + .await + } + GameState::GameOver(GameResults { winners, score }) => { + self.send_game_over(&cx, winners, *score).await + } + } + } + + async fn send_game_over(&self, cx: &Cx, winners: &[String], score: u8) -> Result<()> { + cx.answer(format!( + "Game Over!\n\tWinners ๐Ÿ‘‘: {}\n\tScore: {}", + winners.join(", "), + score + )) + .await?; Ok(()) } - async fn send_status_to_players(&self, cx: Cx) -> Result<()> { + async fn send_asking_data(&self, cx: &Cx, name: &str) -> Result<()> { + let players_data: Vec<(usize, String)> = self + .game + .players + .iter() + .enumerate() + .map(|(index, player)| (index, player.name.clone())) + .collect(); + cx.answer( + format!( + "{} lets ask someone for a card๐Ÿ˜‡:\n\nType '/ask