NAME

Game::Gin::Deal - one hand of gin rummy, from the deal to the knock

VERSION

Version 0.01

SYNOPSIS

my $deal = Game::Gin::Deal->build(seed => $bytes, number => 1, dealer => 'p1');

$deal->turn;                        # 'p2', the non-dealer
$deal->phase;                       # 'upcard'
$deal->legal('p2');                 # take or pass

my @out = $deal->apply('p2', { kind => 'take' });
@out = $deal->apply('p2', { kind => 'discard', card => $id, knock => 1 });

$deal->over;                        # 1
$deal->result;                      # { winner, points, kind, ... }

DESCRIPTION

One deal. A match to 100 is many of these; keeping them apart is what makes the first turn testable on its own.

Nothing here prints, reads a handle or calls rand.

The first turn is not a normal turn

The non-dealer may take the upcard. If they decline, the dealer may. If both decline, the non-dealer draws from the stock and may not take the card they have just refused. Three phases rather than one condition, because each has a different set of legal moves.

The stock is never named

A draw from the stock returns an outcome with no card in it. The stock is the tail of the shuffled order, so the card is derivable from the seed and the number of draws; nothing downstream has to be trusted to keep it secret, because there is no field for it to leak from.

The hand is cancelled at two cards

When a discard leaves two cards in the stock, the hand ends and nobody scores.

METHODS

build

Game::Gin::Deal->build(seed => $bytes, number => $n, dealer => 'p1');

Deals. Returns the deal, or a Game::Gin::Error for a bad seed.

The moves this seat may make now, as arrayrefs of hashrefs. Empty for the seat not on turn and for a finished hand.

apply

$deal->apply($seat, { kind => 'discard', card => $id });

Applies a move and returns the outcomes, or a Game::Gin::Error.

turn, phase, over, result

Where the hand is. phase is upcard, forced_draw, draw, discard or over.

hand_of, upcard, stock_left, discard, hands, stock

The position. hand_of takes a seat and returns its Game::Gin::Hand; upcard is the top of the discard pile, or undef if the pile is empty; stock_left is how many cards remain to be drawn.

history

Every outcome this deal has produced, in order. A draw outcome names no card, so a history cannot leak the stock.

seed

The 32 bytes this deal came from.

number

Which deal of the match this is. It is part of the shuffle key, so deal two of a match deals differently from deal one.

dealer

The seat that dealt. The other seat has the first say on the upcard.

taken

The card just taken from the discard pile, or 0. It exists so that the discard which follows cannot simply put it back, which would be a turn that changed nothing and a way to stall for ever.

other

The other seat.

SEE ALSO

Game::Gin::Scoring, Game::Gin::Deadwood, Game::Gin::Deck.

AUTHOR

LNATION, <email@lnation.org>

LICENSE AND COPYRIGHT

This software is Copyright (c) 2026 by LNATION.

This is free software, licensed under the Artistic License 2.0.