package game type PlayerNotificationType int const ( DeclaredActionNotification = iota ResolvedActionNotification PriorityNotification UpkeepPrompt BuyPrompt HandCardSelectionPrompt ) func (n PlayerNotification) IsPriorityNotification() bool { return n.Notification == PriorityNotification } type PlayerNotification struct { Notification PlayerNotificationType Context interface{} Error error } func NewPriorityNotification() PlayerNotification { return PlayerNotification{PriorityNotification, nil, nil} } func NewDeclaredActionNotification(a Action, err error) PlayerNotification { return PlayerNotification{DeclaredActionNotification, a, err} } func NewResolvedActionNotification(a Action, err error) PlayerNotification { return PlayerNotification{ResolvedActionNotification, a, err} } func NewUpkeepPrompt(u *Unit) PlayerNotification { return PlayerNotification{ResolvedActionNotification, u, nil} } func NewBuyPrompt() PlayerNotification { return PlayerNotification{BuyPrompt, nil, nil} } func NewHandCardSelectionPrompt(min, max int) PlayerNotification { return PlayerNotification{HandCardSelectionPrompt, []int{min, max}, nil} } type PlayerControl interface { RecvAction() Action SendNotification(PlayerNotification) } type DummyPlayerControl struct{ P *Player } func (c *DummyPlayerControl) RecvAction() Action { return NewPassPriority(c.P) } func (*DummyPlayerControl) SendNotification(PlayerNotification) {} type ChanPlayerControl struct { Actions chan Action Notifications chan PlayerNotification } func (c *ChanPlayerControl) SendAction(a Action) { c.Actions <- a } func (c *ChanPlayerControl) RecvAction() Action { return <-c.Actions } func (c *ChanPlayerControl) SendNotification(n PlayerNotification) { c.Notifications <- n } func (c *ChanPlayerControl) RecvNotification() *PlayerNotification { select { case n := <-c.Notifications: return &n default: return nil } } func NewChanPlayerControl() *ChanPlayerControl { a := make(chan Action) n := make(chan PlayerNotification) return &ChanPlayerControl{a, n} } func prompt(ctrl PlayerControl, notification PlayerNotification) Action { ctrl.SendNotification(NewPriorityNotification()) return ctrl.RecvAction() } func promptBuy(ctrl PlayerControl) Action { return prompt(ctrl, NewBuyPrompt()) } func promptAction(ctrl PlayerControl) Action { return prompt(ctrl, NewPriorityNotification()) }