## JavaScript Card Objects

### The `Stack`

Object

See the card stacks
demo.
The `Stack`

object is designed to make it easier for a programmer
to use `Card`

objects in a manner similar to how a real deck or
stack of cards is used. Basically, it creates an ordered set of cards that can
be drawn from, added to, shuffled or combined with other
`Stacks.`

The constructor for the `Stack`

object is shown below.

function Stack() { // Create an empty array of cards. this.cards = new Array(); this.makeDeck = stackMakeDeck; this.shuffle = stackShuffle; this.deal = stackDeal; this.draw = stackDraw; this.addCard = stackAddCard; this.combine = stackCombine; this.cardCount = stackCardCount; }

There's not much to it other than creating an empty array for the cards and
assigning the methods. Many of these methods will in fact make use of the
methods already provided by the built-in JavaScript `Array`

object to manipulate the set of cards.

#### Building a Deck of Cards

The first method, `makeDeck(),`

is provided save a user of the
object some work by generating a full deck of cards in the stack.

function stackMakeDeck(n) { var ranks = new Array("A", "2", "3", "4", "5", "6", "7", "8", "9", "10", "J", "Q", "K"); var suits = new Array("C", "D", "H", "S"); var i, j, k; var m; m = ranks.length * suits.length; // Set array of cards. this.cards = new Array(n * m); // Fill the array with 'n' packs of cards. for (i = 0; i < n; i++) for (j = 0; j < suits.length; j++) for (k = 0; k < ranks.length; k++) this.cards[i * m + j * ranks.length + k] = new Card(ranks[k], suits[j]); }

Note that it takes an integer argument. Some card games may require you to combine two or more regular packs of cards into a single deck for play. This argument let's you specify how many packs to include in the deck.

The first step is to recreate the array of `Card`

objects based
on the number of cards needed. Then it loops through the rank and suit values,
creating a `Card`

object for each and placing it in the
`cards`

array. The process is repeated `n`

times.

This creates a nicely ordered set of cards. Of course, the first thing you'll probably want to do with a new deck is destroy that nice order by shuffling them.

#### Shuffling a `Stack`

The `shuffle()`

method accomplishes this by randomizing the order
of the cards currently in the stack.

function stackShuffle(n) { var i, j, k; var temp; // Shuffle the stack 'n' times. for (i = 0; i < n; i++) for (j = 0; j < this.cards.length; j++) { k = Math.floor(Math.random() * this.cards.length); temp = this.cards[j]; this.cards[j] = this.cards[k]; this.cards[k] = temp; } }

It takes a numeric argument which defines how many times the stack should be shuffled. For each shuffle it simply loops though every card in the array and swaps it with another card randomly selected from the array.

#### Dealing Cards from a `Stack`

The `deal()`

method simulates dealing a single card from the
stack. The first card is removed from the stack and returned to the caller.

function stackDeal() { if (this.cards.length > 0) return this.cards.shift(); else return null; }

The `draw()`

method does the same thing, except that it allows
you to specify any card in the stack by passing an index value in the call.

function stackDraw(n) { var card; if (n >= 0 && n < this.cards.length) { card = this.cards[n]; this.cards.splice(n, 1); } else card = null; return card; }

The index value is zero-based, so `draw(0)`

is equivalent to
`deal().`

Note that if no cards are left in a stack or if an
invalid value is given, `null`

is returned. You can find out how
many cards are in a stack at any given time using the `cardCount()`

method.

function stackCardCount() { return this.cards.length; }

#### Adding Cards to a `Stack`

The `addCard()`

method appends a `Card`

object to
the end of the stack's card array.

function stackAddCard(card) { this.cards.push(card); }

As and example, you could define one `Stack`

for a deck and one
for a poker hand, then deal from the deck to the hand.

var deck = new Stack(); var hand = new Stack(); var i; deck.makeDeck(1); for (i = 0; i < 5; i++) hand.addCard(deck.deal());

#### Combining `Stacks`

The final method let's you combine two stacks.

function stackCombine(stack) { this.cards = this.cards.concat(stack.cards); stack.cards = new Array(); }

It takes a `Stack`

object as an argument and appends its cards to
the current stack. Note that the stack being appended is emptied of cards. So
if `stack1`

contained A♣, 7♥, 3♦, Q♥ and
`stack2`

contained K♠, 5♣, the call

stack1.combine(stack2);

would leave `stack1`

with A♣, 7♥, 3♦,
Q♥, K♠, 5♣ while `stack2`

would be empty.

With the `Stack`

object in place, you can play around with a
demo to see how they might be put to use in
managing sets of cards.