Un mini, pero que mini (como todo hasta ahora) juego de Blackjack, sacado del ya conocido curso de coursera.
Las reglas son sencillas: las cartas J,Q y K valen diez puntos, los ases 10 o 1, y el resto por su número de carta. Tienes que intentar tener más puntos que el otro, sin pasarse de 21. De forma que puedes escoger que te de más cartas para tener más puntos, o quedarte con las que tienes.
Una vez más, toca ejecutarlo en CodeSkulptor por la librería gráfica propia de la plataforma.
Blackjack: Pulsa para ver/ocultar el código
# Mini-project #6 - Blackjack
import simplegui
import random
# load card sprite - 949x392 - source: jfitz.com
CARD_SIZE = (73, 98)
CARD_CENTER = (36.5, 49)
card_images = simplegui.load_image("http://commondatastorage.googleapis.com/codeskulptor-assets/cards.jfitz.png")
CARD_BACK_SIZE = (71, 96)
CARD_BACK_CENTER = (35.5, 48)
card_back = simplegui.load_image("http://commondatastorage.googleapis.com/codeskulptor-assets/card_back.png")
# initialize some useful global variables
in_play = False
outcome = ""
score_dealer = 0
score_player = 0
the_deck =""
dealer_hand=""
my_hand=""
# define globals for cards
SUITS = ('C', 'S', 'H', 'D')
RANKS = ('A', '2', '3', '4', '5', '6', '7', '8', '9', 'T', 'J', 'Q', 'K')
VALUES = {'A':1, '2':2, '3':3, '4':4, '5':5, '6':6, '7':7, '8':8, '9':9, 'T':10, 'J':10, 'Q':10, 'K':10}
# define card class
class Card:
def __init__(self, suit, rank):
if (suit in SUITS) and (rank in RANKS):
self.suit = suit
self.rank = rank
else:
self.suit = None
self.rank = None
print "Invalid card: ", suit, rank
def __str__(self):
return self.suit + self.rank
def get_suit(self):
return self.suit
def get_rank(self):
return self.rank
def draw(self, canvas, pos):
card_loc = (CARD_CENTER[0] + CARD_SIZE[0] * RANKS.index(self.rank),
CARD_CENTER[1] + CARD_SIZE[1] * SUITS.index(self.suit))
canvas.draw_image(card_images, card_loc, CARD_SIZE, [pos[0] + CARD_CENTER[0], pos[1] + CARD_CENTER[1]], CARD_SIZE)
# define hand class
class Hand:
def __init__(self):
#list of cards of the hand
self.cards=[]
# value of the hand
self.hand_value=0
#has hand an ace?
self.has_ace = False
# return a string representation of a hand
def __str__(self):
result="Hand contains "
#for every card...
for next in self.cards:
result=result + " " + str(next)
return result
def add_card(self, card):
# add a card object to a hand
self.cards.append(card)
#sum the value of the card
self.hand_value=self.hand_value+VALUES[card.get_rank()]
#check if i have an ace
if card.get_rank() == RANKS[0]:
self.has_ace=True
def get_value(self):
# count aces as 1, if the hand has an ace, then add 10 to hand value if it doesn't bust
if self.has_ace == True:
if self.hand_value+10 <=21:
return self.hand_value+10
return self.hand_value
def draw(self, canvas, pos):
i=0
#for every card...
for next in self.cards:
card_pos=((i * CARD_SIZE[0])+pos[0]+10*i, pos[1])
next.draw(canvas, card_pos)
i=i+1 #increase the position of the card
# define deck class
class Deck:
def __init__(self):
#list of cards
self.cards=[]
#double for, every cards
for rank in RANKS:
for suit in SUITS:
self.cards.append(Card(suit, rank))
#remix the cards
def shuffle(self):
# shuffle the deck
random.shuffle(self.cards)
def deal_card(self):
return self.cards.pop()
def __str__(self):
result="Deck contains "
#for every card...
for next in self.cards:
result=result + " " + str(next)
return result
#define event handlers for buttons
def deal():
global outcome, in_play, the_deck, dealer_hand, my_hand, score_dealer
#reset the outcome
outcome=""
#reset the deck and hands
the_deck=Deck()
the_deck.shuffle()
dealer_hand=Hand()
my_hand=Hand()
#give the cards
dealer_hand.add_card(the_deck.deal_card())
dealer_hand.add_card(the_deck.deal_card())
my_hand.add_card(the_deck.deal_card())
my_hand.add_card(the_deck.deal_card())
#check if was playing
if in_play:
score_dealer=score_dealer+1
else:
in_play=True
def hit():
global score_dealer, in_play, outcome
if in_play:
#get a card
my_hand.add_card(the_deck.deal_card())
#check bust
if my_hand.get_value()>21:
outcome="You went bust and lose"
score_dealer=score_dealer+1
in_play=False
def stand():
global outcome, score_dealer, score_player, in_play
if in_play:
#hit cards to dealer until value of 17 or higher
while dealer_hand.get_value()<17:
dealer_hand.add_card(the_deck.deal_card())
#check situation
if dealer_hand.get_value()>21:
outcome="Dealer got busted. You win"
score_player=score_player+1
elif dealer_hand.get_value()>=my_hand.get_value():
outcome="You lose"
score_dealer=score_dealer+1
else:
outcome="You win"
score_player=score_player+1
in_play=False
# draw handler
def draw(canvas):
#title
canvas.draw_text("Blackjack", [100, 70], 36, "Blue")
#message of hit or deal
next_step=""
if in_play:
next_step="Hit or stand?"
else:
next_step="New deal?"
#title and cards of dealer
canvas.draw_text("Dealer", [100, 130], 24, "Black")
canvas.draw_text(outcome, [220, 130], 24, "Black")
dealer_hand.draw(canvas, [100, 150])
#title and cards of player
canvas.draw_text("Player", [100, 370], 24, "Black")
canvas.draw_text(next_step, [220, 370], 24, "Black")
my_hand.draw(canvas, [100, 400])
#score
canvas.draw_text("Score ", [440, 30], 24, "Black")
canvas.draw_text("Dealer: "+str(score_dealer), [430, 50], 24, "Black")
canvas.draw_text("Player: "+str(score_player), [430, 70], 24, "Black")
#if in play, hidde the card of dealer
if in_play:
pos=[100, 150]
canvas.draw_image(card_back, CARD_BACK_CENTER, CARD_BACK_SIZE, [pos[0] + CARD_CENTER[0], pos[1] + CARD_CENTER[1]], CARD_SIZE)
# initialization frame
frame = simplegui.create_frame("Blackjack", 600, 600)
frame.set_canvas_background("Green")
#create buttons and canvas callback
frame.add_button("Deal", deal, 200)
frame.add_button("Hit", hit, 200)
frame.add_button("Stand", stand, 200)
frame.set_draw_handler(draw)
# get things rolling
deal()
frame.start()

