board.go 2.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113
  1. package board
  2. import (
  3. "bytes"
  4. "encoding/json"
  5. "fmt"
  6. "io"
  7. "math/rand"
  8. "time"
  9. )
  10. type Board struct {
  11. Cols int `json:"cols"`
  12. Rows int `json:"rows"`
  13. Tiles []Tile `json:"tiles"`
  14. }
  15. var rnd = rand.New(rand.NewSource(time.Now().UnixNano()))
  16. const maxIceWidth = 26
  17. // Create a new randomly generated board.
  18. func New(cols, rows int) Board {
  19. b := Board{cols, rows, make([]Tile, rows*cols)}
  20. for y := 0; y < rows; y++ {
  21. for x := 0; x < cols; x++ {
  22. b.randomizeTile(x, y)
  23. }
  24. }
  25. return b
  26. }
  27. // Set the tile in column x and row y to val.
  28. func (b Board) Set(x, y int, val Tile) {
  29. b.Tiles[y*b.Cols+x] = val
  30. }
  31. // Get the tile in column x and row y.
  32. func (b Board) Get(x, y int) Tile {
  33. return b.Tiles[y*b.Cols+x]
  34. }
  35. func (b Board) String() string {
  36. var buffer bytes.Buffer
  37. for y := 0; y < b.Rows; y++ {
  38. for x := 0; x < b.Cols; x++ {
  39. buffer.WriteString(b.Get(x, y).String())
  40. }
  41. buffer.WriteString(fmt.Sprintln())
  42. }
  43. return buffer.String()
  44. }
  45. type jsonTile struct {
  46. X int `json:"x"`
  47. Y int `json:"y"`
  48. Type string`json:"type"`
  49. Player string `json:"player,omitempty"`
  50. }
  51. func (b Board) WriteJSON(w io.Writer) {
  52. //fmt.Fpr
  53. fmt.Fprintf(w, "{rows=\"%v\",columns=\"%v\",tiles={", b.Rows, b.Cols)
  54. for y := 0; y < b.Rows; y++ {
  55. for x := 0; x < b.Cols; x++ {
  56. t := &jsonTile{x, y, b.Get(x, y).Name(), ""}
  57. bs, _ := json.Marshal(t)
  58. w.Write(bs)
  59. w.Write([]byte{','})
  60. }
  61. }
  62. fmt.Fprintf(w, "}}")
  63. }
  64. func (b Board) randomizeTile(x, y int) {
  65. switch {
  66. case b.isIglo(x, y):
  67. b.Set(x, y, Iglo)
  68. case b.isRock(x, y):
  69. b.Set(x, y, Rock)
  70. case b.isIce(x, y):
  71. b.Set(x, y, Ice)
  72. default:
  73. b.Set(x, y, Water)
  74. }
  75. }
  76. func (b Board) isIglo(x, y int) bool {
  77. return x == (b.Cols-1) && y == (b.Rows-1)/2
  78. }
  79. func (b Board) isRock(x, y int) bool {
  80. return rnd.Intn(10) > 7
  81. }
  82. func (b Board) isIce(x, y int) bool {
  83. leftLimit := (b.Cols - maxIceWidth) / 2
  84. rightLimit := b.Cols/2 + maxIceWidth/2
  85. return x > leftLimit && x < rightLimit && rnd.Intn(maxIceWidth) >= abs((b.Cols/2)-x)
  86. }
  87. func abs(a int) int {
  88. if a < 0 {
  89. return -a
  90. }
  91. return a
  92. }