bool CanPlace(int t, int h, int b, VoxelInfo[, ,] neighbourhood) { bool res = neighbourhood[t, h, b].Type == VoxelType.EMPTY; if (h < 2) res = res && neighbourhood[t, h + 1, b].Type != VoxelType.PINE_NEEDLE; if (h > 0) res = res && neighbourhood[t, h - 1, b].Type != VoxelType.PINE_NEEDLE; return res && neighbourhood[1, 1, 1].Resources < 51; }
private bool CanFungusGrowOn(int t, int h, int b, VoxelInfo[, ,] neighbourhood) { bool res = false; if (t < 2) res = res || TypeInformation.CanFungusGrowOn(neighbourhood[t + 1, h, b].Type); if (t > 0) res = res || TypeInformation.CanFungusGrowOn(neighbourhood[t - 1, h, b].Type); if (h < 2) res = res || TypeInformation.CanFungusGrowOn(neighbourhood[t, h + 1, b].Type); if (h > 0) res = res || TypeInformation.CanFungusGrowOn(neighbourhood[t, h - 1, b].Type); if (b < 2) res = res || TypeInformation.CanFungusGrowOn(neighbourhood[t, h, b + 1].Type); if (b > 0) res = res || TypeInformation.CanFungusGrowOn(neighbourhood[t, h, b - 1].Type); return res; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.NOBLEROT_FUNGUS)) return null; VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; int min = 0;// TypeInformation.GetGrowingSteps(VoxelType.NOBLEROT_FUNGUS) / 2; int max = TypeInformation.GetGrowingSteps(VoxelType.NOBLEROT_FUNGUS) / 2; int growadd; if (gen == 0) { int fung = 0; VoxelType voxeltype; // check the neighbourhood for (int t = 0; t < 3; ++t) for (int h = 0; h < 3; ++h) for (int b = 0; b < 3; ++b) if (!(t == 1 && h == 1 && b == 1)) // if not the voxel itself { voxeltype = neighbourhood[t, h, b].Type; if ((TypeInformation.IsBiomass(voxeltype) // there is a voxel in which the fungus can grow || voxeltype == VoxelType.EMPTY) // or the field is empty && !TypeInformation.IsGroundOrFungus(voxeltype)) { if (CanFungusGrowOn(t, h, b, neighbourhood)) // there is a voxel in d6 on which the fungus can grow on { // grow growadd = 0; if (voxeltype == VoxelType.ROCK || voxeltype == VoxelType.TEAK_WOOD) growadd = -30; if (voxeltype == VoxelType.PINE_WOOD || voxeltype == VoxelType.BEECH_WOOD || voxeltype == VoxelType.REDWOOD) growadd = 10; output[t, h, b] = new VoxelInfo(VoxelType.NOBLEROT_FUNGUS, true, 0, 0, random.Next(min, max) + growadd); } } } // check for kill the fungus (if in d6 all places are occupied) if (TypeInformation.IsGroundOrFungus(neighbourhood[2, 1, 1].Type)) fung++; if (TypeInformation.IsGroundOrFungus(neighbourhood[0, 1, 1].Type)) fung++; if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 2, 1].Type)) fung++; if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 0, 1].Type)) fung++; if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 1, 2].Type)) fung++; if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 1, 0].Type)) fung++; if (fung == 6) output[2, 1, 1] = new VoxelInfo(VoxelType.NOBLEROT_FUNGUS); } return output; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.TEAK_WOOD)) return null; int height = random.Next((int)(TypeInformation.GetGrowHeight(VoxelType.TEAK_WOOD) *0.75), (int)(TypeInformation.GetGrowHeight(VoxelType.TEAK_WOOD) * 1.25)); VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; if (gen == 0) { // Grow a 2x2 quad (override current generation) output[1, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); output[2, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); output[1, 1, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); output[2, 1, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 1].Type) || neighbourhood[1, 0, 1].Type == VoxelType.EMPTY) output[1, 0, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 1].Type) || neighbourhood[2, 0, 1].Type == VoxelType.EMPTY) output[2, 0, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 2].Type) || neighbourhood[1, 0, 2].Type == VoxelType.EMPTY) output[1, 0, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 2].Type) || neighbourhood[2, 0, 2].Type == VoxelType.EMPTY) output[2, 0, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); } else if (gen < height) { Int3 coord = DirectionConverter.FromDirection(DirectionConverter.ToOppositeDirection(neighbourhood[1, 1, 1].From)); // Grow in given direction if (TypeInformation.IsNotWoodButBiomass(neighbourhood[coord.X, coord.Y, coord.Z].Type) || neighbourhood[coord.X, coord.Y, coord.Z].Type == VoxelType.EMPTY) { output[coord.X, coord.Y, coord.Z] = new VoxelInfo(VoxelType.TEAK_WOOD, true, gen + 1,0,0,neighbourhood[1,1,1].From); } output[1, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD); } else { if (neighbourhood[1, 1, 1].From == Direction.DOWN) { if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 2, 1].Type) || neighbourhood[1, 2, 1].Type == VoxelType.EMPTY) { output[1, 2, 1] = new VoxelInfo(VoxelType.TEAK_LEAF, true, 1); } } output[1, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD); } return output; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.PINE_NEEDLE)) return null; VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; int res = neighbourhood[1, 1, 1].Resources; if (gen == 0) { output[1, 1, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE); if(TypeInformation.IsNotWoodButBiomass(neighbourhood[1,2,1].Type) || neighbourhood[1,2,1].Type == VoxelType.EMPTY) output[1, 2, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE); if (CanPlace(2, 1, 1, neighbourhood)) output[2, 1, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, 1); if (CanPlace(0, 1, 1, neighbourhood)) output[0, 1, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, 1); if (CanPlace(1, 1, 2, neighbourhood)) output[1, 1, 2] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, 1); if (CanPlace(1, 1, 0, neighbourhood)) output[1, 1, 0] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, 1); } else if (gen < TypeInformation.GetGrowHeight(VoxelType.PINE_NEEDLE)) { // Grow to the side //output[1, 2, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, gen + 1); //output[1, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD); output[1, 1, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE); if (CanPlace(2, 1, 1, neighbourhood)) output[2, 1, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, gen + random.Next(0, 3), res += 10, random.Next(0, TypeInformation.GetGrowingSteps(VoxelType.PINE_NEEDLE))); if (CanPlace(0, 1, 1, neighbourhood)) output[0, 1, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, gen + random.Next(0, 3), res += 10, random.Next(0, TypeInformation.GetGrowingSteps(VoxelType.PINE_NEEDLE))); if (CanPlace(1, 1, 2, neighbourhood)) output[1, 1, 2] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, gen + random.Next(0, 3), res += 10, random.Next(0, TypeInformation.GetGrowingSteps(VoxelType.PINE_NEEDLE))); if (CanPlace(1, 1, 0, neighbourhood)) output[1, 1, 0] = new VoxelInfo(VoxelType.PINE_NEEDLE, true, gen + random.Next(0, 3), res += 10, random.Next(0, TypeInformation.GetGrowingSteps(VoxelType.PINE_NEEDLE))); } else { // Grow upwards one last time //output[1, 2, 1] = new VoxelInfo(VoxelType.TEAK_WOOD); output[1, 1, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE); } return output; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.BEECH_WOOD)) return null; VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; if (gen == 0) { // Grow 2x2 and ovveride current generation output[1, 1, 1] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1, 10); output[2, 1, 1] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1, 10); output[1, 1, 2] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1, 10); output[2, 1, 2] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1, 10); } else if (gen == 1 && neighbourhood[1, 1, 1].Resources == 10) { // Grow Cross and ovveride current generation output[1, 1, 1] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1, 0, TypeInformation.GetGrowingSteps(VoxelType.PINE_WOOD) / 2); if (neighbourhood[2, 1, 1].Type == VoxelType.EMPTY) output[2, 1, 1] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1); if (neighbourhood[0, 1, 1].Type == VoxelType.EMPTY) output[0, 1, 1] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1); if (neighbourhood[1, 1, 2].Type == VoxelType.EMPTY) output[1, 1, 2] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1); if (neighbourhood[1, 1, 0].Type == VoxelType.EMPTY) output[1, 1, 0] = new VoxelInfo(VoxelType.BEECH_WOOD, true, 1); } else if(gen < TypeInformation.GetGrowHeight(VoxelType.BEECH_WOOD)) { // Grow upwards output[1, 2, 1] = new VoxelInfo(VoxelType.BEECH_WOOD, true, gen + 1); output[1, 1, 1] = new VoxelInfo(VoxelType.BEECH_WOOD); } else { // Grow upwards one last time output[1, 2, 1] = new VoxelInfo(VoxelType.BEECH_WOOD); output[1, 1, 1] = new VoxelInfo(VoxelType.BEECH_WOOD); } return output; }
/// <summary> /// Load a MagicaVoxel .vox format file into the custom ushort[] structure that we use for voxel chunks. /// </summary> /// <param name="stream">An open BinaryReader stream that is the .vox file.</param> /// <param name="overrideColors">Optional color lookup table for converting RGB values into my internal engine color format.</param> /// <returns>The voxel chunk data for the MagicaVoxel .vox file.</returns> public static Vector3[,,] LoadModel(string filename) { FileStream fs = File.Open(filename, FileMode.Open); BinaryReader stream = new BinaryReader(fs); VoxelInfo[] voxelData = null; List <VoxelInfo[]> frames = new List <VoxelInfo[]>(); List <Vector3> sizes = new List <Vector3>(); string magic = new string(stream.ReadChars(4)); int version = stream.ReadInt32(); Dictionary <int, Vector3> colorTable = new Dictionary <int, Vector3>(); Vector3[,,] voxels = null; // a MagicaVoxel .vox file starts with a 'magic' 4 character 'VOX ' identifier if (magic == "VOX ") { int sizex = 0, sizey = 0, sizez = 0; //bool subsample = false; while (stream.BaseStream.Position < stream.BaseStream.Length) { // each chunk has an ID, size and child chunks char[] chunkId = stream.ReadChars(4); int chunkSize = stream.ReadInt32(); int childChunks = stream.ReadInt32(); string chunkName = new string(chunkId); // there are only 2 chunks we only care about, and they are SIZE and XYZI if (chunkName == "SIZE") { if (voxelData != null) { frames.Add(voxelData); sizes.Add(new Vector3(sizex, sizez, sizey)); voxelData = null; voxels = null; } sizex = stream.ReadInt32(); sizey = stream.ReadInt32(); sizez = stream.ReadInt32(); stream.ReadBytes(chunkSize - 4 * 3); } else if (chunkName == "XYZI") { // XYZI contains n voxels int numVoxels = stream.ReadInt32(); // each voxel has x, y, z and color index values voxelData = new VoxelInfo[numVoxels]; for (int i = 0; i < voxelData.Length; i++) { voxelData[i] = new VoxelInfo(stream); } } else if (chunkName == "RGBA") { colorTable.Clear(); for (int i = 0; i < 256; i++) { byte r = stream.ReadByte(); byte g = stream.ReadByte(); byte b = stream.ReadByte(); byte a = stream.ReadByte(); if (!colorTable.ContainsKey(i + 1)) { colorTable.Add(i + 1, new Vector3((float)(r) / 256.0f, (float)(g) / 256.0f, (float)(b) / 256.0f)); } } } else { byte[] chunk = stream.ReadBytes(chunkSize); //Console.WriteLine(System.Text.Encoding.Default.GetString(chunk)); } // read any excess bytes } frames.Add(voxelData); sizes.Add(new Vector3(sizex, sizez, sizey)); for (int q = 0; q < frames.Count; q++) { voxelData = frames[q]; if (colorTable.Count == 0) { for (int i = 0; i < default_palette.Length; i++) { float color = (float)(default_palette[i] % (256 * 256 * 256)); colorTable[i + 1] = new Vector3((float)(color % 256) / 256.0f, (float)(Math.Floor(color / 256) % 256) / 256.0f, (float)(Math.Floor(color / 256 / 256) % (256 * 256)) / 256.0f); } } voxels = new Vector3[(int)sizes[q].X, (int)sizes[q].Z, (int)sizes[q].Y]; for (int x = 0; x < (int)sizes[q].X; x++) { for (int y = 0; y < (int)sizes[q].Y; y++) { for (int z = 0; z < (int)sizes[q].Z; z++) { voxels[x, z, y] = negative; } } } for (int i = 0; i < voxelData.Length; i++) { if (voxelData[i].x >= 0 && voxelData[i].x < sizes[q].X && voxelData[i].y >= 0 && voxelData[i].y < sizes[q].Z && voxelData[i].z >= 0 && voxelData[i].z < sizes[q].Y) { voxels[voxelData[i].x, voxelData[i].y, voxelData[i].z] = colorTable[voxelData[i].color]; } } fs.Close(); stream.Close(); return(voxels); } } fs.Close(); stream.Close(); return(null); }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD)) return null; VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; if (gen == 0) { // Grow 3x3 and ovveride current generation output[1, 1, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 1, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 2); output[2, 1, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4); output[0, 1, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4); output[1, 1, 2] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4); output[1, 1, 0] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4); output[2, 1, 2] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2); output[2, 1, 0] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2); output[0, 1, 2] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2); output[0, 1, 0] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 1].Type) || neighbourhood[2, 0, 1].Type == VoxelType.EMPTY) output[2, 0, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4,Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[0, 0, 1].Type) || neighbourhood[0, 0, 1].Type == VoxelType.EMPTY) output[0, 0, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 2].Type) || neighbourhood[1, 0, 2].Type == VoxelType.EMPTY) output[1, 0, 2] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 0].Type) || neighbourhood[1, 0, 0].Type == VoxelType.EMPTY) output[1, 0, 0] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.SPRUCE_WOOD) / 4, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 2].Type) || neighbourhood[2, 0, 2].Type == VoxelType.EMPTY) output[2, 0, 2] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0,0,Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 0].Type) || neighbourhood[2, 0, 0].Type == VoxelType.EMPTY) output[2, 0, 0] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2,0,0,Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[0, 0, 2].Type) || neighbourhood[0, 0, 2].Type == VoxelType.EMPTY) output[0, 0, 2] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[0, 0, 0].Type) || neighbourhood[0, 0, 0].Type == VoxelType.EMPTY) output[0, 0, 0] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, 2, 0, 0, Direction.UP); } else if (gen < TypeInformation.GetGrowHeight(VoxelType.SPRUCE_WOOD)) { // Grow upwards // Grow in given direction Int3 coord = DirectionConverter.FromDirection(DirectionConverter.ToOppositeDirection(neighbourhood[1, 1, 1].From)); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[coord.X, coord.Y, coord.Z].Type) || neighbourhood[coord.X, coord.Y, coord.Z].Type == VoxelType.EMPTY) { output[coord.X, coord.Y, coord.Z] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, gen + 1, 0, 0, neighbourhood[1, 1, 1].From); } //output[1, 2, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD, true, gen + 1); output[1, 1, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD); } else { // Grow upwards one last time //output[1, 2, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD); if (neighbourhood[1, 1, 1].From != Direction.UP) { output[1, 2, 1] = new VoxelInfo(VoxelType.SPRUCE_NEEDLE, true); } output[1, 1, 1] = new VoxelInfo(VoxelType.SPRUCE_WOOD); } return output; }
private bool IsWalkable(VoxelInfo voxelInfo) { return voxelInfo.Type == VoxelType.EMPTY; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.HESPEROPHANES_CINNEREUS)) return null; VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; int res = neighbourhood[1, 1, 1].Resources; int t = random.Next(0, 3); int h = random.Next(0, 3); int b = random.Next(0, 3); if (gen == 0) { if (IsWalkable(neighbourhood[t, h, b])) { output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY); output[t, h, b] = new VoxelInfo(VoxelType.HESPEROPHANES_CINNEREUS, true, 1); } else { output[1, 1, 1] = new VoxelInfo(VoxelType.HESPEROPHANES_CINNEREUS, true, 1); } } else if (gen < TypeInformation.GetGrowHeight(VoxelType.HESPEROPHANES_CINNEREUS) && res == 10) { Int3 moveTo = DirectionConverter.FromDirection(neighbourhood[1, 1, 1].From); t = moveTo.X; h = moveTo.Y; b = moveTo.Z; output[t, h, b] = new VoxelInfo(VoxelType.HESPEROPHANES_CINNEREUS, true, 0); if (random.Next(0, 11) > 7) output[1, 1, 1] = new VoxelInfo(VoxelType.HESPEROPHANES_CINNEREUS, true, gen + random.Next(1, 5), 0, TypeInformation.GetGrowingSteps(VoxelType.HESPEROPHANES_CINNEREUS), Direction.SELF); else output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY); } else// if (gen < TypeInformation.GetGrowHeight(VoxelType.HESPEROPHANES_CINNEREUS)) { Direction food = FoodInDirection(neighbourhood); if (food != Direction.SELF) { Int3 foodPos = DirectionConverter.FromDirection(food); int eattime = -10; if (neighbourhood[foodPos.X, foodPos.Y, foodPos.Z].Type == VoxelType.PINE_WOOD || neighbourhood[foodPos.X, foodPos.Y, foodPos.Z].Type == VoxelType.SPRUCE_WOOD) eattime = -20; if (neighbourhood[foodPos.X, foodPos.Y, foodPos.Z].Type == VoxelType.TEAK_WOOD || neighbourhood[foodPos.X, foodPos.Y, foodPos.Z].Type == VoxelType.OAK_WOOD) eattime = -5; output[1, 1, 1] = new VoxelInfo(VoxelType.HESPEROPHANES_CINNEREUS, true, gen + random.Next(0, 3), 10, eattime, food); } else if (IsWalkable(neighbourhood[t, h, b])) { output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY); output[t, h, b] = new VoxelInfo(VoxelType.HESPEROPHANES_CINNEREUS, true, gen + random.Next(1, 5)); } else { output[1, 1, 1] = new VoxelInfo(VoxelType.HESPEROPHANES_CINNEREUS, true, gen + random.Next(1, 5)); } } /* else { output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY); }*/ return output; }
private Direction FoodInDirection(VoxelInfo[, ,] neighbourhood) { for (int t = 0; t < 3; ++t) for (int h = 0; h < 3; ++h) for (int b = 0; b < 3; ++b) if (!(t == 1 && h == 1 && b == 1)) // if not the voxel itself { if (TypeInformation.IsBiomass(neighbourhood[t, h, b].Type)) return DirectionConverter.ToDirection(t, h, b); } return Direction.SELF; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.PINE_WOOD)) return null; int height = random.Next((int)(TypeInformation.GetGrowHeight(VoxelType.PINE_WOOD) * 0.75), (int)(TypeInformation.GetGrowHeight(VoxelType.PINE_WOOD) * 1.25)); VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; int res = neighbourhood[1, 1, 1].Resources; if (gen == 0) { // Grow Cross and ovveride current generation output[1, 1, 1] = new VoxelInfo(VoxelType.PINE_WOOD, true, 1, 0, TypeInformation.GetGrowingSteps(VoxelType.PINE_WOOD) / 2); output[2, 1, 1] = new VoxelInfo(VoxelType.PINE_WOOD, true, 2, 30); output[0, 1, 1] = new VoxelInfo(VoxelType.PINE_WOOD, true, 2, 30); output[1, 1, 2] = new VoxelInfo(VoxelType.PINE_WOOD, true, 2, 30); output[1, 1, 0] = new VoxelInfo(VoxelType.PINE_WOOD, true, 2, 30); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 1].Type) || neighbourhood[1, 0, 1].Type == VoxelType.EMPTY) output[1, 0, 1] = new VoxelInfo(VoxelType.PINE_WOOD, true, random.Next(1,height), 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 1].Type) || neighbourhood[2, 0, 1].Type == VoxelType.EMPTY) output[2, 0, 1] = new VoxelInfo(VoxelType.PINE_WOOD, true, random.Next(1, height), 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[0, 0, 1].Type) || neighbourhood[0, 0, 1].Type == VoxelType.EMPTY) output[0, 0, 1] = new VoxelInfo(VoxelType.PINE_WOOD, true, random.Next(1, height), 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 2].Type) || neighbourhood[1, 0, 2].Type == VoxelType.EMPTY) output[1, 0, 2] = new VoxelInfo(VoxelType.PINE_WOOD, true, random.Next(1, height), 0, 0, Direction.UP); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 0].Type) || neighbourhood[1, 0, 0].Type == VoxelType.EMPTY) output[1, 0, 0] = new VoxelInfo(VoxelType.PINE_WOOD, true, random.Next(1, height), 0, 0, Direction.UP); } else if (gen == -1) { output[1, 2, 1] = new VoxelInfo(VoxelType.PINE_NEEDLE, true); output[1, 1, 1] = new VoxelInfo(VoxelType.PINE_WOOD); } else if (gen < height) { if (res > 0 && gen > TypeInformation.GetGrowHeight(VoxelType.PINE_WOOD) / 2) { if (random.Next(0, 11) > 7) { res -= 15; Direction grow = GetBranchDirection(neighbourhood); Int3 temp = DirectionConverter.FromDirection(grow); if (neighbourhood[temp.X, 0, temp.Z].Type == VoxelType.EMPTY || TypeInformation.IsNotWoodButBiomass(neighbourhood[temp.X, 0, temp.Z].Type)) { output[temp.X, temp.Y, temp.Z] = new VoxelInfo(VoxelType.PINE_WOOD, true, random.Next((int)(height * 0.75), height), 0, 0, DirectionConverter.ToOppositeDirection(grow)); } } } Int3 coord = DirectionConverter.FromDirection(DirectionConverter.ToOppositeDirection(neighbourhood[1, 1, 1].From)); // Grow in given direction if (TypeInformation.IsNotWoodButBiomass(neighbourhood[coord.X, coord.Y, coord.Z].Type) || neighbourhood[coord.X, coord.Y, coord.Z].Type == VoxelType.EMPTY) { output[coord.X, coord.Y, coord.Z] = new VoxelInfo(VoxelType.PINE_WOOD, true, gen + 1, res, 0, neighbourhood[1, 1, 1].From); } output[1, 1, 1] = new VoxelInfo(VoxelType.PINE_WOOD); } else { // Grow upwards one last time if(neighbourhood[1,1,1].From != Direction.UP) output[1, 2, 1] = new VoxelInfo(VoxelType.PINE_WOOD, true, -1, 0, TypeInformation.GetGrowingSteps(VoxelType.PINE_WOOD)); output[1, 1, 1] = new VoxelInfo(VoxelType.PINE_WOOD); } return output; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.OAK_WOOD)) return null; VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; int res = neighbourhood[1, 1, 1].Resources; if (gen == 0) { // Grow Cross and ovveride current generation output[1, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 0, TypeInformation.GetGrowingSteps(VoxelType.OAK_WOOD) / 2); output[2, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 10); output[0, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 10); output[1, 1, 2] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 10); output[1, 1, 0] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 10); } else if (gen == 1 && res == 10) { // Grow Cross and ovveride current generation output[1, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 2, 0, TypeInformation.GetGrowingSteps(VoxelType.OAK_WOOD) / 2); if (neighbourhood[2, 1, 1].Type == VoxelType.EMPTY) output[2, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 20); if (neighbourhood[0, 1, 1].Type == VoxelType.EMPTY) output[0, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 20); if (neighbourhood[1, 1, 2].Type == VoxelType.EMPTY) output[1, 1, 2] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 20); if (neighbourhood[1, 1, 0].Type == VoxelType.EMPTY) output[1, 1, 0] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 20); } else if (gen == 1 && res == 20) { int energy = 0; if (neighbourhood[1, 1, 0].Type != VoxelType.OAK_WOOD && neighbourhood[1, 1, 2].Type != VoxelType.OAK_WOOD) { energy = 3; if (neighbourhood[1, 1, 2].Type == VoxelType.EMPTY) output[1, 1, 2] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1); if (neighbourhood[1, 1, 0].Type == VoxelType.EMPTY) output[1, 1, 0] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1); } else if (neighbourhood[0, 1, 1].Type != VoxelType.OAK_WOOD && neighbourhood[2, 1, 1].Type != VoxelType.OAK_WOOD) { energy = 3; if (neighbourhood[2, 1, 1].Type == VoxelType.EMPTY) output[2, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1); if (neighbourhood[0, 1, 1].Type == VoxelType.EMPTY) output[0, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1); } output[1, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 2, energy, TypeInformation.GetGrowingSteps(VoxelType.OAK_WOOD) / 4); } else if (res == 4 && gen < 5) { if (neighbourhood[2, 1, 1].Type == VoxelType.EMPTY && neighbourhood[0, 1, 1].Type == VoxelType.OAK_WOOD) output[2, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, gen < 4, gen + 1, res); if (neighbourhood[0, 1, 1].Type == VoxelType.EMPTY && neighbourhood[2, 1, 1].Type == VoxelType.OAK_WOOD) output[0, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, gen < 4, gen + 1, res); if (neighbourhood[1, 1, 2].Type == VoxelType.EMPTY && neighbourhood[1, 1, 0].Type == VoxelType.OAK_WOOD) output[1, 1, 2] = new VoxelInfo(VoxelType.OAK_WOOD, gen < 4, gen + 1, res); if (neighbourhood[1, 1, 0].Type == VoxelType.EMPTY && neighbourhood[1, 1, 2].Type == VoxelType.OAK_WOOD) output[1, 1, 0] = new VoxelInfo(VoxelType.OAK_WOOD, gen < 4, gen + 1, res); /*if (!(gen < 4)) { if (neighbourhood[2, 1, 1].Type == VoxelType.EMPTY && neighbourhood[0, 1, 1].Type == VoxelType.OAK_WOOD) output[2, 1, 1] = new VoxelInfo(VoxelType.SPRUCE_NEEDLE, true, gen, res); if (neighbourhood[0, 1, 1].Type == VoxelType.EMPTY && neighbourhood[2, 1, 1].Type == VoxelType.OAK_WOOD) output[0, 1, 1] = new VoxelInfo(VoxelType.SPRUCE_NEEDLE, true, gen, res); if (neighbourhood[1, 1, 2].Type == VoxelType.EMPTY && neighbourhood[1, 1, 0].Type == VoxelType.OAK_WOOD) output[1, 1, 2] = new VoxelInfo(VoxelType.SPRUCE_NEEDLE, true, gen, res); if (neighbourhood[1, 1, 0].Type == VoxelType.EMPTY && neighbourhood[1, 1, 2].Type == VoxelType.OAK_WOOD) output[1, 1, 0] = new VoxelInfo(VoxelType.SPRUCE_NEEDLE, true, gen, res); }*/ } else if (gen < TypeInformation.GetGrowHeight(VoxelType.OAK_WOOD)) { // Grow upwards output[1, 2, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, gen + 1, res); output[1, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD); if (res == 3 && gen > TypeInformation.GetGrowHeight(VoxelType.OAK_WOOD) / 2 && random.Next(0, 11) > 6) { if (neighbourhood[2, 1, 1].Type == VoxelType.EMPTY) output[2, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 4); if (neighbourhood[0, 1, 1].Type == VoxelType.EMPTY) output[0, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 4); if (neighbourhood[1, 1, 2].Type == VoxelType.EMPTY) output[1, 1, 2] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 4); if (neighbourhood[1, 1, 0].Type == VoxelType.EMPTY) output[1, 1, 0] = new VoxelInfo(VoxelType.OAK_WOOD, true, 1, 4); } } else { // Grow upwards one last time output[1, 2, 1] = new VoxelInfo(VoxelType.SPRUCE_NEEDLE,true); output[1, 1, 1] = new VoxelInfo(VoxelType.OAK_WOOD); } return output; }
private Direction GetBranchDirection(VoxelInfo[, ,] neighbourhood) { if (neighbourhood[2, 1, 1].Type == VoxelType.PINE_WOOD && neighbourhood[0, 1, 1].Type == VoxelType.EMPTY) return DirectionConverter.ToDirection(0, 1, 1); if (neighbourhood[0, 1, 1].Type == VoxelType.PINE_WOOD && neighbourhood[2, 1, 1].Type == VoxelType.EMPTY) return DirectionConverter.ToDirection(2, 1, 1); if (neighbourhood[1, 1, 2].Type == VoxelType.PINE_WOOD && neighbourhood[1, 1, 0].Type == VoxelType.EMPTY) return DirectionConverter.ToDirection(1, 1, 0); if (neighbourhood[1, 1, 0].Type == VoxelType.PINE_WOOD && neighbourhood[1, 1, 2].Type == VoxelType.EMPTY) return DirectionConverter.ToDirection(1, 1, 2); return Direction.SELF; }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.TEAK_WOOD)) { return(null); } int height = random.Next((int)(TypeInformation.GetGrowHeight(VoxelType.TEAK_WOOD) * 0.75), (int)(TypeInformation.GetGrowHeight(VoxelType.TEAK_WOOD) * 1.25)); VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; if (gen == 0) { // Grow a 2x2 quad (override current generation) output[1, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); output[2, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); output[1, 1, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); output[2, 1, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1); if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 1].Type) || neighbourhood[1, 0, 1].Type == VoxelType.EMPTY) { output[1, 0, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); } if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 1].Type) || neighbourhood[2, 0, 1].Type == VoxelType.EMPTY) { output[2, 0, 1] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); } if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 0, 2].Type) || neighbourhood[1, 0, 2].Type == VoxelType.EMPTY) { output[1, 0, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); } if (TypeInformation.IsNotWoodButBiomass(neighbourhood[2, 0, 2].Type) || neighbourhood[2, 0, 2].Type == VoxelType.EMPTY) { output[2, 0, 2] = new VoxelInfo(VoxelType.TEAK_WOOD, true, 1, 0, 0, Direction.UP); } } else if (gen < height) { Int3 coord = DirectionConverter.FromDirection(DirectionConverter.ToOppositeDirection(neighbourhood[1, 1, 1].From)); // Grow in given direction if (TypeInformation.IsNotWoodButBiomass(neighbourhood[coord.X, coord.Y, coord.Z].Type) || neighbourhood[coord.X, coord.Y, coord.Z].Type == VoxelType.EMPTY) { output[coord.X, coord.Y, coord.Z] = new VoxelInfo(VoxelType.TEAK_WOOD, true, gen + 1, 0, 0, neighbourhood[1, 1, 1].From); } output[1, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD); } else { if (neighbourhood[1, 1, 1].From == Direction.DOWN) { if (TypeInformation.IsNotWoodButBiomass(neighbourhood[1, 2, 1].Type) || neighbourhood[1, 2, 1].Type == VoxelType.EMPTY) { output[1, 2, 1] = new VoxelInfo(VoxelType.TEAK_LEAF, true, 1); } } output[1, 1, 1] = new VoxelInfo(VoxelType.TEAK_WOOD); } return(output); }
private bool IsWalkable(VoxelInfo voxelInfo) { return(voxelInfo.Type == VoxelType.EMPTY); }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.HOUSE_LONGHORN_BEETLE)) { return(null); } VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; int res = neighbourhood[1, 1, 1].Resources; int t = random.Next(0, 3); int h = random.Next(0, 3); int b = random.Next(0, 3); if (gen == 0) { if (IsWalkable(neighbourhood[t, h, b])) { output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY);; output[t, h, b] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, 1); } else { output[1, 1, 1] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, 1); } } else if (gen < TypeInformation.GetGrowHeight(VoxelType.HOUSE_LONGHORN_BEETLE) && res == 10) { Int3 moveTo = DirectionConverter.FromDirection(neighbourhood[1, 1, 1].From); t = moveTo.X; h = moveTo.Y; b = moveTo.Z; output[t, h, b] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, 0); if (random.Next(0, 11) > 7) { output[1, 1, 1] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, gen + random.Next(1, 5), 0, TypeInformation.GetGrowingSteps(VoxelType.HOUSE_LONGHORN_BEETLE), Direction.SELF); } else { output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY); } } else //if (gen < TypeInformation.GetGrowHeight(VoxelType.HOUSE_LONGHORN_BEETLE)) { Direction food = FoodInDirection(neighbourhood); if (food != Direction.SELF) { Int3 foodPos = DirectionConverter.FromDirection(food); int eattime = -10; if (neighbourhood[foodPos.X, foodPos.Y, foodPos.Z].Type == VoxelType.BEECH_WOOD || neighbourhood[foodPos.X, foodPos.Y, foodPos.Z].Type == VoxelType.OAK_WOOD) { eattime = -20; } if (neighbourhood[foodPos.X, foodPos.Y, foodPos.Z].Type == VoxelType.SPRUCE_WOOD) { eattime = -5; } output[1, 1, 1] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, gen + random.Next(0, 3), 10, eattime, food); } else if (IsWalkable(neighbourhood[t, h, b])) { if (5 > random.Next(0, 15)) { output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY); output[t, h, b] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, gen + random.Next(1, 5)); } else { output[1, 1, 1] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, gen + random.Next(1, 5)); } } else { output[1, 1, 1] = new VoxelInfo(VoxelType.HOUSE_LONGHORN_BEETLE, true, gen + random.Next(1, 5)); } } /* else * { * output[1, 1, 1] = new VoxelInfo(VoxelType.EMPTY); * }*/ return(output); }
public VoxelInfo[, ,] ApplyRule(VoxelInfo[, ,] neighbourhood) { // Apply each 18-th turn if (neighbourhood[1, 1, 1].Ticks < TypeInformation.GetGrowingSteps(VoxelType.WHITEROT_FUNGUS)) { return(null); } VoxelInfo[, ,] output = new VoxelInfo[3, 3, 3]; int gen = neighbourhood[1, 1, 1].Generation; int min = 0;// TypeInformation.GetGrowingSteps(VoxelType.WHITEROT_FUNGUS) / 2; int max = TypeInformation.GetGrowingSteps(VoxelType.WHITEROT_FUNGUS) / 2; int growadd; if (gen == 0) { int fung = 0; VoxelType voxeltype; // check the neighbourhood for (int t = 0; t < 3; ++t) { for (int h = 0; h < 3; ++h) { for (int b = 0; b < 3; ++b) { if (!(t == 1 && h == 1 && b == 1)) // if not the voxel itself { voxeltype = neighbourhood[t, h, b].Type; if ((TypeInformation.IsBiomass(voxeltype) || // there is a voxel in which the fungus can grow voxeltype == VoxelType.EMPTY) && // or the field is empty !TypeInformation.IsGroundOrFungus(voxeltype)) { if (CanFungusGrowOn(t, h, b, neighbourhood)) // there is a voxel in d6 on which the fungus can grow on { // grow growadd = 0; if (voxeltype == VoxelType.ROCK || voxeltype == VoxelType.TEAK_WOOD) { growadd = -30; } if (voxeltype == VoxelType.PINE_WOOD || voxeltype == VoxelType.BEECH_WOOD || voxeltype == VoxelType.OAK_WOOD || voxeltype == VoxelType.REDWOOD) { growadd = 10; } output[t, h, b] = new VoxelInfo(VoxelType.WHITEROT_FUNGUS, true, 0, 0, (int)(random.Next(min, max) + growadd)); } } } } } } // check for kill the fungus (if in d6 all places are occupied) if (TypeInformation.IsGroundOrFungus(neighbourhood[2, 1, 1].Type)) { fung++; } if (TypeInformation.IsGroundOrFungus(neighbourhood[0, 1, 1].Type)) { fung++; } if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 2, 1].Type)) { fung++; } if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 0, 1].Type)) { fung++; } if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 1, 2].Type)) { fung++; } if (TypeInformation.IsGroundOrFungus(neighbourhood[1, 1, 0].Type)) { fung++; } if (fung == 6) { output[2, 1, 1] = new VoxelInfo(VoxelType.WHITEROT_FUNGUS); } } return(output); }