func LoadWorldStore(worldPath string) (world *WorldStore, err os.Error) { levelData, err := loadLevelData(worldPath) if err != nil { return } // In both single-player and SMP maps, the 'spawn position' is stored in // the level data. x, xok := levelData.Lookup("Data/SpawnX").(*nbt.Int) y, yok := levelData.Lookup("Data/SpawnY").(*nbt.Int) z, zok := levelData.Lookup("Data/SpawnZ").(*nbt.Int) if !xok || !yok || !zok { err = os.NewError("Invalid map level data: does not contain Spawn{X,Y,Z}") log.Printf("%#v", levelData) return } spawnPosition := BlockXyz{ BlockCoord(x.Value), BlockYCoord(y.Value), BlockCoord(z.Value), } var timeTicks Ticks if timeTag, ok := levelData.Lookup("Data/Time").(*nbt.Long); ok { timeTicks = Ticks(timeTag.Value) } var chunkStores []chunkstore.IChunkStore persistantChunkStore, err := chunkstore.ChunkStoreForLevel(worldPath, levelData, DimensionNormal) if err != nil { return } chunkStores = append(chunkStores, chunkstore.NewChunkService(persistantChunkStore)) var seed int64 if seedNbt, ok := levelData.Lookup("Data/RandomSeed").(*nbt.Long); ok { seed = seedNbt.Value } else { seed = rand.NewSource(time.Seconds()).Int63() } chunkStores = append(chunkStores, chunkstore.NewChunkService(generation.NewTestGenerator(seed))) for _, store := range chunkStores { go store.Serve() } world = &WorldStore{ WorldPath: worldPath, Seed: seed, Time: timeTicks, LevelData: levelData, ChunkStore: chunkstore.NewChunkService(chunkstore.NewMultiStore(chunkStores)), SpawnPosition: spawnPosition, } go world.ChunkStore.Serve() return }
// NOTE: ChunkStoreForDimension shouldn't really be used in the server just // yet. func (world *WorldStore) ChunkStoreForDimension(dimension DimensionId) (store chunkstore.IChunkStore, err error) { fgStore, err := chunkstore.ChunkStoreForLevel(world.WorldPath, world.LevelData, dimension) if err != nil { return } store = chunkstore.NewChunkService(fgStore) go store.Serve() return }