Commit 838b8e93 authored by ceddral's avatar ceddral
Browse files

game: detect impossible pieces

impossible means the piece can not be placed on the
current board due to collisions in all free places
parent a146ed29
......@@ -324,17 +324,17 @@ func (p *Piece) render(v *tg.View, viewx, viewy int, board *Board, boardx, board
}
}
func (b *Board) DetectCollisions(s *StatePlacePiece) []bool {
func (b *Board) DetectCollisions(x, y int, p *Piece, rot Rotation) []bool {
cs := getAdjacentCoords(0, 0)
r := make([]bool, 0, 4)
for _, c := range cs {
nPlace, ok := b.Get(s.boardx + c.x, s.boardy + c.y)
nPlace, ok := b.Get(x + c.x, y + c.y)
if !ok {
r = append(r, false)
} else {
// field and neighbouring field are the middle fields on the border of both pieces
nField := nPlace.piece.f[nPlace.rot][1 - c.y][2 - (2 * c.x)]
field := s.p.f[s.rot][1 + c.y][2 + (2 * c.x)]
field := p.f[rot][1 + c.y][2 + (2 * c.x)]
r = append(r, nField.t != field.t)
}
}
......@@ -368,7 +368,7 @@ func (b *Board) renderCurrentPiece(p *GamePlayer, s *StatePlacePiece) {
viewx += pieceWidth
viewy += pieceHeight
cs := getAdjacentCoords(0, 0)
collisions := b.DetectCollisions(s)
collisions := b.DetectCollisions(s.boardx, s.boardy, s.p, s.rot)
_, occupied := b.Get(s.boardx, s.boardy)
hasNeighbour := b.HasNeighbour(s.boardx, s.boardy)
for i, c := range cs {
......
......@@ -42,6 +42,9 @@ func (m *GameMenu) Redraw(s GameState) {
if spp, ok := s.(*StatePlacePiece); ok {
spp.p.render(v, 0, line, nil, 0, 0, spp.rot, PMPlaces, nil)
}
if sip, ok := s.(*StateImpossiblePiece); ok {
sip.p.render(v, 0, line, nil, 0, 0, 0, PMPlayers, nil)
}
v.DrawTextClearLine(fg, bg, []byte(fmt.Sprintf("%d/%d pieces", 0, 1337)), 6, line)
line += 4
p := m.p
......@@ -451,15 +454,36 @@ type StatePlacePiece struct {
rot Rotation
}
func NewStatePlacePiece(g *Game, a *GamePlayer) *StatePlacePiece {
func NewStatePlacePiece(g *Game, a *GamePlayer) GameState {
if len(g.pieceOrder) == 0 {
// TODO wertung
panic("we did it")
}
p := g.drawPiece()
placeable := false
g.board.free.Range(func(key, value interface{})bool {
c := key.(Coord)
for rot := Rotation(0); rot < 4; rot++ {
collisions := g.board.DetectCollisions(c.x, c.y, p, rot)
anyCollision := false
for _, col := range collisions {
anyCollision = anyCollision || col
}
if anyCollision {
continue
}
placeable = true
return false
}
return true
})
if !placeable {
return NewStateImpossiblePiece(g, a, p)
}
return &StatePlacePiece{
agent: a,
g: g,
p: g.drawPiece(),
p: p,
boardx: 0,
boardy: 0,
rot: 0,
......@@ -488,7 +512,7 @@ func (s *StatePlacePiece) agentAction(p *GamePlayer, key Key) bool {
if !s.g.board.HasNeighbour(s.boardx, s.boardy) {
return true
}
collisions := s.g.board.DetectCollisions(s)
collisions := s.g.board.DetectCollisions(s.boardx, s.boardy, s.p, s.rot)
for _, c := range collisions {
if c {
return true
......@@ -529,6 +553,36 @@ func (s *StatePlacePiece) patientAction(p *GamePlayer, key Key) bool {
return false
}
type StateImpossiblePiece struct {
agent *GamePlayer
g *Game
p *Piece
}
func NewStateImpossiblePiece(g *Game, a *GamePlayer, p *Piece) *StateImpossiblePiece {
return &StateImpossiblePiece{
agent: a,
g: g,
p: p,
}
}
func (s *StateImpossiblePiece) getAgent() *GamePlayer { return s.agent }
func (s *StateImpossiblePiece) getGame() *Game { return s.g }
func (s *StateImpossiblePiece) String() string { return "StateImpossiblePiece" }
func (s *StateImpossiblePiece) agentTransition(p *GamePlayer) {}
func (s *StateImpossiblePiece) patientTransition(p *GamePlayer) {}
func (s *StateImpossiblePiece) agentAction(p *GamePlayer, key Key) bool {
if key == keyReturn {
s.g.broadcastState(NewStatePlacePiece(s.g, s.agent))
return true
}
return false
}
func (s *StateImpossiblePiece) patientAction(p *GamePlayer, key Key) bool { return false }
type StatePlaceFollower struct {
agent *GamePlayer
g *Game
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment