euchre-live

Euchre web-app for the socially distant family
git clone git://git.alexkarle.com/euchre-live.git
Log | Files | Refs | README | LICENSE

commit 79a60c1f9bc5138d8116bb9d36e235073135d60d (patch)
parent 6d5e9081e6cfca3b1b11db00738296fea96688e3
Author: Alex Karle <alex@karle.co>
Date:   Fri,  3 Apr 2020 23:59:00 -0400

Euchre::Dealer: Add first pass at vote_trump action

This will need some tweaking in the near future. Particularly we need to
handle the 'loner' state. However, committing as is now as it (1) test
compiles and (2) isn't used anywhere.

There's an interesting mix appearing of server side validation vs client
side validation. I think my general leanings are towards the following
guidelines:

    * Communication Order -- handled by server (i.e. who can play a card
      when)
    * Communication Content -- handled by client (i.e. can you
      _actually_ play that card)

Obviously there is some content validation (valid messages) on the
server side, but otherwise, we don't manage hands or whether it's ok to
vote for what trump when. Makes things easier (and these are easy for
the client to handle themselves).

Diffstat:
Mlib/Euchre/Dealer.pm | 40+++++++++++++++++++++++++++++++++++++++-
1 file changed, 39 insertions(+), 1 deletion(-)

diff --git a/lib/Euchre/Dealer.pm b/lib/Euchre/Dealer.pm @@ -37,6 +37,7 @@ our @EXPORT = qw( # score => [X, Y], # phase => 'lobby', 'play', 'vote', 'end' # trump_nominee => 0-23, +# pass_count => 0-7, # } # # We decided the players would keep track of their own hands @@ -99,6 +100,7 @@ sub handle_msg { take_seat => \&take_seat, stand_up => \&stand_up, start_game => \&start_game, + vote_trump => \&vote_trump, ); if (exists $dispatch{$msg->{action}}) { @@ -126,7 +128,7 @@ sub join_game { trump => -1, tricks => [0, 0, 0, 0], table => [], - callers => -1, + caller => -1, score => [0, 0], phase => 'lobby', }; @@ -221,6 +223,7 @@ sub start_new_round { # Signal vote of player next to dealer... $game->{turn} = ($game->{dealer} + 1 % 4); $game->{phase} = 'vote'; + $game->{pass_count} = 0; broadcast_gamestate($game); # includes trump_nominee } @@ -242,6 +245,41 @@ sub deal_players_hands { } } + +# msg.vote = 'suit' or 'pass' +# msg.loner = 0 or 1 +sub vote_trump { + my ($p, $msg) = @_; + + my $game = $p->{game}; + if ($game->{turn} != $p->{seat}) { + send_error("Not your turn!"); + } else { + if ($msg->{vote} eq 'pass') { + $game->{turn} = ($game->{turn} + 1 % 4); + $game->{pass_count}++; + if ($game->{pass_count} >= 8) { + # Throw em in + start_new_round($game); + } else { + broadcast_gamestate($game); + } + } elsif (defined suit_to_id($msg->{vote})) { + # XXX handle loner (needs to handle next-player) + # NOTE: we let clients decide what's kosher to vote + # based on their hand state, pass_count + $game->{trump} = suit_to_id($msg->{vote}); + $game->{caller} = $p->{seat}; + $game->{phase} = 'play'; + $game->{turn} = ($game->{dealer} + 1 % 4); + broadcast_gamestate($game); + } else { + send_error("Bad vote"); + } + } +} + + # XXX: The most simplest (bulkiest) message we can send is to just # broadcast the gamestate to all clients. This will be our temporary # debugging method / MVP. We can trim down the communication later