Class: Gambler::Game::Blackjack

Inherits:
BasicGame show all
Defined in:
lib/gambler/game/blackjack.rb

Overview

The Game of Blackjack.

Constant Summary collapse

BUST =

The hand_value in which the Player busts.

21
INITIAL_CARDS =
2
FACE_VALUES =

These are used instead of Card::FACE_VALUES to accommodate Blackjack.

{
  'A' => 11,
  'K' => 10,
  'Q' => 10,
  'J' => 10,
  'T' => 10,
  '9' => 9,
  '8' => 8,
  '7' => 7,
  '6' => 6,
  '5' => 5,
  '4' => 4,
  '3' => 3,
  '2' => 2,
  'L' => 1 # Magic low Ace.
}

Constants inherited from BasicGame

Gambler::Game::BasicGame::INITIAL_ANTE, Gambler::Game::BasicGame::INITIAL_POT

Instance Attribute Summary collapse

Attributes inherited from BasicGame

#ante, #deck, #players, #pot

Instance Method Summary collapse

Constructor Details

#initialize(options = {}) ⇒ Blackjack

Returns a new instance of Blackjack.



31
32
33
34
35
36
37
38
# File 'lib/gambler/game/blackjack.rb', line 31

def initialize(options = {})
  raise Exceptions::InvalidPlayerSize unless options[:players].size >= 2
  super(options)
  @players.each { |player| player.empty_hand! }
  @players_in_round = Array.new
  @players_in_round.replace(@players)
  @round_winner = nil
end

Instance Attribute Details

#players_in_roundObject (readonly)

Returns the value of attribute players_in_round.



28
29
30
# File 'lib/gambler/game/blackjack.rb', line 28

def players_in_round
  @players_in_round
end

#round_winnerObject (readonly)

Returns the value of attribute round_winner.



29
30
31
# File 'lib/gambler/game/blackjack.rb', line 29

def round_winner
  @round_winner
end

Instance Method Details

#ante_up!Object

Forces each Player to put ante in the pot.



41
42
43
# File 'lib/gambler/game/blackjack.rb', line 41

def ante_up!
  @players_in_round.each { |player| place_bet(player, @ante) }
end

#finish_round!Object

This should be called after all players bust or stay. Sets the @round_winner variable to the Player object who won and gives them the pot.



106
107
108
109
110
111
112
113
114
# File 'lib/gambler/game/blackjack.rb', line 106

def finish_round!
  raise Exceptions::NoWinner if @players_in_round.nil?
  # The winner is the Player with the highest hand_value.
  @round_winner = @players_in_round.sort_by do |player|
    hand_value(player.hand)
  end.reverse.first
  @round_winner.chips += @pot
  @pot = INITIAL_POT
end

#hand_value(hand) ⇒ Object

Calculates the integer value for a Blackjack hand. Aces are converted to their lower value if the total hand value will bust the Player (and there are aces in the hand, of course).



48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# File 'lib/gambler/game/blackjack.rb', line 48

def hand_value(hand)
  return 0 if hand.empty?
  value = 0

  # Add up the face values
  hand.each do |card|
    value += FACE_VALUES[card.face]
  end

  # Handle any needed Ace changes.
  while value > BUST
    hand.each do |card|
      if card.face == 'A'
        # Subtract the difference between high and low ace (10).
        value -= (FACE_VALUES['A'] - FACE_VALUES['L'])
      end
    end
    break # no aces to change, bail
  end

  return value
end

#hit(player) ⇒ Object

Give player a Card.



72
73
74
75
76
77
78
# File 'lib/gambler/game/blackjack.rb', line 72

def hit(player)
  @deck.deal_to player
  if player_bust?(player)
    @players_in_round.delete(player)
    raise Exceptions::PlayerBust
  end
end

#place_bet(player, amount) ⇒ Object

Allows player to place a bet for amount which will be added to the current hand’s pot.



82
83
84
85
86
# File 'lib/gambler/game/blackjack.rb', line 82

def place_bet(player, amount)
  raise Exceptions::NotEnoughChips if player.chips < amount
  @pot += amount
  player.chips -= amount
end

#player_bust?(player) ⇒ Boolean

Returns true of the Player’s hand has a value above BUST.

Returns:

  • (Boolean)


89
90
91
# File 'lib/gambler/game/blackjack.rb', line 89

def player_bust?(player)
  hand_value(player.hand) > BUST
end

#start_round!Object

This should be called at the beginning of every round (not game), and sets up things like the ante and dealing initial hands.



95
96
97
98
99
100
101
# File 'lib/gambler/game/blackjack.rb', line 95

def start_round!
  @players.each { |player| player.empty_hand! }
  @players_in_round.replace(@players)
  @round_winner = nil
  ante_up!
  deal_initial_hands
end