121 lines
3.2 KiB
Go
121 lines
3.2 KiB
Go
package game
|
|
|
|
import "fmt"
|
|
|
|
// Suit is the trade-in symbol printed on pet cards. Three pets of the same
|
|
// suit can be traded for a pick of the next tier's deck.
|
|
type Suit string
|
|
|
|
const (
|
|
SuitSun Suit = "sun"
|
|
SuitMoon Suit = "moon"
|
|
SuitStar Suit = "star"
|
|
SuitLeaf Suit = "leaf"
|
|
)
|
|
|
|
var suits = []Suit{SuitSun, SuitMoon, SuitStar, SuitLeaf}
|
|
|
|
// CardKind distinguishes pets from foods.
|
|
type CardKind string
|
|
|
|
const (
|
|
KindPet CardKind = "pet"
|
|
KindFood CardKind = "food"
|
|
)
|
|
|
|
// Food identifiers. Only apples exist for now; more foods come later.
|
|
const FoodApple = "apple"
|
|
|
|
// Card is a single physical card instance. IDs are unique per game.
|
|
type Card struct {
|
|
ID string `json:"id"`
|
|
Kind CardKind `json:"kind"`
|
|
Name string `json:"name"`
|
|
Tier int `json:"tier"`
|
|
Power int `json:"power,omitempty"`
|
|
Suit Suit `json:"suit,omitempty"`
|
|
// Effect is display text for the pet's ability. Effects are not yet
|
|
// implemented mechanically; the field keeps card data forward-compatible.
|
|
Effect string `json:"effect,omitempty"`
|
|
Food string `json:"food,omitempty"`
|
|
}
|
|
|
|
func (c Card) IsPet() bool { return c.Kind == KindPet }
|
|
func (c Card) IsFood() bool { return c.Kind == KindFood }
|
|
|
|
// petTemplate is the printed definition of a pet; each template appears as
|
|
// multiple card copies in its tier's shop deck.
|
|
type petTemplate struct {
|
|
Name string
|
|
Power int
|
|
}
|
|
|
|
const copiesPerPet = 2
|
|
|
|
// petTiers defines the shop decks. Index 0 is tier 1 (round 1) through
|
|
// index 5 for tier 6 (round 6). Suits are assigned round-robin per tier so
|
|
// every tier contains every suit.
|
|
var petTiers = [MaxRounds][]petTemplate{
|
|
{ // Tier 1
|
|
{"Ant", 1}, {"Cricket", 1}, {"Fish", 2}, {"Horse", 1},
|
|
{"Beaver", 2}, {"Otter", 1}, {"Pig", 3}, {"Mosquito", 2},
|
|
},
|
|
{ // Tier 2
|
|
{"Crab", 3}, {"Swan", 2}, {"Hedgehog", 3}, {"Peacock", 4},
|
|
{"Flamingo", 3}, {"Rat", 2}, {"Shrimp", 2}, {"Spider", 3},
|
|
},
|
|
{ // Tier 3
|
|
{"Dog", 4}, {"Badger", 4}, {"Camel", 3}, {"Giraffe", 3},
|
|
{"Kangaroo", 4}, {"Ox", 5}, {"Rabbit", 3}, {"Sheep", 4},
|
|
},
|
|
{ // Tier 4
|
|
{"Skunk", 5}, {"Hippo", 6}, {"Bison", 6}, {"Deer", 4},
|
|
{"Squirrel", 4}, {"Whale", 5}, {"Worm", 4}, {"Penguin", 5},
|
|
},
|
|
{ // Tier 5
|
|
{"Scorpion", 5}, {"Rhino", 7}, {"Monkey", 6}, {"Cow", 6},
|
|
{"Seal", 6}, {"Shark", 7}, {"Turkey", 5}, {"Crocodile", 8},
|
|
},
|
|
{ // Tier 6
|
|
{"Leopard", 8}, {"Boar", 9}, {"Fly", 7}, {"Gorilla", 9},
|
|
{"Mammoth", 10}, {"Snake", 8}, {"Tiger", 9}, {"Dragon", 10},
|
|
},
|
|
}
|
|
|
|
// newCardID mints a unique card ID within the game.
|
|
func (g *Game) newCardID() string {
|
|
g.NextCardID++
|
|
return fmt.Sprintf("c%d", g.NextCardID)
|
|
}
|
|
|
|
// buildShopDecks creates all six tier decks (unshuffled).
|
|
func (g *Game) buildShopDecks() {
|
|
g.ShopDecks = make([][]Card, MaxRounds)
|
|
for tierIdx, templates := range petTiers {
|
|
deck := make([]Card, 0, len(templates)*copiesPerPet)
|
|
for i, t := range templates {
|
|
for range copiesPerPet {
|
|
deck = append(deck, Card{
|
|
ID: g.newCardID(),
|
|
Kind: KindPet,
|
|
Name: t.Name,
|
|
Tier: tierIdx + 1,
|
|
Power: t.Power,
|
|
Suit: suits[i%len(suits)],
|
|
})
|
|
}
|
|
}
|
|
g.ShopDecks[tierIdx] = deck
|
|
}
|
|
}
|
|
|
|
// newApple mints an apple food card (from discarding, etc.).
|
|
func (g *Game) newApple() Card {
|
|
return Card{
|
|
ID: g.newCardID(),
|
|
Kind: KindFood,
|
|
Name: "Apple",
|
|
Food: FoodApple,
|
|
}
|
|
}
|