1 package minecraft 2 3 import "testing" 4 5 func TestNewLevel(t *testing.T) { 6 m := NewMemPath() 7 l, err := NewLevel(m) 8 if err != nil { 9 t.Error(err.Error()) 10 return 11 } 12 x, y, z := int32(1534545), int32(23), int32(-56456) 13 l.Spawn(x, y, z) 14 x, y, z = l.GetSpawn() 15 if x != 1534545 || y != 23 || z != -56456 { 16 t.Errorf("[SG]etSpawn test failed, expecting 1534545, 23, -56456, got %d, %d, %d", x, y, z) 17 } 18 biomes := []struct { 19 x, z int32 20 Biome 21 }{ 22 {0, 0, 1}, 23 {45323, 5, 6}, 24 {56454, 868, 4}, 25 {45645, 23498, 22}, 26 {-42536, 0, 5}, 27 {-23465, 5426, 9}, 28 {7843, -3265, 12}, 29 {45, -2465783, 4}, 30 {2553, -26582, 4}, 31 {-2358, -4564, 8}, 32 {456, 45646, 5}, 33 } 34 blocks := []struct { 35 x, y, z int32 36 Block 37 }{ 38 {0, 0, 0, Block{ID: 12, Data: 13}}, 39 {0, 250, 0, Block{ID: 2, Data: 1}}, 40 {185, 0, 10115, Block{ID: 45, Data: 14}}, 41 {4564, 250, 4645, Block{ID: 67, Data: 4}}, 42 {4232, 25, -4234234, Block{ID: 143, Data: 7}}, 43 {-2427824, 35, 23214, Block{ID: 431, Data: 6}}, 44 {-23478621, 0, -12341234, Block{ID: 32, Data: 8}}, 45 {4438, 120, -3123, Block{ID: 98, Data: 13}}, 46 {9762, 45, 3873, Block{ID: 179, Data: 5}}, 47 {39234, 101, 37482, Block{ID: 258, Data: 11}}, 48 } 49 50 for n, biome := range biomes { 51 if err := l.SetBiome(biome.x, biome.z, biome.Biome); err != nil { 52 t.Error(err.Error()) 53 } else if tBiome, err := l.GetBiome(biome.x, biome.z); err != nil { 54 t.Error(err.Error()) 55 } else if tBiome != biome.Biome { 56 t.Errorf("biome test %d: expecting %s, got %s", n, biome, tBiome) 57 } 58 } 59 60 for n, block := range blocks { 61 if err := l.SetBlock(block.x, block.y, block.z, block.Block); err != nil { 62 t.Error(err.Error()) 63 } else if tBlock, err := l.GetBlock(block.x, block.y, block.z); err != nil { 64 t.Error(err.Error()) 65 } else if !block.EqualBlock(tBlock) { 66 t.Errorf("biome test %d: expecting %s, got %s", n, block, tBlock) 67 } 68 } 69 l.Save() 70 if l, err = NewLevel(m); err != nil { 71 t.Error(err.Error()) 72 return 73 } 74 x, y, z = l.GetSpawn() 75 l.Spawn(x, y, z) 76 if x != 1534545 || y != 23 || z != -56456 { 77 t.Errorf("[SG]etSpawn test failed, expecting 1534545, 23, -56456, got %d, %d, %d", x, y, z) 78 } 79 for n, biome := range biomes { 80 if tBiome, err := l.GetBiome(biome.x, biome.z); err != nil { 81 t.Error(err.Error()) 82 } else if tBiome != biome.Biome { 83 t.Errorf("biome test %d: expecting %s, got %s", n, biome.Biome, tBiome) 84 } 85 } 86 for n, block := range blocks { 87 if tBlock, err := l.GetBlock(block.x, block.y, block.z); err != nil { 88 t.Error(err.Error()) 89 } else if !block.EqualBlock(tBlock) { 90 t.Errorf("biome test %d: expecting %s, got %s", n, block, tBlock) 91 } 92 } 93 } 94 95 func TestSkyLight(t *testing.T) { 96 l, _ := NewLevel(NewMemPath()) 97 type posBlock struct { 98 x, y, z int32 99 Block 100 } 101 tests := []struct { 102 blocks []posBlock 103 light [][4]int32 //x, y, z, skyLight 104 }{ 105 {[]posBlock{ 106 {0, 20, 0, Block{ID: 39}}, 107 }, [][4]int32{ 108 {0, 20, 0, 15}, 109 {0, 21, 0, 15}, 110 {0, 19, 0, 15}, 111 {0, 26, 0, 15}, 112 {0, 31, 0, 15}, 113 {15, 31, 15, 15}, 114 {15, 15, 15, 15}, 115 {15, 31, 0, 15}, 116 {0, 15, 15, 15}, 117 {0, 31, 0, 15}, 118 {23, 23, 23, 15}, 119 }}, 120 {[]posBlock{ 121 {0, 20, 0, Block{ID: 1}}, 122 }, [][4]int32{ 123 {0, 21, 0, 15}, 124 {0, 20, 0, 0}, 125 {0, 19, 0, 14}, 126 {0, 18, 0, 14}, 127 {0, 16, 0, 14}, 128 }}, 129 {[]posBlock{ 130 {-1, 20, -1, Block{ID: 1}}, 131 {-1, 20, 0, Block{ID: 1}}, 132 {-1, 20, 1, Block{ID: 1}}, 133 {0, 20, -1, Block{ID: 1}}, 134 {0, 20, 1, Block{ID: 1}}, 135 {1, 20, -1, Block{ID: 1}}, 136 {1, 20, 0, Block{ID: 1}}, 137 {1, 20, 1, Block{ID: 1}}, 138 }, [][4]int32{ 139 {0, 19, 0, 13}, 140 {-1, 19, -1, 14}, 141 {1, 19, 1, 14}, 142 {-1, 19, 1, 14}, 143 {1, 19, -1, 14}, 144 {0, 18, 0, 13}, 145 {-1, 18, -1, 14}, 146 {1, 18, 1, 14}, 147 {-1, 18, 1, 14}, 148 {1, 18, -1, 14}, 149 }}, 150 {[]posBlock{ 151 {0, 20, 0, Block{}}, 152 }, [][4]int32{ 153 {0, 20, 0, 15}, 154 {0, 19, 0, 15}, 155 {0, 18, 0, 15}, 156 {0, 16, 0, 15}, 157 }}, 158 {[]posBlock{ 159 {0, 20, 0, Block{ID: 1}}, 160 }, [][4]int32{ 161 {0, 20, 0, 0}, 162 {0, 19, 0, 13}, 163 {0, 19, 1, 14}, 164 {1, 19, 0, 14}, 165 {0, 18, 0, 13}, 166 {0, 16, 0, 13}, 167 }}, 168 {[]posBlock{ 169 {10, 20, 10, Block{ID: 1}}, 170 {11, 20, 10, Block{ID: 1}}, 171 {12, 20, 10, Block{ID: 1}}, 172 {13, 20, 10, Block{ID: 1}}, 173 {14, 20, 10, Block{ID: 1}}, 174 {10, 20, 11, Block{ID: 1}}, 175 {11, 20, 11, Block{ID: 1}}, 176 {12, 20, 11, Block{ID: 1}}, 177 {13, 20, 11, Block{ID: 1}}, 178 {14, 20, 11, Block{ID: 1}}, 179 {10, 20, 12, Block{ID: 1}}, 180 {11, 20, 12, Block{ID: 1}}, 181 {12, 20, 12, Block{ID: 1}}, 182 {13, 20, 12, Block{ID: 1}}, 183 {14, 20, 12, Block{ID: 1}}, 184 {10, 20, 13, Block{ID: 1}}, 185 {11, 20, 13, Block{ID: 1}}, 186 {12, 20, 13, Block{ID: 1}}, 187 {13, 20, 13, Block{ID: 1}}, 188 {14, 20, 13, Block{ID: 1}}, 189 {10, 20, 14, Block{ID: 1}}, 190 {11, 20, 14, Block{ID: 1}}, 191 {12, 20, 14, Block{ID: 1}}, 192 {13, 20, 14, Block{ID: 1}}, 193 {14, 20, 14, Block{ID: 1}}, 194 195 {10, 19, 10, Block{ID: 1}}, 196 {11, 19, 10, Block{ID: 1}}, 197 {12, 19, 10, Block{ID: 1}}, 198 {13, 19, 10, Block{ID: 1}}, 199 {14, 19, 10, Block{ID: 1}}, 200 {10, 19, 11, Block{ID: 1}}, 201 {14, 19, 11, Block{ID: 1}}, 202 {10, 19, 12, Block{ID: 1}}, 203 {14, 19, 12, Block{ID: 1}}, 204 {10, 19, 13, Block{ID: 1}}, 205 {14, 19, 13, Block{ID: 1}}, 206 {10, 19, 14, Block{ID: 1}}, 207 {11, 19, 14, Block{ID: 1}}, 208 {12, 19, 14, Block{ID: 1}}, 209 {13, 19, 14, Block{ID: 1}}, 210 {14, 19, 14, Block{ID: 1}}, 211 212 {10, 18, 10, Block{ID: 1}}, 213 {11, 18, 10, Block{ID: 1}}, 214 {12, 18, 10, Block{ID: 1}}, 215 {13, 18, 10, Block{ID: 1}}, 216 {14, 18, 10, Block{ID: 1}}, 217 {10, 18, 11, Block{ID: 1}}, 218 {14, 18, 11, Block{ID: 1}}, 219 {10, 18, 12, Block{ID: 1}}, 220 {14, 18, 12, Block{ID: 1}}, 221 {10, 18, 13, Block{ID: 1}}, 222 {14, 18, 13, Block{ID: 1}}, 223 {10, 18, 14, Block{ID: 1}}, 224 {11, 18, 14, Block{ID: 1}}, 225 {12, 18, 14, Block{ID: 1}}, 226 {13, 18, 14, Block{ID: 1}}, 227 {14, 18, 14, Block{ID: 1}}, 228 229 {10, 17, 10, Block{ID: 1}}, 230 {11, 17, 10, Block{ID: 1}}, 231 {12, 17, 10, Block{ID: 1}}, 232 {13, 17, 10, Block{ID: 1}}, 233 {14, 17, 10, Block{ID: 1}}, 234 {10, 17, 11, Block{ID: 1}}, 235 {14, 17, 11, Block{ID: 1}}, 236 {10, 17, 12, Block{ID: 1}}, 237 {14, 17, 12, Block{ID: 1}}, 238 {10, 17, 13, Block{ID: 1}}, 239 {14, 17, 13, Block{ID: 1}}, 240 {10, 17, 14, Block{ID: 1}}, 241 {11, 17, 14, Block{ID: 1}}, 242 {12, 17, 14, Block{ID: 1}}, 243 {13, 17, 14, Block{ID: 1}}, 244 {14, 17, 14, Block{ID: 1}}, 245 246 {10, 16, 10, Block{ID: 1}}, 247 {11, 16, 10, Block{ID: 1}}, 248 {12, 16, 10, Block{ID: 1}}, 249 {13, 16, 10, Block{ID: 1}}, 250 {14, 16, 10, Block{ID: 1}}, 251 {10, 16, 11, Block{ID: 1}}, 252 {11, 16, 11, Block{ID: 1}}, 253 {12, 16, 11, Block{ID: 1}}, 254 {13, 16, 11, Block{ID: 1}}, 255 {14, 16, 11, Block{ID: 1}}, 256 {10, 16, 12, Block{ID: 1}}, 257 {11, 16, 12, Block{ID: 1}}, 258 {12, 16, 12, Block{ID: 1}}, 259 {13, 16, 12, Block{ID: 1}}, 260 {14, 16, 12, Block{ID: 1}}, 261 {10, 16, 13, Block{ID: 1}}, 262 {11, 16, 13, Block{ID: 1}}, 263 {12, 16, 13, Block{ID: 1}}, 264 {13, 16, 13, Block{ID: 1}}, 265 {14, 16, 13, Block{ID: 1}}, 266 {10, 16, 14, Block{ID: 1}}, 267 {11, 16, 14, Block{ID: 1}}, 268 {12, 16, 14, Block{ID: 1}}, 269 {13, 16, 14, Block{ID: 1}}, 270 {14, 16, 14, Block{ID: 1}}, 271 }, [][4]int32{ 272 {10, 20, 10, 0}, 273 {14, 20, 14, 0}, 274 {12, 19, 12, 0}, 275 {13, 18, 13, 0}, 276 {11, 17, 11, 0}, 277 }}, 278 {[]posBlock{ 279 {100, 10, 100, Block{ID: 8}}, 280 }, [][4]int32{ 281 {100, 10, 100, 12}, 282 }}, 283 {[]posBlock{ 284 {99, 12, 100, Block{ID: 1}}, 285 {99, 11, 100, Block{ID: 1}}, 286 {99, 10, 100, Block{ID: 1}}, 287 {99, 9, 100, Block{ID: 1}}, 288 {99, 8, 100, Block{ID: 1}}, 289 {99, 7, 100, Block{ID: 1}}, 290 291 {101, 12, 100, Block{ID: 1}}, 292 {101, 11, 100, Block{ID: 1}}, 293 {101, 10, 100, Block{ID: 1}}, 294 {101, 9, 100, Block{ID: 1}}, 295 {101, 8, 100, Block{ID: 1}}, 296 {101, 7, 100, Block{ID: 1}}, 297 298 {100, 12, 99, Block{ID: 1}}, 299 {100, 11, 99, Block{ID: 1}}, 300 {100, 10, 99, Block{ID: 1}}, 301 {100, 9, 99, Block{ID: 1}}, 302 {100, 8, 99, Block{ID: 1}}, 303 {100, 7, 99, Block{ID: 1}}, 304 305 {100, 12, 101, Block{ID: 1}}, 306 {100, 11, 101, Block{ID: 1}}, 307 {100, 10, 101, Block{ID: 1}}, 308 {100, 9, 101, Block{ID: 1}}, 309 {100, 8, 101, Block{ID: 1}}, 310 {100, 7, 101, Block{ID: 1}}, 311 312 {100, 8, 100, Block{ID: 8}}, 313 {100, 7, 100, Block{ID: 1}}, 314 315 {100, 11, 100, Block{ID: 8}}, 316 {100, 9, 100, Block{ID: 8}}, 317 }, [][4]int32{ 318 {100, 8, 100, 3}, 319 {100, 9, 100, 6}, 320 {100, 10, 100, 9}, 321 {100, 11, 100, 12}, 322 }}, 323 {[]posBlock{ 324 {100, 12, 100, Block{ID: 8}}, 325 {100, 7, 100, Block{ID: 8}}, 326 {100, 6, 100, Block{ID: 1}}, 327 }, [][4]int32{ 328 {100, 6, 100, 0}, 329 {100, 7, 100, 0}, 330 {100, 8, 100, 0}, 331 {100, 9, 100, 3}, 332 {100, 10, 100, 6}, 333 {100, 11, 100, 9}, 334 {100, 12, 100, 12}, 335 }}, 336 {[]posBlock{ 337 {100, 6, 100, Block{}}, 338 }, [][4]int32{ 339 {100, 6, 100, 13}, 340 {100, 7, 100, 10}, 341 {100, 8, 100, 7}, 342 {100, 9, 100, 4}, 343 {100, 10, 100, 6}, 344 {100, 11, 100, 9}, 345 {100, 12, 100, 12}, 346 }}, 347 } 348 for n, test := range tests { 349 for _, b := range test.blocks { 350 l.SetBlock(b.x, b.y, b.z, b.Block) 351 } 352 for o, light := range test.light { 353 if m, _ := l.getSkyLight(light[0], light[1], light[2]); int32(m) != light[3] { 354 t.Errorf("test %d-%d: sky light level at [%d, %d, %d] does not match expected, got %d, expecting %d", n+1, o+1, light[0], light[1], light[2], m, light[3]) 355 } 356 } 357 } 358 } 359 360 func TestBlockLight(t *testing.T) { 361 l, _ := NewLevel(NewMemPath()) 362 type posBlock struct { 363 x, y, z int32 364 Block 365 } 366 tests := []struct { 367 blocks []posBlock 368 light [][4]int32 //x, y, z, skyLight 369 }{ 370 {[]posBlock{ //Test 1 371 {0, 10, 0, Block{ID: 89}}, 372 }, [][4]int32{ 373 {0, 10, 0, 15}, 374 {0, 9, 0, 14}, 375 {0, 8, 0, 13}, 376 {0, 7, 0, 12}, 377 {0, 6, 0, 11}, 378 {0, 5, 0, 10}, 379 {0, 4, 0, 9}, 380 {0, 3, 0, 8}, 381 {0, 2, 0, 7}, 382 {0, 1, 0, 6}, 383 {0, 0, 0, 5}, 384 {0, 11, 0, 14}, 385 {0, 12, 0, 13}, 386 {0, 13, 0, 12}, 387 {0, 14, 0, 11}, 388 {0, 15, 0, 10}, 389 {1, 10, 0, 14}, 390 {0, 10, 1, 14}, 391 {1, 10, 1, 13}, 392 }}, 393 {[]posBlock{ //Test 2 394 {-16, 15, 15, Block{ID: 20}}, 395 }, [][4]int32{ 396 {-1, 10, 0, 14}, 397 {-2, 10, 0, 13}, 398 {-3, 10, 0, 12}, 399 {-1, 10, 1, 13}, 400 {-1, 10, 2, 12}, 401 {-1, 10, 3, 11}, 402 {-1, 11, 0, 13}, 403 {-2, 11, 0, 12}, 404 }}, 405 {[]posBlock{ //Test 3 406 {-16, 15, 15, Block{}}, 407 {-1, 10, 0, Block{ID: 20}}, 408 }, [][4]int32{ 409 {-1, 10, 0, 14}, 410 {-2, 10, 0, 13}, 411 {-3, 10, 0, 12}, 412 {-1, 10, 1, 13}, 413 {-1, 10, 2, 12}, 414 {-1, 10, 3, 11}, 415 {-1, 11, 0, 13}, 416 {-2, 11, 0, 12}, 417 }}, 418 {[]posBlock{ //Test 4 419 {1, 10, 0, Block{ID: 1}}, 420 }, [][4]int32{ 421 {1, 10, 0, 0}, 422 {2, 10, 0, 11}, 423 {3, 10, 0, 10}, 424 {2, 10, 1, 12}, 425 {3, 10, 1, 11}, 426 {1, 9, 0, 13}, 427 {1, 11, 0, 13}, 428 {1, 9, 1, 12}, 429 }}, 430 } 431 for n, test := range tests { 432 for _, b := range test.blocks { 433 l.SetBlock(b.x, b.y, b.z, b.Block) 434 } 435 for o, light := range test.light { 436 if m, _ := l.getBlockLight(light[0], light[1], light[2]); int32(m) != light[3] { 437 t.Errorf("test %d-%d: block light level at [%d, %d, %d] does not match expected, got %d, expecting %d", n+1, o+1, light[0], light[1], light[2], m, light[3]) 438 } 439 } 440 } 441 } 442 443 func BenchmarkSkyLight(b *testing.B) { 444 l, _ := NewLevel(NewMemPath()) 445 block := Block{ID: 1} 446 for n := 0; n < b.N; n++ { 447 m := int32(n) 448 for i := int32(0); i < 5; i++ { 449 for j := int32(0); j < 5; j++ { 450 l.SetBlock(16*m+i, 20, j, block) 451 } 452 } 453 } 454 } 455 456 func (l *Level) getBlockLight(x, y, z int32) (uint8, error) { 457 c, err := l.getChunk(x, z, false) 458 if err != nil { 459 return 0, err 460 } else if c == nil { 461 return 0, nil 462 } 463 return c.GetBlockLight(x, y, z), nil 464 } 465 466 func (l *Level) getSkyLight(x, y, z int32) (uint8, error) { 467 c, err := l.getChunk(x, z, false) 468 if err != nil { 469 return 0, err 470 } else if c == nil { 471 return 15, nil 472 } 473 return c.GetSkyLight(x, y, z), nil 474 } 475