package server import ( "iter" "git.citrons.xyz/metronode/classic" ) type blockType int16 const ( walkThrough = classic.WalkThrough swimThrough = classic.SwimThrough solid = classic.Solid partiallySlippery = classic.PartiallySlippery fullySlippery = classic.FullySlippery water = classic.Water lava = classic.Lava rope = classic.Rope ) type blockSolidity byte const ( noSound = classic.NoSound woodSound = classic.WoodSound gravelSound = classic.GravelSound grassSound = classic.GrassSound stoneSound = classic.StoneSound metalSound = classic.MetalSound glassSound = classic.GlassSound woolSound = classic.WoolSound sandSound = classic.SandSound snowSound = classic.SnowSound ) type blockSound byte const ( opaque = classic.Opaque transparentGlass = classic.TransparentGlass transparentLeaves = classic.TransparentLeaves translucent = classic.Translucent invisible = classic.Invisible ) type blockOpacity byte const ( cubeShape = iota spriteShape cuboidShape ) type blockShape byte type textureId int const fillTextures = -1 type blockDef struct { Name string Solidity blockSolidity MovementSpeed byte Textures [6]textureId TransmitsLight bool WalkSound blockSound FullBright bool Shape blockShape Min [3]byte Max [3]byte Opacity blockOpacity FogDensity byte FogColor [3]byte Variants map[any]blockType } type rotateVariant int var rotationNames = []string {"-N", "-E", "-S", "-W"} func makeRotations(block blockType) { var variants = make(map[any]blockType) oldDef := blockDefinitions[block] for i := 0; i < 4; i++ { newBlock := block + blockType(i) if _, ok := blockDefinitions[newBlock]; i != 0 && ok { panic("variant would override existing block") } newDef := oldDef for j := 0; j < 4; j++ { k := (j + i) % 4 newDef.Textures[j + 1] = oldDef.Textures[k + 1] } var minX, minZ, maxX, maxZ byte switch i { case 1: minX = oldDef.Min[2] minZ = 16 - oldDef.Min[0] maxX = oldDef.Max[2] maxZ = 16 - oldDef.Max[0] case 2: minX = 16 - oldDef.Min[0] minZ = 16 - oldDef.Min[2] maxX = 16 - oldDef.Max[0] maxZ = 16 - oldDef.Max[2] case 3: minX = oldDef.Min[2] minZ = 16 - oldDef.Min[0] maxX = oldDef.Max[2] maxZ = 16 - oldDef.Max[0] } newDef.Min = [3]byte {byte(minX), oldDef.Min[1], byte(minZ)} newDef.Max = [3]byte {byte(maxX), oldDef.Max[1], byte(maxZ)} newDef.Name = newDef.Name + rotationNames[i] newDef.Variants = variants blockDefinitions[newBlock] = newDef } } func getBlockDefPackets() iter.Seq[classic.Packet] { return func(yield func(classic.Packet) bool) { for id, def := range blockDefinitions { var packet classic.Packet var ( transmitsLight byte fullBright byte ) if def.TransmitsLight { transmitsLight = 1 } if def.FullBright { fullBright = 1 } if def.Shape != spriteShape { var (i int; texture textureId) for i, texture = range def.Textures { if texture == fillTextures { break } } if texture == fillTextures { for i = i; i < len(def.Textures); i++ { def.Textures[i] = def.Textures[i - 1] } } if def.Shape == cubeShape { def.Min = [3]byte {0, 0, 0} def.Max = [3]byte {16, 16, 16} } packet = &classic.DefineBlockExt { BlockId: byte(id), Name: classic.PadString(def.Name), Solidity: byte(def.Solidity), MovementSpeed: def.MovementSpeed, TopTextureId: byte(def.Textures[0]), LeftTextureId: byte(def.Textures[4]), RightTextureId: byte(def.Textures[2]), FrontTextureId: byte(def.Textures[3]), BackTextureId: byte(def.Textures[1]), BottomTextureId: byte(def.Textures[5]), TransmitsLight: transmitsLight, WalkSound: byte(def.WalkSound), FullBright: fullBright, Min: def.Min, Max: def.Max, BlockDraw: byte(def.Opacity), FogDensity: def.FogDensity, FogColor: def.FogColor, } } else { packet = &classic.DefineBlock { BlockId: byte(id), Name: classic.PadString(def.Name), Solidity: byte(def.Solidity), MovementSpeed: def.MovementSpeed, SideTextureId: byte(def.Textures[1]), TransmitsLight: transmitsLight, WalkSound: byte(def.WalkSound), FullBright: fullBright, Shape: 0, BlockDraw: byte(def.Opacity), FogDensity: def.FogDensity, FogColor: def.FogColor, } } if !yield(packet) { return } } } }