7 notes &
Cocoa coding:Blackjack tutorial - part 9
Well. That looks really smart. But how come after clicking I still see a start button and not the hit and stand button. Obviously, it is because I haven’t said anything in the code about it yet.
And that’s what I will do now.
First I’ll declare the hitCard: and stand: methods in the BlackJackController.h - They look the same as the existing startGame: method.
The implementation in the BlackJackController.m is of course different. For now, just add the methods and leave them empty. Like this:
-(IBAction) hitCard:(id)sender{
}
-(IBAction) stand:(id)sender{
}
Let’s update the BlackJackController.xib. Find the Hit and Stand Button and attach them to File’s Owner (and the correct method - the ones that were just declared).

The buttons are still hidden though. You have to think when you need what buttons:
- Not playing: No Hit, No Stand - but yes on the start button.
- Playing: Both Hit and Stand need to be there, but no start button.
- Standing: No more buttons. The table will start playing.
- Finished. Well, that’s just similar to not playing.
So the first situation (not playing) is already happening in the application right now.
Basically I mean, after someone clicks the start button, the buttons hidden attribure should be set differently.
So at the end of the BlackJackController’s startGame: method I’ll add that the start button will be hidden from now on, and that the others will be visible.
That will make the code look like this:
-(IBAction) startGame:(id)sender{
blackJackModel = [[BlackJackModel alloc] init];
[blackJackModel setupGame];
[(BlackJackView *)self.view showHand:[blackJackModel playerHand]];
[(BlackJackView *)self.view showHand:[blackJackModel tableHand]];
[[(BlackJackView *)self.view hitBtn] setHidden:NO];
[[(BlackJackView *)self.view standBtn] setHidden:NO];
[[(BlackJackView *)self.view restartBtn] setHidden:YES];
}
Because it’s good to enjoy the little things in life, i’d recommend run the application after you changed this. Just to see the buttons appear and disappear (once). Don’t bother clicking on Hit or Stand yet, though. Just cherish the moment that they appeared.
It’s not really a big deal to implement the hitCard:, though and it would make the interactive experience a lot greater.
So the hitCard: should draw a card from the deck and add it to the playerhand.
-(IBAction) hitCard:(id)sender{
[blackJackModel.playerHand addCard:[blackJackModel.deck drawCard] open:YES];
[(BlackJackView *)self.view showHand:blackJackModel.playerHand];
}
If you added the code and run the application again, you should see it working, however you’ll be able to hitCards indefinitely. And logically, if you’re bust (meaning over 21 pipValue), you shouldn’t be able to draw at all. In fact, the game is over when you’re bust.
So let’s add that. By adding the following lines
-(IBAction) hitCard:(id)sender{
[blackJackModel.playerHand addCard:[blackJackModel.deck drawCard] open:YES];
[(BlackJackView *)self.view showHand:blackJackModel.playerHand];
if ( [blackJackModel.playerHand getPipValue] > 21) {
[[(BlackJackView *)self.view hitBtn] setHidden:YES];
[[(BlackJackView *)self.view standBtn] setHidden:YES];
[[(BlackJackView *)self.view restartBtn] setHidden:NO];
}
}
The compiler will complain about not knowing a few of the methods of Hand and Deck. So be sure to do some extra imports in the top of this file, so it will look like this:
#import "BlackJackController.h" #import "BlackJackModel.h" #import "BlackJackView.h" #import "Deck.h" #import "Hand.h"
Maybe eventually I’ll move that part to another method. But for now, it will do.
In the stand: method I’ll add the complete AI for blackjack. What will happen when you click the stand button? First the hit and stand button are set to hidden. Then the table first will have to show it’s cards. And the mac will do it’s AI.
Before we’ll add all that: Let’s set the buttons and show the cards of the dealer (by turning that 2nd card, that was a closed card, and then displaying them both). I’ll add a new method OpenTableHand to the BlackJackModel. Which will loop to all cards in the tableHand and turn their open to YES.
To loop over all the cards in the BlackJackModel I need the cardsInHand (that was declared private before) in Hand to be a @property (assign) and @synthesize it.
So in hand.h, you’ll now find:
@interface Hand : NSObject {
NSMutableArray *cardsInHand;
HandType handType;
}
@property (assign) NSMutableArray *cardsInHand;
@property HandType handType;
In the hand.m it’s synthesized:
@synthesize handType, cardsInHand;
The blackjackmodel.h has this added:
-(void) openTableHand;
And this has the following method implemented in it’s .m counterpart:
-(void) openTableHand{
for (Card *tCard in self.tableHand.cardsInHand) {
tCard.open=YES;
}
}
However all that could be done differently, since you know it is always only the 2nd card which has a open=NO. But still: this works too.
So back to the stand: method in BlackJackController.m
-(IBAction) stand:(id)sender{
[[(BlackJackView *)self.view hitBtn] setHidden:YES];
[[(BlackJackView *)self.view standBtn] setHidden:YES];
[blackJackModel openTableHand];
[(BlackJackView *)self.view showHand:blackJackModel.tableHand];
// We'll add some AI later
[[(BlackJackView *)self.view restartBtn] setHidden:NO];
}
Now all I need is the drawing of Cards of the computer to win or go bust. Tomorrow!
Previous chapter: Blackjack tutorial - part 8.
Next chapter: Blackjack tutorial - part 10.