Example #1
0
int main(int argc, char **argv)
{
	int i;
	int player = 0;
	int numPlayers = 2;
	int kingdomCardTypes[10] = {
		adventurer, smithy, village, salvager, minion,
		feast, gardens, mine, remodel, baron
	};
	int randomSeed = time(NULL);
	int ret;
	struct gameState game;

	// Setup a contrived game state for testing.
	{
		initializeGame(numPlayers, kingdomCardTypes, randomSeed, &game);
		game.whoseTurn = player;

		// Three of the five cards in the deck are treasures.
		int preDeck[] = {copper, silver, smithy, estate, gold};
		int preDeckCount = 5;
		for (i = 0; i < preDeckCount; i++) {
			game.deck[player][i] = preDeck[i];
		}
		game.deckCount[player] = preDeckCount;

		// One of the three cards in the hand is a treasure.
		int preHand[] = {copper, curse, remodel};
		int preHandCount = 3;
		for (i = 0; i < preHandCount; i++) {
			game.hand[player][i] = preHand[i];
		}
		game.handCount[player] = preHandCount;

		// The discard pile is empty.
		game.discardCount[player] = 0;
	}

	// Apply the adventurer card effect.
	ret = adventurerCardEffect(&game);

	// Compare the actual results against expectations.
	{
		// The operations should be successful.
		if (ret == 0) {
			printf("adventurerCardEffect() PASSED: Return value check\n");
		} else {
			printf("adventurerCardEffect() FAILED: Return value check\n");
			printf("  Expected: %d, Resulted: %d", 0, ret);
		}

		// Four cards needed to be drawn in order to acquire two treasures.
		int postDeck[] = {copper};
		int postDeckCount = 1;
		if (game.deckCount[player] == postDeckCount
		    && cardArrayCmp(game.deck[player], postDeck, postDeckCount) == 0
		) {
			printf("adventurerCardEffect() PASSED: Deck check \n");
		} else {
			printf("adventurerCardEffect() FAILED: Deck check \n");
			printf("  Expected: ");
			printCardArray(postDeck, postDeckCount);
			printf(", Resulted: ");
			printCardArray(game.deck[player], game.deckCount[player]);
			printf("\n");
		}

		// The hand then contains the two drawn treasure cards.
		int postHand[] = {copper, curse, remodel, gold, silver};
		int postHandCount = 5;
		if (game.handCount[player] == postHandCount
		    && cardArrayCmp(game.hand[player], postHand, postHandCount) == 0
		) {
			printf("adventurerCardEffect() PASSED: Hand check\n");
		}
		else {
			printf("adventurerCardEffect() FAILED: Hand check\n");
			printf("  Expected: ");
			printCardArray(postHand, postHandCount);
			printf(", Resulted: ");
			printCardArray(game.hand[player], game.handCount[player]);
			printf("\n");
		}

		// A total of three treasures should now be in hand.
		int treasures = 0;
		for (i = 0; i < game.handCount[player]; i++) {
			int card = game.hand[player][i];
			if (card == copper || card == silver || card == gold) {
				treasures++;
			}
		}
		if (treasures == 3) {
			printf("adventurerCardEffect() PASSED: Hand treasure count check\n");
		}
		else {
			printf("adventurerCardEffect() FAILED: Hand treasure count check\n");
			printf("  Expected: %d, Resulted: %d\n", 3, treasures);
		}

		// Two cards were discarded during the treasure drawing process.
		int postDiscard[] = {estate, smithy};
		int postDiscardCount = 2;
		if (game.discardCount[player] == postDiscardCount
		    && cardArrayCmp(game.discard[player], postDiscard, postDiscardCount) == 0
		) {
			printf("adventurerCardEffect() PASSED: Discard check\n");
		} else {
			printf("adventurerCardEffect() FAILED: Discard check\n");
			printf("  Expected: ");
			printCardArray(postDiscard, postDiscardCount);
			printf(", Resulted: ");
			printCardArray(game.discard[player], game.discardCount[player]);
			printf("\n");
		}
	}

	return 0;
}
Example #2
0
int main() {
  printf("*** Testing adventurerCardEffect *** \n");

  struct gameState game;
  int cards[10] = { adventurer, council_room, feast, gardens, mine, remodel, smithy, village, baron, great_hall };
  int all_cards[17] = { adventurer, council_room, feast, gardens, mine, remodel, smithy, village, baron, great_hall, copper, silver, gold, estate, duchy, province, curse };
  int player = 0;
  int other_player = 1;
  initializeGame(2, cards, 1, &game);

  //Test if two treatures added to hand with normal deck
  int handSize = game.handCount[player] + 1;
  adventurerCardEffect(player, 0, &game);
  if (handSize == game.handCount[player]) {
    printf("Player hand size increased by one.\n");
  } else {
    printf("FAIL: Player hand size failed to increase. Got %d, expected %d.\n", game.handCount[player], handSize);
  }
  int hand_count = game.handCount[player];
  int top_hand = game.hand[player][hand_count - 1];
  int sec_hand = game.hand[player][hand_count - 2];

  if ((top_hand >= 4 && top_hand <=6) && (sec_hand >= 4 && sec_hand <=6) ) {
    printf("Two treasure cards added to hand.\n");
  } else {
    printf("FAIL: two treasure cards not drawn.\n");
  }

  //Test to make sure additional treasures not added to deck
  int orig_copp = fullDeckCount(player, copper, &game);
  int orig_silv = fullDeckCount(player, silver, &game);
  int orig_gold = fullDeckCount(player, gold, &game);
  adventurerCardEffect(player, 0, &game);
  int new_copp = fullDeckCount(player, copper, &game);
  int new_silv = fullDeckCount(player, silver, &game);
  int new_gold = fullDeckCount(player, gold, &game);
  if ((orig_copp == new_copp) && (orig_silv == new_silv) && (orig_gold == new_gold)) {
    printf("No new treasures added to take.\n");
  } else {
    printf("FAIL: treasures added or removed from deck.\n");
  }
  // Test if other players are unaffected.
  int orig_deck_count = game.deckCount[other_player];
  int orig_hand_count = game.handCount[other_player];
  villageCardEffect(player, 0, &game);
  if (orig_deck_count == game.deckCount[other_player]) {
    printf("Other player's deck unaffected.\n");
  } else {
    printf("FAIL: other player's deck changed\n");
  }

  if (orig_hand_count == game.handCount[other_player]) {
    printf("Other player's hand unaffected.\n");
  } else {
    printf("FAIL: other player's hand changed\n");
  }

  // Test if global supplies unaffected
  int i;
  int changed = 0;
  int changed_card;
  int orig_supplies[17];
  for (i = 0; i < 17; i++) {
    orig_supplies[i] = game.supplyCount[all_cards[i]];
  }
  adventurerCardEffect(player, 0, &game);
  for (i = 0; i < 17; i++) {
    if (orig_supplies[i] != game.supplyCount[all_cards[i]]) {
      changed = 1;
      changed_card = all_cards[i];
    }
  }
  if (changed == 0) {
    printf("Supplies unchanged.\n");
  } else {
    printf("FAIL: supplies changed. Last cards supply changed was #%d\n.", changed_card);
  }

  return 0;

}
int main() {

  srand(time(NULL));

  struct gameState game;
  int cards[10] = { adventurer, council_room, feast, gardens, mine, remodel, smithy, village, baron, great_hall };
  int all_cards[17] = { adventurer, council_room, feast, gardens, mine, remodel, smithy, village, baron, great_hall, copper, silver, gold, estate, duchy, province, curse };
  int player = 0;
  int other_player = 1;
  int failed = 0;
  int fail_iteration;

  printf("Starting random testing for adventurerCardEffect.\n");

  int i;
  for (i = 0; i < 30000; i++) {
    //Randomize the game
    initializeGame(2, cards, 1, &game);
    game.playedCardCount = 0;
    genRandomDeck(player, &game);
    genRandomHand(player, &game);
    genRandomDiscard(player, &game);
    printf("Random iteration #%d, Deck size: %d, Hand size: %d, Discard size: %d\n", i, game.deckCount[player], game.handCount[player], game.discardCount[player]);
    int card_pos = pickHandCard(player, &game);
    game.hand[player][card_pos] = adventurer;

    //Capture preconditions
    int pre_money_count_deck = moneyCountDeck(player, &game);
    int pre_money_count_hand = moneyCountHand(player, &game);
    int start_hand_size = game.handCount[player];
    int total_cards = game.deckCount[player] + game.handCount[player] + game.discardCount[player];


    int j;
    int orig_supplies[17];
    for (j = 0; j < 17; j++) {
      orig_supplies[j] = game.supplyCount[all_cards[j]];
    }

    int orig_deck_count = game.deckCount[other_player];
    int orig_hand_count = game.handCount[other_player];
    int orig_disc_count = game.discardCount[other_player];

    //Run method
    adventurerCardEffect(player, card_pos, &game);

    //Check postconditions
    int post_money_count_deck = moneyCountDeck(player, &game);
    int post_money_count_hand = moneyCountHand(player, &game);

    if (pre_money_count_deck == 0) {
      if (start_hand_size - 1 != game.handCount[player]) {
        printf("Failed: No money in deck or discard, so handsize should decrease by 1.\n");
        printf("Expected %d, got %d\n", start_hand_size - 1, game.handCount[player]);
        failed++;
        fail_iteration = i;
      }
      if (post_money_count_deck != pre_money_count_deck || post_money_count_hand != pre_money_count_hand) {
        printf("Failed: No money in deck or discard, so number of coins should be unchanged in hand and deck.\n");
        failed++;
        fail_iteration = i;
      }

    } else if (pre_money_count_deck == 1) {
      if (start_hand_size != game.handCount[player] ) {
        printf("Failed: One money in deck or discard, so handsize should stay the same.\n");
        failed++;
        fail_iteration = i;
      }
      if (post_money_count_deck != pre_money_count_deck - 1 || post_money_count_hand != pre_money_count_hand + 1) {
        printf("Failed: One money in deck or discard, so number of coins should be +1 in hand and -1 in deck.\n");
        failed++;
        fail_iteration = i;
      }

    } else if (pre_money_count_deck > 1) {
      if (start_hand_size + 1 != game.handCount[player]) {
        printf("Failed: At least two money in deck or discard, so handsize should increase by 1.\n");
        failed++;
        fail_iteration = i;
      }
      if (post_money_count_deck != pre_money_count_deck - 2 || post_money_count_hand != pre_money_count_hand + 2) {
        printf("Failed: Two money in deck or discard, so number of coins should be +2 in hand and -2 in deck.\n");
        failed++;
        fail_iteration = i;
      }
    }

    int post_total_cards = game.deckCount[player] + game.handCount[player] + game.discardCount[player] + game.playedCardCount;
    if (total_cards != post_total_cards) {
      printf("Failed: started with %d cards total, ended with %d\n", total_cards, post_total_cards);
      failed += 1;
      fail_iteration = i;
    }

    int post_deck_count = game.deckCount[other_player];
    int post_hand_count = game.handCount[other_player];
    int post_disc_count = game.discardCount[other_player];
    if (post_deck_count != orig_deck_count || post_hand_count != orig_hand_count || post_disc_count != orig_disc_count) {
      printf("Failed: other player's cards were affected.\n");
      failed++;
      fail_iteration = i;
    }

    int changed = 0;
    int changed_card;

    for (j = 0; j < 17; j++) {
      if (orig_supplies[j] != game.supplyCount[all_cards[j]]) {
        changed = 1;
        changed_card = all_cards[j];
      }
    }
    if (changed != 0) {
      printf("FAIL: supplies changed. Last cards supply changed was #%d\n.", changed_card);
      failed++;
      fail_iteration = i;
    }
  }

  if (failed == 0) {
    printf("All tests passed!\n");
  } else {
    printf("FAILED:  Number of failed tests: %d. Last failure was for iteration #%d.\n", failed, fail_iteration);
  }
  return 0;
}
Example #4
0
int cardEffect(int card, int choice1, int choice2, int choice3, struct gameState *state, int handPos, int *bonus) {
    int i;
    int j;
    int x;
    int currentPlayer = whoseTurn(state);
    int nextPlayer = currentPlayer + 1;

    int tributeRevealedCards[2] = {-1, -1};
    int temphand[MAX_HAND];    // moved above the if statement

    if (nextPlayer > (state->numPlayers - 1)) {
        nextPlayer = 0;
    }

    //uses switch to select card and perform actions
    switch (card) {
    case adventurer:
        return adventurerCardEffect(currentPlayer, state);

    case council_room:
        //+4 Cards
        for (i = 0; i < 4; i++) {
            drawCard(currentPlayer, state);
        }

        //+1 Buy
        state->numBuys++;

        //Each other player draws a card
        for (i = 0; i < state->numPlayers; i++) {
            if (i != currentPlayer) {
                drawCard(i, state);
            }
        }

        //put played card in played card pile
        discardCard(handPos, currentPlayer, state, 0);

        return 0;

    case feast:
        //gain card with cost up to 5
        //Backup hand
        for (i = 0; i <= state->handCount[currentPlayer]; i++) {
            temphand[i] = state->hand[currentPlayer][i];            //Backup card
            state->hand[currentPlayer][i] = -1;            //Set to nothing
        }
        //Backup hand

        //Update Coins for Buy
        updateCoins(currentPlayer, state, 5);
        x = 1;        //Condition to loop on
        while (x == 1) {        //Buy one card
            if (supplyCount(choice1, state) <= 0) {
                if (DEBUG) {
                    printf("None of that card left, sorry!\n");
                }

                if (DEBUG) {
                    printf("Cards Left: %d\n", supplyCount(choice1, state));
                }
            }
            else if (state->coins < getCost(choice1)) {
                printf("That card is too expensive!\n");

                if (DEBUG) {
                    printf("Coins: %d < %d\n", state->coins, getCost(choice1));
                }
            }
            else {

                if (DEBUG) {
                    printf("Deck Count: %d\n", state->handCount[currentPlayer] + state->deckCount[currentPlayer] +
                           state->discardCount[currentPlayer]);
                }

                gainCard(choice1, state, 0, currentPlayer);                //Gain the card
                x = 0;                //No more buying cards

                if (DEBUG) {
                    printf("Deck Count: %d\n", state->handCount[currentPlayer] + state->deckCount[currentPlayer] +
                           state->discardCount[currentPlayer]);
                }

            }
        }

        //Reset Hand
        for (i = 0; i <= state->handCount[currentPlayer]; i++) {
            state->hand[currentPlayer][i] = temphand[i];
            temphand[i] = -1;
        }
        //Reset Hand

        return 0;

    case gardens:
        return -1;

    case mine:
        j = state->hand[currentPlayer][choice1];         //store card we will trash

        if (state->hand[currentPlayer][choice1] < copper || state->hand[currentPlayer][choice1] > gold) {
            return -1;
        }

        if (choice2 > treasure_map || choice2 < curse) {
            return -1;
        }

        if ((getCost(state->hand[currentPlayer][choice1]) + 3) > getCost(choice2)) {
            return -1;
        }

        gainCard(choice2, state, 2, currentPlayer);

        //discard card from hand
        discardCard(handPos, currentPlayer, state, 0);

        //discard trashed card
        for (i = 0; i < state->handCount[currentPlayer]; i++) {
            if (state->hand[currentPlayer][i] == j) {
                discardCard(i, currentPlayer, state, 0);
                break;
            }
        }

        return 0;

    case remodel:
        j = state->hand[currentPlayer][choice1];         //store card we will trash

        if ((getCost(state->hand[currentPlayer][choice1]) + 2) > getCost(choice2)) {
            return -1;
        }

        gainCard(choice2, state, 0, currentPlayer);

        //discard card from hand
        discardCard(handPos, currentPlayer, state, 0);

        //discard trashed card
        for (i = 0; i < state->handCount[currentPlayer]; i++) {
            if (state->hand[currentPlayer][i] == j) {
                discardCard(i, currentPlayer, state, 0);
                break;
            }
        }


        return 0;

    case smithy:
        return smithyCardEffect(currentPlayer, handPos, state);

    case village:
        //+1 Card
        drawCard(currentPlayer, state);

        //+2 Actions
        state->numActions = state->numActions + 2;

        //discard played card from hand
        discardCard(handPos, currentPlayer, state, 0);
        return 0;

    case baron:
        state->numBuys++;        //Increase buys by 1!
        if (choice1 > 0) {        //Boolean true or going to discard an estate
            int p = 0;            //Iterator for hand!
            int card_not_discarded = 1;            //Flag for discard set!
            while (card_not_discarded) {
                if (state->hand[currentPlayer][p] == estate) {                //Found an estate card!
                    state->coins += 4;                    //Add 4 coins to the amount of coins
                    state->discard[currentPlayer][state->discardCount[currentPlayer]] = state->hand[currentPlayer][p];
                    state->discardCount[currentPlayer]++;
                    for (; p < state->handCount[currentPlayer]; p++) {
                        state->hand[currentPlayer][p] = state->hand[currentPlayer][p + 1];
                    }
                    state->hand[currentPlayer][state->handCount[currentPlayer]] = -1;
                    state->handCount[currentPlayer]--;
                    card_not_discarded = 0;                    //Exit the loop
                }
                else if (p > state->handCount[currentPlayer]) {
                    if (DEBUG) {
                        printf("No estate cards in your hand, invalid choice\n");
                        printf("Must gain an estate if there are any\n");
                    }
                    if (supplyCount(estate, state) > 0) {
                        gainCard(estate, state, 0, currentPlayer);
                        state->supplyCount[estate]--;                        //Decrement estates
                        if (supplyCount(estate, state) == 0) {
                            isGameOver(state);
                        }
                    }
                    card_not_discarded = 0;                    //Exit the loop
                }

                else {
                    p++;                    //Next card
                }
            }
        }

        else {
            if (supplyCount(estate, state) > 0) {
                gainCard(estate, state, 0, currentPlayer);                //Gain an estate
                state->supplyCount[estate]--;                //Decrement Estates
                if (supplyCount(estate, state) == 0) {
                    isGameOver(state);
                }
            }
        }


        return 0;

    case great_hall:
        return greatHallCardEffect(currentPlayer, handPos, state);

    case minion:
        //+1 action
        state->numActions++;

        //discard card from hand
        discardCard(handPos, currentPlayer, state, 0);

        if (choice1)         //+2 coins
        {
            state->coins = state->coins + 2;
        }

        else if (choice2)         //discard hand, redraw 4, other players with 5+ cards discard hand and draw 4
        {
            //discard hand
            while (numHandCards(state) > 0) {
                discardCard(handPos, currentPlayer, state, 0);
            }

            //draw 4
            for (i = 0; i < 4; i++) {
                drawCard(currentPlayer, state);
            }

            //other players discard hand and redraw if hand size > 4
            for (i = 0; i < state->numPlayers; i++) {
                if (i != currentPlayer) {
                    if (state->handCount[i] > 4) {
                        //discard hand
                        while (state->handCount[i] > 0) {
                            discardCard(handPos, i, state, 0);
                        }

                        //draw 4
                        for (j = 0; j < 4; j++) {
                            drawCard(i, state);
                        }
                    }
                }
            }

        }
        return 0;

    case steward:
        if (choice1 == 1) {
            //+2 cards
            drawCard(currentPlayer, state);
            drawCard(currentPlayer, state);
        }
        else if (choice1 == 2) {
            //+2 coins
            state->coins = state->coins + 2;
        }
        else {
            //trash 2 cards in hand
            discardCard(choice2, currentPlayer, state, 1);
            discardCard(choice3, currentPlayer, state, 1);
        }

        //discard card from hand
        discardCard(handPos, currentPlayer, state, 0);
        return 0;

    case tribute:
        if ((state->discardCount[nextPlayer] + state->deckCount[nextPlayer]) <= 1) {
            if (state->deckCount[nextPlayer] > 0) {
                tributeRevealedCards[0] = state->deck[nextPlayer][state->deckCount[nextPlayer] - 1];
                state->deckCount[nextPlayer]--;
            }
            else if (state->discardCount[nextPlayer] > 0) {
                tributeRevealedCards[0] = state->discard[nextPlayer][state->discardCount[nextPlayer] - 1];
                state->discardCount[nextPlayer]--;
            }
            else {
                //No Card to Reveal
                if (DEBUG) {
                    printf("No cards to reveal\n");
                }
            }
        }

        else {
            if (state->deckCount[nextPlayer] == 0) {
                for (i = 0; i < state->discardCount[nextPlayer]; i++) {
                    state->deck[nextPlayer][i] = state->discard[nextPlayer][i];                    //Move to deck
                    state->deckCount[nextPlayer]++;
                    state->discard[nextPlayer][i] = -1;
                    state->discardCount[nextPlayer]--;
                }

                shuffle(nextPlayer, state);                //Shuffle the deck
            }
            tributeRevealedCards[0] = state->deck[nextPlayer][state->deckCount[nextPlayer] - 1];
            state->deck[nextPlayer][state->deckCount[nextPlayer]--] = -1;
            state->deckCount[nextPlayer]--;
            tributeRevealedCards[1] = state->deck[nextPlayer][state->deckCount[nextPlayer] - 1];
            state->deck[nextPlayer][state->deckCount[nextPlayer]--] = -1;
            state->deckCount[nextPlayer]--;
        }

        if (tributeRevealedCards[0] == tributeRevealedCards[1]) {        //If we have a duplicate card, just drop one
            state->playedCards[state->playedCardCount] = tributeRevealedCards[1];
            state->playedCardCount++;
            tributeRevealedCards[1] = -1;
        }

        for (i = 0; i <= 2; i++) {
            if (tributeRevealedCards[i] == copper || tributeRevealedCards[i] == silver ||
                tributeRevealedCards[i] == gold) {            //Treasure cards
                state->coins += 2;
            }

            else if (tributeRevealedCards[i] == estate || tributeRevealedCards[i] == duchy ||
                     tributeRevealedCards[i] == province || tributeRevealedCards[i] == gardens ||
                     tributeRevealedCards[i] == great_hall) {            //Victory Card Found
                drawCard(currentPlayer, state);
                drawCard(currentPlayer, state);
            }
            else {            //Action Card
                state->numActions = state->numActions + 2;
            }
        }

        return 0;

    case ambassador:
        j = 0;         //used to check if player has enough cards to discard

        if (choice2 > 2 || choice2 < 0) {
            return -1;
        }

        if (choice1 == handPos) {
            return -1;
        }

        for (i = 0; i < state->handCount[currentPlayer]; i++) {
            if (i != handPos && i == state->hand[currentPlayer][choice1] && i != choice1) {
                j++;
            }
        }
        if (j < choice2) {
            return -1;
        }

        if (DEBUG) {
            printf("Player %d reveals card number: %d\n", currentPlayer, state->hand[currentPlayer][choice1]);
        }

        //increase supply count for choosen card by amount being discarded
        state->supplyCount[state->hand[currentPlayer][choice1]] += choice2;

        //each other player gains a copy of revealed card
        for (i = 0; i < state->numPlayers; i++) {
            if (i != currentPlayer) {
                gainCard(state->hand[currentPlayer][choice1], state, 0, i);
            }
        }

        //discard played card from hand
        discardCard(handPos, currentPlayer, state, 0);

        //trash copies of cards returned to supply
        for (j = 0; j < choice2; j++) {
            for (i = 0; i < state->handCount[currentPlayer]; i++) {
                if (state->hand[currentPlayer][i] == state->hand[currentPlayer][choice1]) {
                    discardCard(i, currentPlayer, state, 1);
                    break;
                }
            }
        }

        return 0;

    case cutpurse:
        return cutpurseCardEffect(currentPlayer, handPos, state);

    case embargo:
        //+2 Coins
        state->coins = state->coins + 2;

        //see if selected pile is in play
        if (state->supplyCount[choice1] == -1) {
            return -1;
        }

        //add embargo token to selected supply pile
        state->embargoTokens[choice1]++;

        //trash card
        discardCard(handPos, currentPlayer, state, 1);
        return 0;

    case outpost:
        //set outpost flag
        state->outpostPlayed++;

        //discard card
        discardCard(handPos, currentPlayer, state, 0);
        return 0;

    case salvager:
        //+1 buy
        state->numBuys++;

        if (choice1) {
            //gain coins equal to trashed card
            state->coins = state->coins + getCost(handCard(choice1, state));
            //trash card
            discardCard(choice1, currentPlayer, state, 1);
        }

        //discard card
        discardCard(handPos, currentPlayer, state, 0);
        return 0;

    case sea_hag:
        for (i = 0; i < state->numPlayers; i++) {
            if (i != currentPlayer) {
                state->discard[i][state->discardCount[i]] = state->deck[i][state->deckCount[i]--];
                state->deckCount[i]--;
                state->discardCount[i]++;
                state->deck[i][state->deckCount[i]--] = curse;                //Top card now a curse
            }
        }
        return 0;

    case treasure_map:
        return treasureMapCardEffect(currentPlayer, handPos, state);
    }

    return -1;
}