Last active
July 21, 2017 03:32
-
-
Save chaupt/3c79c92e9f7bb2bf2f61b1cd0a0f48b9 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# | |
# Ruby For Kids Project 9: Acey Deucy | |
# Programmed By: Chris Haupt | |
# A multiplayer card game where you try to guess whether the next | |
# card will be between two other cards, placing bets on the results | |
# | |
require_relative "game" | |
require_relative "deck" | |
require_relative "card" | |
require_relative "player" | |
STARTING_NUMBER_OF_CHIPS = 10 | |
MINIMUM_PLAYERS = 2 | |
puts "Welcome to Acey Deucy" | |
print "Enter number of players: " | |
player_count = gets | |
player_count = player_count.to_i | |
if player_count >= MINIMUM_PLAYERS | |
# Load up some players | |
players = [] | |
(0...player_count).each do |index| | |
print "Enter name for player ##{index + 1}: " | |
name = gets | |
name = name.chomp | |
players << Player.new(name, STARTING_NUMBER_OF_CHIPS) | |
end | |
# Initialize a new game | |
game_engine = Game.new(players) | |
# Let's see the setup game | |
game_engine.show_player_chips | |
# Let's play and see who wins | |
game_engine.play | |
else | |
puts "There should be at least #{MINIMUM_PLAYERS}" | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Card | |
SUITS = %w(Clubs Diamonds Hearts Spades) | |
RANKS = %w(2 3 4 5 6 7 8 9 10 Jack Queen King Ace) | |
attr_accessor :rank, :suit | |
def initialize(rank, suit) | |
@rank = rank | |
@suit = suit | |
end | |
def to_s | |
"#{rank} of #{suit}" | |
end | |
# returns -1 if card1 is less than, 0 if same as, | |
# and 1 if larger than card2 | |
def self.compare_rank(card1, card2) | |
RANKS.index(card1.rank) <=> RANKS.index(card2.rank) | |
end | |
def self.create_cards | |
cards = [] | |
SUITS.each do |suit| | |
RANKS.each do |rank| | |
cards << Card.new(rank, suit) | |
end | |
end | |
cards | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Deck | |
def initialize(cards) | |
@cards = cards | |
end | |
def shuffle | |
unless @cards.empty? | |
@cards.shuffle! | |
end | |
end | |
def deal | |
unless @cards.empty? | |
@cards.pop | |
end | |
end | |
def size | |
@cards.length | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Game | |
attr_reader :players, :deck, :bank, :round | |
ANTE_AMOUNT = 1 | |
def initialize(players) | |
@players = players | |
@deck = Deck.new(Card.create_cards) | |
@deck.shuffle | |
@bank = 0 | |
@round = 0 | |
end | |
def remaining_players | |
players.count {|player| !player.eliminated?} | |
end | |
def play | |
while deck.size > (players.length * 3) && remaining_players > 1 do | |
new_round | |
puts "-" * 40 | |
puts "Round #{round}! The dealer has #{bank} chips." | |
puts "-" * 40 | |
puts "Everyone antes" | |
ante | |
puts "The dealer now has #{bank} chips." | |
deal_cards(2) | |
sort_cards | |
puts "---> Current cards:\n" | |
show_cards | |
puts "---> Players bet:\n" | |
players_bet | |
puts "\n---> Dealer deals one more card\n" | |
deal_cards(1) | |
show_cards | |
puts "---> Determining results\n" | |
determine_results | |
puts "\n---> New standings\n" | |
show_player_chips | |
puts "" | |
end | |
game_over | |
end | |
def new_round | |
@round += 1 | |
players.each do |player| | |
player.discard_hand | |
end | |
end | |
def ante | |
players.each do |player| | |
if not player.eliminated? | |
@bank = @bank + player.pay(ANTE_AMOUNT) | |
end | |
end | |
end | |
def deal_cards(num_of_cards) | |
players.each do |player| | |
next if player.eliminated? | |
1.upto(num_of_cards) do | |
player.take_card(deck.deal) | |
end | |
end | |
end | |
def sort_cards | |
players.each do |player| | |
next if player.eliminated? | |
player.sort_hand_by_rank | |
end | |
end | |
def players_bet | |
players.each do |player| | |
if player.eliminated? | |
puts "#{player.name} passes. (Out of chips!)" | |
else | |
print "#{player.name} can bet between 0 and #{max_bet(player)}: " | |
bet = gets.to_i | |
if bet < 0 || bet > max_bet(player) | |
bet = 0 | |
end | |
puts "#{player.name} bet #{bet}" | |
player.bet = bet | |
end | |
end | |
end | |
def max_bet(player) | |
[player.chips, bank].min | |
end | |
def show_player_chips | |
players.each do |player| | |
if player.eliminated? | |
puts "#{player.name} has been eliminated" | |
else | |
puts "#{player.name} has #{player.chips} chips" | |
end | |
end | |
end | |
def show_cards | |
players.each do |player| | |
puts "Player #{player.name}" | |
if player.eliminated? | |
puts "Has been eliminated!" | |
else | |
player.hand.each do |card| | |
puts card.to_s | |
end | |
end | |
puts "" | |
end | |
end | |
def determine_results | |
players.each do |player| | |
if not player.eliminated? | |
low_card = player.hand[0] | |
high_card = player.hand[1] | |
middle_card = player.hand[2] | |
if Card.compare_rank(low_card, middle_card) == 0 || Card.compare_rank(high_card,middle_card) == 0 | |
puts "#{player.name} got an exact match, loses twice the bet!" | |
chips = player.pay(player.bet * 2) | |
elsif Card.compare_rank(middle_card, low_card) < 0 || Card.compare_rank(middle_card, high_card) > 0 | |
puts "#{player.name} wasn't inbetween loses the bet!" | |
chips = player.pay(player.bet) | |
else | |
puts "#{player.name} wins bet!" | |
chips = -player.bet | |
player.win(player.bet) | |
end | |
@bank = @bank + chips | |
if @bank <= 0 | |
puts "Dealer is out of chips, everyone needs to ante up!" | |
end | |
while @bank <= 0 | |
ante | |
end | |
end | |
end | |
end | |
def game_over | |
puts "Game Over!" | |
players.sort! do |player1, player2| | |
player1.chips <=> player2.chips | |
end | |
puts "The winner is #{players.last.name}" | |
end | |
end | |
# Check to see if player has enough chips to play that round, she needs at | |
# least ANTE + 1, why? | |
# Write the loops that use next a different way that doesn't require next | |
# Change the rules so the player's only ante up once at the start of the game | |
# and again only when the bank is empty. Does that change the outcome of the game? |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Player | |
attr_accessor :name, :hand, :chips, :bet | |
def initialize(name, chips) | |
@name = name | |
@hand = [] | |
@chips = chips | |
@bet = nil | |
end | |
def discard_hand | |
@bet = nil | |
@hand = [] | |
end | |
def take_card(card) | |
@hand << card | |
end | |
def sort_hand_by_rank | |
@hand.sort! do |card1, card2| | |
Card.compare_rank(card1, card2) | |
end | |
end | |
def eliminated? | |
@chips <= 0 | |
end | |
def pay(amount) | |
if amount > @chips | |
pay = @chips | |
@chips = 0 | |
else | |
pay = amount | |
@chips -= amount | |
end | |
pay | |
end | |
def win(amount) | |
@chips += amount | |
end | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment