/// <summary> /// This is the function that actually decides what mesh and texture each tile gets /// </summary> /// <param name="buffer">Buffer to put the chosen meshes into for combining</param> /// <param name="layer">layer currently being worked on</param> /// <param name="tile">The tile to get all the needed info from.</param> void FillMeshBuffer(out MeshCombineUtility.MeshInstance buffer, MeshLayer layer, MapDataStore.Tile tile) { buffer = new MeshCombineUtility.MeshInstance(); MeshContent mesh = null; if (tile.hidden) { buffer.meshData = null; return; } if (layer == MeshLayer.BuildingMaterial || layer == MeshLayer.BuildingMaterialCutout || layer == MeshLayer.NoMaterialBuilding || layer == MeshLayer.NoMaterialBuildingCutout || layer == MeshLayer.BuildingMaterialTransparent || layer == MeshLayer.NoMaterialBuildingTransparent ) { if(tile.buildingType == default(BuildingStruct)) { buffer.meshData = null; return; } if (!contentLoader.BuildingMeshConfiguration.GetValue(tile, layer, out mesh)) { buffer.meshData = null; return; } } else { if (!contentLoader.TileMeshConfiguration.GetValue(tile, layer, out mesh)) { buffer.meshData = null; return; } } buffer.meshData = mesh.MeshData[(int)layer]; buffer.transform = Matrix4x4.TRS(GameMap.DFtoUnityCoord(tile.position), mesh.GetRotation(tile), Vector3.one); Matrix4x4 shapeTextTransform = Matrix4x4.identity; NormalContent tileTexContent; if (mesh.NormalTexture == null) { if (layer == MeshLayer.BuildingMaterial || layer == MeshLayer.BuildingMaterialCutout || layer == MeshLayer.NoMaterialBuilding || layer == MeshLayer.NoMaterialBuildingCutout || layer == MeshLayer.BuildingMaterialTransparent || layer == MeshLayer.NoMaterialBuildingTransparent ) { if (contentLoader.BuildingShapeTextureConfiguration.GetValue(tile, layer, out tileTexContent)) shapeTextTransform = tileTexContent.UVTransform; } else { if (contentLoader.ShapeTextureConfiguration.GetValue(tile, layer, out tileTexContent)) shapeTextTransform = tileTexContent.UVTransform; } } else { shapeTextTransform = mesh.NormalTexture.UVTransform; } Matrix4x4 matTexTransform = Matrix4x4.identity; TextureContent matTexContent; if (contentLoader.MaterialTextureConfiguration.GetValue(tile, layer, out matTexContent)) matTexTransform = matTexContent.UVTransform; ColorContent newColorContent; Color newColor; if (contentLoader.ColorConfiguration.GetValue(tile, layer, out newColorContent)) { newColor = newColorContent.value; } else { MatPairStruct mat = new MatPairStruct(-1, -1); switch (layer) { case MeshLayer.StaticMaterial: case MeshLayer.StaticCutout: case MeshLayer.StaticTransparent: mat = tile.material; break; case MeshLayer.BaseMaterial: case MeshLayer.BaseCutout: case MeshLayer.BaseTransparent: mat = tile.base_material; break; case MeshLayer.LayerMaterial: case MeshLayer.LayerCutout: case MeshLayer.LayerTransparent: mat = tile.layer_material; break; case MeshLayer.VeinMaterial: case MeshLayer.VeinCutout: case MeshLayer.VeinTransparent: mat = tile.vein_material; break; case MeshLayer.NoMaterial: case MeshLayer.NoMaterialCutout: case MeshLayer.NoMaterialBuildingCutout: case MeshLayer.NoMaterialBuilding: case MeshLayer.NoMaterialBuildingTransparent: case MeshLayer.NoMaterialTransparent: break; case MeshLayer.Growth0Cutout: break; case MeshLayer.Growth1Cutout: break; case MeshLayer.Growth2Cutout: break; case MeshLayer.Growth3Cutout: break; case MeshLayer.BuildingMaterial: case MeshLayer.BuildingMaterialCutout: case MeshLayer.BuildingMaterialTransparent: mat = tile.buildingMaterial; break; default: break; } MaterialDefinition mattie; if (materials.TryGetValue(mat, out mattie)) { ColorDefinition color = mattie.state_color; if (color == null) newColor = Color.cyan; else newColor = new Color(color.red / 255.0f, color.green / 255.0f, color.blue / 255.0f, 1); } else { newColor = Color.grey; } } buffer.color = newColor; buffer.uv1Transform = matTexTransform; buffer.uv2Transform = shapeTextTransform; buffer.hiddenFaces = MeshCombineUtility.HiddenFaces.None; if (tile.North != null && tile.North.isWall) buffer.hiddenFaces |= MeshCombineUtility.HiddenFaces.North; if (tile.South != null && tile.South.isWall) buffer.hiddenFaces |= MeshCombineUtility.HiddenFaces.South; if (tile.East != null && tile.East.isWall) buffer.hiddenFaces |= MeshCombineUtility.HiddenFaces.East; if (tile.West != null && tile.West.isWall) buffer.hiddenFaces |= MeshCombineUtility.HiddenFaces.West; if (tile.Up != null && tile.Up.isSolidBase) buffer.hiddenFaces |= MeshCombineUtility.HiddenFaces.Up; if (tile.Down != null && tile.Down.isWall) buffer.hiddenFaces |= MeshCombineUtility.HiddenFaces.Down; }
/// <summary> /// This is the function that actually decides what mesh and texture each tile gets /// </summary> /// <param name="buffer">Buffer to put the chosen meshes into for combining</param> /// <param name="layer">layer currently being worked on</param> /// <param name="tile">The tile to get all the needed info from.</param> void FillMeshBuffer(out MeshCombineUtility.MeshInstance buffer, MeshLayer layer, MapDataStore.Tile tile, Vector3 pos) { buffer = new MeshCombineUtility.MeshInstance(); MeshContent meshContent = null; if(contentLoader.DesignationMeshConfiguration.GetValue(tile, layer, out meshContent)) { if(!meshContent.MeshData.ContainsKey(layer)) { buffer.meshData = null; return; } buffer.meshData = meshContent.MeshData[layer]; buffer.transform = Matrix4x4.TRS(pos, meshContent.GetRotation(tile), Vector3.one); if (meshContent.MaterialTexture != null) buffer.uv1Transform = meshContent.MaterialTexture.UVTransform; else buffer.uv1Transform = contentLoader.DefaultMatTexTransform; if (meshContent.ShapeTexture != null) buffer.uv2Transform = meshContent.ShapeTexture.UVTransform; else buffer.uv2Transform = contentLoader.DefaultShapeTexTransform; if (meshContent.SpecialTexture != null) buffer.uv3Transform = meshContent.SpecialTexture.UVTransform; else buffer.uv3Transform = contentLoader.DefaultSpecialTexTransform; buffer.hiddenFaces = CalculateHiddenFaces(tile); return; } switch (layer) { case MeshLayer.GrowthMaterial: case MeshLayer.GrowthMaterial1: case MeshLayer.GrowthMaterial2: case MeshLayer.GrowthMaterial3: case MeshLayer.GrowthCutout: case MeshLayer.GrowthCutout1: case MeshLayer.GrowthCutout2: case MeshLayer.GrowthCutout3: case MeshLayer.GrowthTransparent: case MeshLayer.GrowthTransparent1: case MeshLayer.GrowthTransparent2: case MeshLayer.GrowthTransparent3: { switch (tile.tiletypeMaterial) { case TiletypeMaterial.PLANT: case TiletypeMaterial.ROOT: case TiletypeMaterial.TREE_MATERIAL: case TiletypeMaterial.MUSHROOM: if (!contentLoader.GrowthMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } break; default: buffer.meshData = null; return; } } break; case MeshLayer.BuildingMaterial: case MeshLayer.NoMaterialBuilding: case MeshLayer.BuildingMaterialCutout: case MeshLayer.NoMaterialBuildingCutout: case MeshLayer.BuildingMaterialTransparent: case MeshLayer.NoMaterialBuildingTransparent: { if (tile.buildingType == default(BuildingStruct)) { buffer.meshData = null; return; } if (!contentLoader.BuildingMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } } break; default: { if (!contentLoader.TileMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } } break; } if (!meshContent.MeshData.ContainsKey(layer)) { buffer.meshData = null; return; } buffer.meshData = meshContent.MeshData[layer]; buffer.transform = Matrix4x4.TRS(pos, meshContent.GetRotation(tile), Vector3.one); Matrix4x4 shapeTextTransform = contentLoader.DefaultShapeTexTransform; NormalContent tileTexContent; if (meshContent.ShapeTexture == null) { if (layer == MeshLayer.BuildingMaterial || layer == MeshLayer.BuildingMaterialCutout || layer == MeshLayer.NoMaterialBuilding || layer == MeshLayer.NoMaterialBuildingCutout || layer == MeshLayer.BuildingMaterialTransparent || layer == MeshLayer.NoMaterialBuildingTransparent ) { if (contentLoader.BuildingShapeTextureConfiguration.GetValue(tile, layer, out tileTexContent)) shapeTextTransform = tileTexContent.UVTransform; } else { if (contentLoader.ShapeTextureConfiguration.GetValue(tile, layer, out tileTexContent)) shapeTextTransform = tileTexContent.UVTransform; } } else { shapeTextTransform = meshContent.ShapeTexture.UVTransform; } Matrix4x4 matTexTransform = contentLoader.DefaultMatTexTransform; if (meshContent.MaterialTexture != null && (layer == MeshLayer.NoMaterial || layer == MeshLayer.NoMaterialBuilding || layer == MeshLayer.NoMaterialBuildingCutout || layer == MeshLayer.NoMaterialBuildingTransparent || layer == MeshLayer.NoMaterialCutout || layer == MeshLayer.NoMaterialTransparent)) { matTexTransform = meshContent.MaterialTexture.UVTransform; } else { TextureContent matTexContent; if (contentLoader.MaterialTextureConfiguration.GetValue(tile, layer, out matTexContent)) matTexTransform = matTexContent.UVTransform; } Matrix4x4 specialTexTransform = Matrix4x4.identity; if(meshContent.SpecialTexture != null) { specialTexTransform = meshContent.SpecialTexture.UVTransform; } else { specialTexTransform = contentLoader.DefaultSpecialTexTransform; } ColorContent newColorContent; Color newColor; if (contentLoader.ColorConfiguration.GetValue(tile, layer, out newColorContent)) { newColor = newColorContent.value; } else { MatPairStruct mat = new MatPairStruct(-1, -1); switch (layer) { case MeshLayer.StaticMaterial: case MeshLayer.StaticCutout: case MeshLayer.StaticTransparent: mat = tile.material; break; case MeshLayer.BaseMaterial: case MeshLayer.BaseCutout: case MeshLayer.BaseTransparent: mat = tile.base_material; break; case MeshLayer.LayerMaterial: case MeshLayer.LayerCutout: case MeshLayer.LayerTransparent: mat = tile.layer_material; break; case MeshLayer.VeinMaterial: case MeshLayer.VeinCutout: case MeshLayer.VeinTransparent: mat = tile.vein_material; break; case MeshLayer.NoMaterial: case MeshLayer.NoMaterialCutout: case MeshLayer.NoMaterialBuildingCutout: case MeshLayer.NoMaterialBuilding: case MeshLayer.NoMaterialBuildingTransparent: case MeshLayer.NoMaterialTransparent: break; case MeshLayer.BuildingMaterial: case MeshLayer.BuildingMaterialCutout: case MeshLayer.BuildingMaterialTransparent: mat = tile.buildingMaterial; break; default: break; } MaterialDefinition mattie; if (materials.TryGetValue(mat, out mattie)) { ColorDefinition color = mattie.state_color; if (color == null) newColor = Color.cyan; else newColor = new Color(color.red / 255.0f, color.green / 255.0f, color.blue / 255.0f, 1); } else { newColor = Color.grey; } } buffer.color = newColor; buffer.uv1Transform = matTexTransform; buffer.uv2Transform = shapeTextTransform; buffer.uv3Transform = specialTexTransform; buffer.hiddenFaces = CalculateHiddenFaces(tile); }
/// <summary> /// This is the function that actually decides what mesh and texture each tile gets /// </summary> /// <param name="buffer">Buffer to put the chosen meshes into for combining</param> /// <param name="layer">layer currently being worked on</param> /// <param name="tile">The tile to get all the needed info from.</param> void FillMeshBuffer(out MeshCombineUtility.MeshInstance buffer, MeshLayer layer, MapDataStore.Tile tile, Vector3 pos) { buffer = new MeshCombineUtility.MeshInstance(); Vector2 index1 = Vector2.zero; Vector2 index2 = Vector2.zero; MeshContent meshContent = null; buffer.color = Color.grey; if (layer == MeshLayer.Collision) { if (!ContentLoader.Instance.CollisionMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } if (meshContent.MeshData.ContainsKey(MeshLayer.Collision)) buffer.meshData = meshContent.MeshData[MeshLayer.Collision]; else if (meshContent.MeshData.ContainsKey(MeshLayer.StaticMaterial)) buffer.meshData = meshContent.MeshData[MeshLayer.StaticMaterial]; else { buffer.meshData = null; return; } buffer.transform = Matrix4x4.TRS(pos, meshContent.GetRotation(tile), Vector3.one); buffer.hiddenFaces = CalculateHiddenFaces(tile, meshContent.Rotation); return; } if (layer == MeshLayer.BuildingCollision) { if (tile.buildingType == default(BuildingStruct) || !ContentLoader.Instance.BuildingCollisionMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } if (meshContent.MeshData.ContainsKey(MeshLayer.Collision)) buffer.meshData = meshContent.MeshData[MeshLayer.Collision]; else if (meshContent.MeshData.ContainsKey(MeshLayer.BuildingMaterial)) buffer.meshData = meshContent.MeshData[MeshLayer.BuildingMaterial]; else if (meshContent.MeshData.ContainsKey(MeshLayer.BuildingMaterialCutout)) buffer.meshData = meshContent.MeshData[MeshLayer.BuildingMaterialCutout]; else if (meshContent.MeshData.ContainsKey(MeshLayer.BuildingMaterialTransparent)) buffer.meshData = meshContent.MeshData[MeshLayer.BuildingMaterialTransparent]; else { buffer.meshData = null; return; } buffer.transform = Matrix4x4.TRS(pos, meshContent.GetRotation(tile), Vector3.one); buffer.hiddenFaces = CalculateHiddenFaces(tile, meshContent.Rotation); return; } if (ContentLoader.Instance.DesignationMeshConfiguration.GetValue(tile, layer, out meshContent)) { if (!meshContent.MeshData.ContainsKey(layer)) { buffer.meshData = null; return; } buffer.meshData = meshContent.MeshData[layer]; buffer.transform = Matrix4x4.TRS(pos, meshContent.GetRotation(tile), Vector3.one); if (TextureStorage.UsingArray) { if (meshContent.MaterialTexture != null) index1.x = meshContent.MaterialTexture.ArrayIndex; else index1.x = ContentLoader.Instance.DefaultMatTexArrayIndex; if (meshContent.ShapeTexture != null) index1.y = meshContent.ShapeTexture.ArrayIndex; else index1.y = ContentLoader.Instance.DefaultShapeTexArrayIndex; if (meshContent.SpecialTexture != null) index2.x = meshContent.SpecialTexture.ArrayIndex; else index2.x = ContentLoader.Instance.DefaultSpecialTexArrayIndex; buffer.uv1Transform = Matrix4x4.identity; buffer.uv2Force = index1; buffer.uv3Force = index2; } else { if (meshContent.MaterialTexture != null) buffer.uv1Transform = meshContent.MaterialTexture.UVTransform; else buffer.uv1Transform = ContentLoader.Instance.DefaultMatTexTransform; if (meshContent.ShapeTexture != null) buffer.uv2Transform = meshContent.ShapeTexture.UVTransform; else buffer.uv2Transform = ContentLoader.Instance.DefaultShapeTexTransform; if (meshContent.SpecialTexture != null) buffer.uv3Transform = meshContent.SpecialTexture.UVTransform; else buffer.uv3Transform = ContentLoader.Instance.DefaultSpecialTexTransform; } buffer.hiddenFaces = CalculateHiddenFaces(tile, meshContent.Rotation); return; } switch (layer) { case MeshLayer.GrowthMaterial: case MeshLayer.GrowthMaterial1: case MeshLayer.GrowthMaterial2: case MeshLayer.GrowthMaterial3: case MeshLayer.GrowthCutout: case MeshLayer.GrowthCutout1: case MeshLayer.GrowthCutout2: case MeshLayer.GrowthCutout3: case MeshLayer.GrowthTransparent: case MeshLayer.GrowthTransparent1: case MeshLayer.GrowthTransparent2: case MeshLayer.GrowthTransparent3: { switch (tile.tiletypeMaterial) { case TiletypeMaterial.PLANT: case TiletypeMaterial.ROOT: case TiletypeMaterial.TREE_MATERIAL: case TiletypeMaterial.MUSHROOM: if (!ContentLoader.Instance.GrowthMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } break; default: buffer.meshData = null; return; } } break; case MeshLayer.BuildingMaterial: case MeshLayer.NoMaterialBuilding: case MeshLayer.BuildingMaterialCutout: case MeshLayer.NoMaterialBuildingCutout: case MeshLayer.BuildingMaterialTransparent: case MeshLayer.NoMaterialBuildingTransparent: { if (tile.buildingType == default(BuildingStruct)) { buffer.meshData = null; return; } if (!ContentLoader.Instance.BuildingMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } } break; default: { if (layer == MeshLayer.NaturalTerrain) { if (VoxelGenerator.IsNatural(tile) && !VoxelGenerator.HandleShape(tile) && !VoxelGenerator.UseBoth(tile)) layer = MeshLayer.StaticMaterial; else { buffer.meshData = null; return; } } else if (VoxelGenerator.IsNatural(tile) && !VoxelGenerator.UseBoth(tile)) { buffer.meshData = null; return; } if (!ContentLoader.Instance.TileMeshConfiguration.GetValue(tile, layer, out meshContent)) { buffer.meshData = null; return; } } break; } if (!meshContent.MeshData.ContainsKey(layer)) { buffer.meshData = null; return; } buffer.meshData = meshContent.MeshData[layer]; buffer.transform = Matrix4x4.TRS(pos, meshContent.GetRotation(tile), Vector3.one); Matrix4x4 matTexTransform = ContentLoader.Instance.DefaultMatTexTransform; Matrix4x4 shapeTextTransform = ContentLoader.Instance.DefaultShapeTexTransform; Matrix4x4 specialTexTransform = Matrix4x4.identity; NormalContent tileTexContent; if (meshContent.ShapeTexture == null) { if (layer == MeshLayer.BuildingMaterial || layer == MeshLayer.BuildingMaterialCutout || layer == MeshLayer.NoMaterialBuilding || layer == MeshLayer.NoMaterialBuildingCutout || layer == MeshLayer.BuildingMaterialTransparent || layer == MeshLayer.NoMaterialBuildingTransparent ) { if (ContentLoader.Instance.BuildingShapeTextureConfiguration.GetValue(tile, layer, out tileTexContent)) { shapeTextTransform = tileTexContent.UVTransform; index1.y = tileTexContent.ArrayIndex; } } else { if (ContentLoader.Instance.ShapeTextureConfiguration.GetValue(tile, layer, out tileTexContent)) { shapeTextTransform = tileTexContent.UVTransform; index1.y = tileTexContent.ArrayIndex; } } } else { shapeTextTransform = meshContent.ShapeTexture.UVTransform; index1.y = meshContent.ShapeTexture.ArrayIndex; } if (meshContent.MaterialTexture != null && (layer == MeshLayer.NoMaterial || layer == MeshLayer.NoMaterialBuilding || layer == MeshLayer.NoMaterialBuildingCutout || layer == MeshLayer.NoMaterialBuildingTransparent || layer == MeshLayer.NoMaterialCutout || layer == MeshLayer.NoMaterialTransparent)) { matTexTransform = meshContent.MaterialTexture.UVTransform; index1.x = meshContent.MaterialTexture.ArrayIndex; } else { TextureContent matTexContent; if (ContentLoader.Instance.MaterialTextureConfiguration.GetValue(tile, layer, out matTexContent)) { matTexTransform = matTexContent.UVTransform; index1.x = matTexContent.ArrayIndex; } } if (meshContent.SpecialTexture != null) { specialTexTransform = meshContent.SpecialTexture.UVTransform; index2.x = meshContent.SpecialTexture.ArrayIndex; } else { specialTexTransform = ContentLoader.Instance.DefaultSpecialTexTransform; index2.x = ContentLoader.Instance.DefaultSpecialTexArrayIndex; } ColorContent newColorContent; Color newColor; if (ContentLoader.Instance.ColorConfiguration.GetValue(tile, layer, out newColorContent)) { newColor = newColorContent.color; } else { MatPairStruct mat = new MatPairStruct(-1, -1); switch (layer) { case MeshLayer.StaticMaterial: case MeshLayer.StaticCutout: case MeshLayer.StaticTransparent: mat = tile.material; break; case MeshLayer.BaseMaterial: case MeshLayer.BaseCutout: case MeshLayer.BaseTransparent: mat = tile.base_material; break; case MeshLayer.LayerMaterial: case MeshLayer.LayerCutout: case MeshLayer.LayerTransparent: mat = tile.layer_material; break; case MeshLayer.VeinMaterial: case MeshLayer.VeinCutout: case MeshLayer.VeinTransparent: mat = tile.vein_material; break; case MeshLayer.NoMaterial: case MeshLayer.NoMaterialCutout: case MeshLayer.NoMaterialBuildingCutout: case MeshLayer.NoMaterialBuilding: case MeshLayer.NoMaterialBuildingTransparent: case MeshLayer.NoMaterialTransparent: break; case MeshLayer.BuildingMaterial: case MeshLayer.BuildingMaterialCutout: case MeshLayer.BuildingMaterialTransparent: mat = tile.buildingMaterial; break; default: break; } MaterialDefinition mattie; if (materials.TryGetValue(mat, out mattie)) { ColorDefinition color = mattie.state_color; if (color == null) newColor = Color.cyan; else newColor = new Color(color.red / 255.0f, color.green / 255.0f, color.blue / 255.0f, 1); } else { newColor = Color.grey; } } buffer.color = newColor; if (TextureStorage.UsingArray) { buffer.uv1Transform = Matrix4x4.identity; buffer.uv2Force = index1; buffer.uv3Force = index2; } else { buffer.uv1Transform = matTexTransform; buffer.uv2Transform = shapeTextTransform; buffer.uv3Transform = specialTexTransform; } buffer.hiddenFaces = CalculateHiddenFaces(tile, meshContent.Rotation); }
/// <summary> /// Combine the given mesh instances into a single mesh and return it. /// </summary> /// <param name="instances">The mesh instances to combine.</param> /// <param name="generateStrips">true to use triangle strips, false to use triangle lists.</param> /// <returns>A combined mesh.</returns> public static Mesh Combine(IEnumerable<MeshInstance> instances, bool generateStrips) { var processor = new MeshCombineUtility(generateStrips); processor.AddMeshInstances(instances); return processor.CreateCombinedMesh(); }
bool GenerateTiles(MapDataStore data, out MeshData tiles, out MeshData stencilTiles, TempBuffers temp) { int block_x = data.SliceOrigin.x / GameMap.blockSize; int block_y = data.SliceOrigin.y / GameMap.blockSize; int block_z = data.SliceOrigin.z; int bufferIndex = 0; int stencilBufferIndex = 0; for (int xx = (block_x * GameMap.blockSize); xx < (block_x + 1) * GameMap.blockSize; xx++) { for (int yy = (block_y * GameMap.blockSize); yy < (block_y + 1) * GameMap.blockSize; yy++) { if (!data.InSliceBounds(new DFCoord(xx, yy, block_z))) { throw new UnityException("OOB"); } if (data[xx, yy, block_z] == null) { continue; } for (int i = 0; i < (int)MeshLayer.Count; i++) { MeshLayer layer = (MeshLayer)i; switch (layer) { case MeshLayer.StaticMaterial: case MeshLayer.BaseMaterial: case MeshLayer.LayerMaterial: case MeshLayer.VeinMaterial: case MeshLayer.NoMaterial: FillMeshBuffer(out temp.meshBuffer[bufferIndex], layer, data[xx, yy, block_z].Value); bufferIndex++; break; case MeshLayer.StaticCutout: case MeshLayer.BaseCutout: case MeshLayer.LayerCutout: case MeshLayer.VeinCutout: case MeshLayer.Growth0Cutout: case MeshLayer.Growth1Cutout: case MeshLayer.Growth2Cutout: case MeshLayer.Growth3Cutout: case MeshLayer.NoMaterialCutout: FillMeshBuffer(out temp.stencilMeshBuffer[stencilBufferIndex], layer, data[xx, yy, block_z].Value); stencilBufferIndex++; break; default: break; } } } } bool dontCare, success; stencilTiles = MeshCombineUtility.ColorCombine(temp.stencilMeshBuffer, out dontCare); tiles = MeshCombineUtility.ColorCombine(temp.meshBuffer, out success); return(success); }
public static Mesh Combine(MeshCombineUtility.MeshInstance[] combines, bool generateStrips) { int num = 0; int length = 0; int num1 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray = combines; for (int i = 0; i < (int)meshInstanceArray.Length; i++) { MeshCombineUtility.MeshInstance meshInstance = meshInstanceArray[i]; if (meshInstance.mesh) { num = num + meshInstance.mesh.vertexCount; if (generateStrips) { int length1 = (int)meshInstance.mesh.GetTriangleStrip(meshInstance.subMeshIndex).Length; if (length1 == 0) { generateStrips = false; } else { if (num1 != 0) { num1 = ((num1 & 1) != 1 ? num1 + 2 : num1 + 3); } num1 = num1 + length1; } } } } if (!generateStrips) { MeshCombineUtility.MeshInstance[] meshInstanceArray1 = combines; for (int j = 0; j < (int)meshInstanceArray1.Length; j++) { MeshCombineUtility.MeshInstance meshInstance1 = meshInstanceArray1[j]; if (meshInstance1.mesh) { length = length + (int)meshInstance1.mesh.GetTriangles(meshInstance1.subMeshIndex).Length; } } } Vector3[] vector3Array = new Vector3[num]; Vector3[] vector3Array1 = new Vector3[num]; Vector4[] vector4Array = new Vector4[num]; Vector2[] vector2Array = new Vector2[num]; Vector2[] vector2Array1 = new Vector2[num]; Color[] colorArray = new Color[num]; int[] numArray = new int[length]; int[] numArray1 = new int[num1]; int num2 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray2 = combines; for (int k = 0; k < (int)meshInstanceArray2.Length; k++) { MeshCombineUtility.MeshInstance meshInstance2 = meshInstanceArray2[k]; if (meshInstance2.mesh) { MeshCombineUtility.Copy(meshInstance2.mesh.vertexCount, meshInstance2.mesh.vertices, vector3Array, ref num2, meshInstance2.transform); } } num2 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray3 = combines; for (int l = 0; l < (int)meshInstanceArray3.Length; l++) { MeshCombineUtility.MeshInstance meshInstance3 = meshInstanceArray3[l]; if (meshInstance3.mesh) { Matrix4x4 matrix4x4 = meshInstance3.transform.inverse.transpose; MeshCombineUtility.CopyNormal(meshInstance3.mesh.vertexCount, meshInstance3.mesh.normals, vector3Array1, ref num2, matrix4x4); } } num2 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray4 = combines; for (int m = 0; m < (int)meshInstanceArray4.Length; m++) { MeshCombineUtility.MeshInstance meshInstance4 = meshInstanceArray4[m]; if (meshInstance4.mesh) { Matrix4x4 matrix4x41 = meshInstance4.transform.inverse.transpose; MeshCombineUtility.CopyTangents(meshInstance4.mesh.vertexCount, meshInstance4.mesh.tangents, vector4Array, ref num2, matrix4x41); } } num2 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray5 = combines; for (int n = 0; n < (int)meshInstanceArray5.Length; n++) { MeshCombineUtility.MeshInstance meshInstance5 = meshInstanceArray5[n]; if (meshInstance5.mesh) { MeshCombineUtility.Copy(meshInstance5.mesh.vertexCount, meshInstance5.mesh.uv, vector2Array, ref num2); } } num2 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray6 = combines; for (int o = 0; o < (int)meshInstanceArray6.Length; o++) { MeshCombineUtility.MeshInstance meshInstance6 = meshInstanceArray6[o]; if (meshInstance6.mesh) { MeshCombineUtility.Copy(meshInstance6.mesh.vertexCount, meshInstance6.mesh.uv1, vector2Array1, ref num2); } } num2 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray7 = combines; for (int p = 0; p < (int)meshInstanceArray7.Length; p++) { MeshCombineUtility.MeshInstance meshInstance7 = meshInstanceArray7[p]; if (meshInstance7.mesh) { MeshCombineUtility.CopyColors(meshInstance7.mesh.vertexCount, meshInstance7.mesh.colors, colorArray, ref num2); } } int length2 = 0; int length3 = 0; int num3 = 0; MeshCombineUtility.MeshInstance[] meshInstanceArray8 = combines; for (int q = 0; q < (int)meshInstanceArray8.Length; q++) { MeshCombineUtility.MeshInstance meshInstance8 = meshInstanceArray8[q]; if (meshInstance8.mesh) { if (!generateStrips) { int[] triangles = meshInstance8.mesh.GetTriangles(meshInstance8.subMeshIndex); for (int r = 0; r < (int)triangles.Length; r++) { numArray[r + length2] = triangles[r] + num3; } length2 = length2 + (int)triangles.Length; } else { int[] triangleStrip = meshInstance8.mesh.GetTriangleStrip(meshInstance8.subMeshIndex); if (length3 != 0) { if ((length3 & 1) != 1) { numArray1[length3] = numArray1[length3 - 1]; numArray1[length3 + 1] = triangleStrip[0] + num3; length3 = length3 + 2; } else { numArray1[length3] = numArray1[length3 - 1]; numArray1[length3 + 1] = triangleStrip[0] + num3; numArray1[length3 + 2] = triangleStrip[0] + num3; length3 = length3 + 3; } } for (int s = 0; s < (int)triangleStrip.Length; s++) { numArray1[s + length3] = triangleStrip[s] + num3; } length3 = length3 + (int)triangleStrip.Length; } num3 = num3 + meshInstance8.mesh.vertexCount; } } Mesh mesh = new Mesh() { name = "Combined Mesh", vertices = vector3Array, normals = vector3Array1, colors = colorArray, uv = vector2Array, uv1 = vector2Array1, tangents = vector4Array }; if (!generateStrips) { mesh.triangles = numArray; } else { mesh.SetTriangleStrip(numArray1, 0); } return mesh; }
//Method responsible for constructing the Decal Mesh, based on the affected objects. public void CalculateDecal() { ClearDecals(); maxAngle = Mathf.Clamp(maxAngle, 0.0f, 180.0f); angleCosine = Mathf.Cos(maxAngle * Mathf.Deg2Rad); uvAngle = Mathf.Clamp(uvAngle, 0.0f, 360.0f); uCos = Mathf.Cos(uvAngle * Mathf.Deg2Rad); vSin = Mathf.Sin(uvAngle * Mathf.Deg2Rad); if (affectedObjects == null) { //Debug.LogWarning("No object will be affected. Decal will not be calculated."); return; } else if (affectedObjects.Length <= 0) { //Debug.LogWarning("No object will be affected. Decal will not be calculated."); return; } //Current transform matrix Matrix4x4 myTransform = transform.worldToLocalMatrix; instancesList = new List <MeshCombineUtility.MeshInstance>(); for (int i = 0; i < affectedObjects.Length; i++) { if (affectedObjects[i] == null) { continue; } CalculateObjectDecal(affectedObjects[i], myTransform); } if (instancesList.Count > 0) { MeshCombineUtility.MeshInstance[] instances = new MeshCombineUtility.MeshInstance[instancesList.Count]; for (int i = 0; i < instances.Length; i++) { instances[i] = instancesList[i]; } MeshRenderer r = gameObject.GetComponent <MeshRenderer>(); if (r == null) { r = gameObject.AddComponent <MeshRenderer>(); } r.material = decalMaterial; MeshFilter fi = gameObject.GetComponent <MeshFilter>(); if (fi == null) { fi = gameObject.AddComponent <MeshFilter>(); } else { DestroyImmediate(fi.sharedMesh); } Mesh finalMesh = MeshCombineUtility.Combine(instances, true); if (pushDistance > 0.0f) { List <List <int> > relations = new List <List <int> >(); Vector3[] vert = finalMesh.vertices; Vector3[] normals = finalMesh.normals; bool[] usedIndex = new bool[vert.Length]; for (int i = 0; i < usedIndex.Length; i++) { usedIndex[i] = false; } for (int i = 0; i < vert.Length; i++) { if (usedIndex[i]) { continue; } List <int> c = new List <int>(); c.Add(i); usedIndex[i] = true; for (int j = i + 1; j < vert.Length; j++) { if (usedIndex[j]) { continue; } if (Vector3.Distance(vert[i], vert[j]) < 0.001f) { c.Add(j); usedIndex[j] = true; } } relations.Add(c); } foreach (List <int> l in relations) { Vector3 nNormal = Vector3.zero; foreach (int i in l) { nNormal += normals[i]; } nNormal = (nNormal / l.Count).normalized; foreach (int i in l) { vert[i] += nNormal * (pushDistance); } } finalMesh.vertices = vert; } finalMesh.name = "DecalMesh"; fi.mesh = finalMesh; for (int i = 0; i < instancesList.Count; i++) { DestroyImmediate(instancesList[i].mesh); } } instancesList.Clear(); instancesList = null; }
void ReCombineSkinnedMeshes() { VERTEX_NUMBER = 0; BONE_NUMBER = 0; Component[] allsmr = GetComponentsInChildren(typeof(SkinnedMeshRenderer)); for (int i = 0; i < allsmr.Length; ++i) { if (allsmr[i].name == name || ((SkinnedMeshRenderer)allsmr[i]).sharedMesh == null) { continue; } VERTEX_NUMBER += ((SkinnedMeshRenderer)allsmr[i]).sharedMesh.vertices.Length; BONE_NUMBER += ((SkinnedMeshRenderer)allsmr[i]).bones.Length; } Matrix4x4 myTransform = transform.worldToLocalMatrix; Hashtable materialToMesh = new Hashtable(); Hashtable boneHash = new Hashtable(); Transform[] totalBones = new Transform[BONE_NUMBER]; Matrix4x4[] totalBindPoses = new Matrix4x4[BONE_NUMBER]; BoneWeight[] totalBoneWeight = new BoneWeight[VERTEX_NUMBER]; int offset = 0; int b_offset = 0; Transform[] usedBones = new Transform[totalBones.Length]; for (int i = 0; i < allsmr.Length; i++) { if (allsmr[i].name == name || ((SkinnedMeshRenderer)allsmr[i]).sharedMesh == null) { continue; } SkinnedMeshRenderer smrenderer = (SkinnedMeshRenderer)allsmr[i]; MeshCombineUtility.MeshInstance instance = new MeshCombineUtility.MeshInstance(); instance.mesh = smrenderer.sharedMesh; if (smrenderer != null && smrenderer.enabled && instance.mesh != null) { instance.transform = myTransform * smrenderer.transform.localToWorldMatrix; Material[] materials = smrenderer.sharedMaterials; for (int m = 0; m < materials.Length; m++) { instance.subMeshIndex = System.Math.Min(m, instance.mesh.subMeshCount - 1); ArrayList objects = (ArrayList)materialToMesh[materials[m]]; if (objects != null) { objects.Add(instance); } else { objects = new ArrayList(); objects.Add(instance); materialToMesh.Add(materials[m], objects); } } for (int x = 0; x < smrenderer.bones.Length; x++) { bool flag = false; for (int j = 0; j < totalBones.Length; j++) { if (usedBones[j] != null) { if ((smrenderer.bones[x] == usedBones[j])) { flag = true; break; } } } if (!flag) { for (int f = 0; f < totalBones.Length; f++) { if (usedBones[f] == null) { usedBones[f] = smrenderer.bones[x]; break; } } totalBones[offset] = smrenderer.bones[x]; boneHash.Add(smrenderer.bones[x].name, offset); totalBindPoses[offset] = smrenderer.bones[x].worldToLocalMatrix * transform.localToWorldMatrix; offset++; } } for (int x = 0; x < smrenderer.sharedMesh.boneWeights.Length; x++) { totalBoneWeight[b_offset] = recalculateIndexes(smrenderer.sharedMesh.boneWeights[x], boneHash, smrenderer.bones); b_offset++; } ((SkinnedMeshRenderer)allsmr[i]).enabled = false; } } foreach (DictionaryEntry de in materialToMesh) { ArrayList elements = (ArrayList)de.Value; MeshCombineUtility.MeshInstance[] instances = (MeshCombineUtility.MeshInstance[])elements.ToArray(typeof(MeshCombineUtility.MeshInstance)); //int i = 0; //foreach (var item in instances) //{ // Debug.Log(item.mesh.name + " !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"); // Mesh mesh = Resources.Load(item.mesh.name) as Mesh; // instances[i++].mesh = mesh; //} if (materialToMesh.Count == 1) { if (GetComponent(typeof(SkinnedMeshRenderer)) == null) { gameObject.AddComponent <SkinnedMeshRenderer>(); } SkinnedMeshRenderer objRenderer = (SkinnedMeshRenderer)GetComponent(typeof(SkinnedMeshRenderer)); objRenderer.sharedMesh = MeshCombineUtility.Combine(instances, generateTriangleStrips); objRenderer.material = (Material)de.Key; objRenderer.castShadows = castShadows; objRenderer.receiveShadows = receiveShadows; objRenderer.sharedMesh.bindposes = totalBindPoses; objRenderer.sharedMesh.boneWeights = totalBoneWeight; objRenderer.bones = totalBones; objRenderer.sharedMesh.RecalculateNormals(); objRenderer.sharedMesh.RecalculateBounds(); objRenderer.enabled = true; } else { Debug.Log("More Than One Material !!!!!! " + materialToMesh.Count); //GameObject go = new GameObject("CombinedSkinnedMesh"); //go.transform.parent = transform; //go.transform.localScale = Vector3.one; //go.transform.localRotation = Quaternion.identity; //go.transform.localPosition = Vector3.zero; //go.AddComponent(typeof(SkinnedMeshRenderer)); //((SkinnedMeshRenderer)go.GetComponent(typeof(SkinnedMeshRenderer))).material = (Material)de.Key; //SkinnedMeshRenderer objRenderer = (SkinnedMeshRenderer)go.GetComponent(typeof(SkinnedMeshRenderer)); //objRenderer.sharedMesh = MeshCombineUtility.Combine(instances, generateTriangleStrips); //objRenderer.sharedMesh.bindposes = totalBindPoses; //objRenderer.sharedMesh.boneWeights = totalBoneWeight; //objRenderer.bones = totalBones; //objRenderer.sharedMesh.RecalculateNormals(); //objRenderer.sharedMesh.RecalculateBounds(); //objRenderer.enabled = true; } } }
public IEnumerator _Batch(bool AddMeshColliders = false, bool RemoveLeftOvers = false, bool isItPatternExport = false, bool isPrepareForLightmapping = false) { for (int i = 0; i < BatchedObjects.Count; i++) { Destroy(BatchedObjects[i]); } BatchedObjects.Clear(); Component[] filters = GetComponentsInChildren(typeof(MeshFilter)); Matrix4x4 myTransform = transform.worldToLocalMatrix; List <Hashtable> materialToMesh = new List <Hashtable>(); int vertexCalc = 0; int hasIterations = 0; materialToMesh.Add(new Hashtable()); for (int i = 0; i < filters.Length; i++) { MeshFilter filter = (MeshFilter)filters[i]; Renderer curRenderer = filters[i].GetComponent <Renderer>(); MeshCombineUtility.MeshInstance instance = new MeshCombineUtility.MeshInstance(); instance.mesh = filter.sharedMesh; if (!instance.mesh) { continue; } vertexCalc += instance.mesh.vertexCount; if (curRenderer != null && curRenderer.enabled && instance.mesh != null) { instance.transform = myTransform * filter.transform.localToWorldMatrix; Material[] materials = curRenderer.sharedMaterials; for (int m = 0; m < materials.Length; m++) { instance.subMeshIndex = System.Math.Min(m, instance.mesh.subMeshCount - 1); ArrayList objects = (ArrayList)materialToMesh[hasIterations][materials[m]]; if (objects != null) { objects.Add(instance); } else { objects = new ArrayList(); objects.Add(instance); materialToMesh[hasIterations].Add(materials[m], objects); } if (vertexCalc > optLevel) { vertexCalc = 0; hasIterations++; materialToMesh.Add(new Hashtable()); } } if (!RemoveLeftOvers) { curRenderer.enabled = false; } } } int counter = 0; for (int i = 0; i < hasIterations + 1; i++) { foreach (DictionaryEntry de in materialToMesh[i]) { #if UNITY_EDITOR if (EditorApplication.isPlaying) { #endif yield return(0); #if UNITY_EDITOR } #endif ArrayList elements = (ArrayList)de.Value; MeshCombineUtility.MeshInstance[] instances = (MeshCombineUtility.MeshInstance[])elements.ToArray(typeof(MeshCombineUtility.MeshInstance)); GameObject go = new GameObject("uteTagID_1555"); BatchedObjects.Add(go); go.transform.parent = transform; go.transform.localScale = Vector3.one; go.transform.localRotation = Quaternion.identity; go.transform.localPosition = Vector3.zero; go.AddComponent(typeof(MeshFilter)); go.AddComponent <MeshRenderer>(); go.isStatic = true; go.GetComponent <Renderer>().material = (Material)de.Key; MeshFilter filter = (MeshFilter)go.GetComponent(typeof(MeshFilter)); filter.mesh = MeshCombineUtility.Combine(instances, generateTriangleStrips); if (isPrepareForLightmapping) { #if UNITY_EDITOR #if UNITY_5_0 || UNITY_5_1 || UNITY_5_2 || UNITY_5_3 || UNITY_5_4 || UNITY_5_5 Unwrapping.GeneratePerTriangleUV(filter.mesh); #endif Unwrapping.GenerateSecondaryUVSet(filter.mesh); #endif } if (AddMeshColliders) { #if UNITY_EDITOR if (EditorApplication.isPlaying) { #endif yield return(0); #if UNITY_EDITOR } #endif go.AddComponent <MeshCollider>(); } } } if (RemoveLeftOvers) { List <GameObject> children = new List <GameObject>(); int counterpp = 0; foreach (Transform child in transform) { children.Add(child.gameObject); } #if UNITY_EDITOR if (EditorApplication.isPlaying) { #endif for (int s = 0; s < children.Count; s++) { if (children[s].name != "uteTagID_1555") { #if UNITY_EDITOR if (EditorApplication.isPlaying) { if (s % 1000 == 0) { yield return(0); } #endif Destroy(children[s]); #if UNITY_EDITOR } #endif } else { children[s].name = "Batch_" + (counterpp++).ToString(); } } #if UNITY_EDITOR } else { for (int s = 0; s < children.Count; s++) { if (children[s].name != ("uteTagID_1555")) { DestroyImmediate(children[s], true); } else { children[s].name = "Batch_" + (counterpp++).ToString(); } } } #endif } yield return(0); }
public void Combine() { if (combine) { return; } combine = true; filters = GetComponentsInChildren(typeof(MeshFilter)); Matrix4x4 myTransform = transform.worldToLocalMatrix; instance = new MeshCombineUtility.MeshInstance[filters.Length]; for (int i = 0; i < filters.Length; i++) { MeshFilter filter = (MeshFilter)filters[i]; Renderer curRenderer = filters[i].GetComponent <Renderer>(); instance[i] = new MeshCombineUtility.MeshInstance(); instance[i].mesh = filter.sharedMesh; instance[i].childIdx = i; if (curRenderer != null && curRenderer.enabled && instance[i].mesh != null) { instance[i].transform = myTransform * filter.transform.localToWorldMatrix; Material[] materials = curRenderer.sharedMaterials; for (int m = 0; m < materials.Length; m++) { instance[i].subMeshIndex = System.Math.Min(m, instance[i].mesh.subMeshCount - 1); ArrayList objects = (ArrayList)materialToMesh[materials[m]]; if (objects != null) { objects.Add(instance[i]); } else { objects = new ArrayList(); objects.Add(instance[i]); materialToMesh.Add(materials[m], objects); } } curRenderer.enabled = false; } } foreach (DictionaryEntry de in materialToMesh) { ArrayList elements = (ArrayList)de.Value; MeshCombineUtility.MeshInstance[] instances = (MeshCombineUtility.MeshInstance[])elements.ToArray(typeof(MeshCombineUtility.MeshInstance)); // We have a maximum of one material, so just attach the mesh to our own game object if (materialToMesh.Count == 1) { // Make sure we have a mesh filter & renderer if (GetComponent(typeof(MeshFilter)) == null) { gameObject.AddComponent(typeof(MeshFilter)); } if (!GetComponent("MeshRenderer")) { gameObject.AddComponent <MeshRenderer>(); } MeshFilter filter = (MeshFilter)GetComponent(typeof(MeshFilter)); filter.mesh = MeshCombineUtility.CombineFirst(instances, generateTriangleStrips, ref element); GetComponent <Renderer>().material = (Material)de.Key; GetComponent <Renderer>().enabled = true; mf = filter; } // We have multiple materials to take care of, build one mesh / gameobject for each material // and parent it to this object else { GameObject combinedMesh = new GameObject("Combined mesh"); combinedMesh.transform.parent = transform; combinedMesh.transform.localScale = Vector3.one; combinedMesh.transform.localRotation = Quaternion.identity; combinedMesh.transform.localPosition = Vector3.zero; combinedMesh.AddComponent(typeof(MeshFilter)); combinedMesh.AddComponent <MeshRenderer>(); combinedMesh.GetComponent <Renderer>().material = (Material)de.Key; MeshFilter filter = (MeshFilter)combinedMesh.GetComponent(typeof(MeshFilter)); filter.mesh = MeshCombineUtility.Combine(instances, generateTriangleStrips); } } }
public static void Combine(SimpleMeshCombine target) { MeshFilter[] meshFilters = FindEnabledMeshes(target.transform); if (meshFilters.Length > 0) { GameObject combinedFrags = new GameObject(); combinedFrags.AddComponent <MeshFilter>(); combinedFrags.AddComponent <MeshRenderer>(); MeshInstance[] instances = new MeshInstance[meshFilters.Length]; GameObject[] combinedGOs = new GameObject[meshFilters.Length]; MeshFilter matFilter = null; for (int i = 0; i < meshFilters.Length; i++) { MeshFilter mf = meshFilters[i]; if (i == meshFilters.Length - 1) { matFilter = mf; } combinedGOs[i] = mf.gameObject; MeshInstance mi = new MeshInstance(); mi.mesh = mf.sharedMesh; // D.Log(mi.mesh.vertices.Length); // mi.subMeshIndex = mf.sharedMesh.subMeshCount; mi.subMeshIndex = 0; mi.transform = mf.transform.localToWorldMatrix; instances[i] = mi; } target.combinedGameObjects = combinedGOs; Mesh m = MeshCombineUtility.Combine(instances, false); // D.Log(target.transform.name+ // " Combined " + meshFilters.Length + " Meshes"); // D.Warn("Mesh: " + m.vertices.Length); // CombineInstance[] combine = new CombineInstance[meshFilters.Length]; // GameObject[] mfGOs = new GameObject[meshFilters.Length]; // for (int i=0; i<meshFilters.Length; i++) { // MeshFilter mf = meshFilters[i]; // MeshRenderer mr = combinedFrags.GetComponent<MeshRenderer>(); // mr.sharedMaterial = mf.transform.GetComponent<MeshRenderer>().sharedMaterial; // mfGOs[i] = meshFilters[i].gameObject; // CombineInstance ci = combine[i]; // ci.mesh = mf.transform.GetComponent<MeshFilter>().sharedMesh; // ci.transform = mf.transform.localToWorldMatrix; // combine[i] = ci; // } combinedFrags.GetComponent <MeshFilter>().mesh = m; combinedFrags.GetComponent <MeshRenderer>().sharedMaterial = matFilter.GetComponent <Renderer>().sharedMaterial; // combinedFrags.GetComponent<MeshFilter>().mesh = new Mesh(); // combinedFrags.GetComponent<MeshFilter>().sharedMesh.CombineMeshes(combine); // // Disabled for now // // if (target._generateLightmapUV){ // // Unwrapping.GenerateSecondaryUVSet(combinedFrags.GetComponent(MeshFilter).sharedMesh); // // combinedFrags.isStatic = true; // // } combinedFrags.name = "_Combined Mesh [" + target.transform.name + "]"; target.combined = combinedFrags.gameObject; combinedFrags.transform.parent = target.transform; EnableRenderers(meshFilters, false); } }
bool GenerateTiles(MapDataStore data, out CPUMesh tiles, out CPUMesh stencilTiles, out CPUMesh transparentTiles, out CPUMesh topTiles, out CPUMesh topStencilTiles, out CPUMesh topTransparentTiles, out CPUMesh collisionTiles, out CPUMesh terrainTiles, out CPUMesh topTerrainTiles) { int block_x = data.SliceOrigin.x / GameMap.blockSize; int block_y = data.SliceOrigin.y / GameMap.blockSize; int block_z = data.SliceOrigin.z; int bufferIndex = 0; int stencilBufferIndex = 0; int transparentBufferIndex = 0; int collisionIndex = 0; int terrainIndex = 0; for (int xx = (block_x * GameMap.blockSize); xx < (block_x + 1) * GameMap.blockSize; xx++) { for (int yy = (block_y * GameMap.blockSize); yy < (block_y + 1) * GameMap.blockSize; yy++) { if (!data.InSliceBounds(new DFCoord(xx, yy, block_z))) { throw new UnityException("OOB"); } if (data[xx, yy, block_z] == null) { continue; } for (int i = 0; i < (int)MeshLayer.Count; i++) { if (i < (int)MeshLayer.StaticCutout) { FillMeshBuffer( out meshBuffer[bufferIndex], (MeshLayer)i, data[xx, yy, block_z], GameMap.DFtoUnityCoord(xx - (block_x * GameMap.blockSize), yy - (block_y * GameMap.blockSize), -GameMap.MapZOffset)); bufferIndex++; } else if (i < (int)MeshLayer.StaticTransparent) { FillMeshBuffer( out stencilMeshBuffer[stencilBufferIndex], (MeshLayer)i, data[xx, yy, block_z], GameMap.DFtoUnityCoord(xx - (block_x * GameMap.blockSize), yy - (block_y * GameMap.blockSize), -GameMap.MapZOffset)); stencilBufferIndex++; } else if (i < (int)MeshLayer.Collision) { FillMeshBuffer( out transparentMeshBuffer[transparentBufferIndex], (MeshLayer)i, data[xx, yy, block_z], GameMap.DFtoUnityCoord(xx - (block_x * GameMap.blockSize), yy - (block_y * GameMap.blockSize), -GameMap.MapZOffset)); transparentBufferIndex++; } else if (i < (int)MeshLayer.NaturalTerrain) { FillMeshBuffer( out collisionMeshBuffer[collisionIndex], (MeshLayer)i, data[xx, yy, block_z], GameMap.DFtoUnityCoord(xx - (block_x * GameMap.blockSize), yy - (block_y * GameMap.blockSize), -GameMap.MapZOffset)); collisionIndex++; } else if (i == (int)MeshLayer.NaturalTerrain) { FillMeshBuffer(out terrainMeshBuffer[terrainIndex], (MeshLayer)i, data[xx, yy, block_z], GameMap.DFtoUnityCoord(xx - (block_x * GameMap.blockSize), yy - (block_y * GameMap.blockSize), -GameMap.MapZOffset)); terrainIndex++; } } } } bool dontCare, success; VoxelGenerator voxelGen = new VoxelGenerator(); if (block_z == 0) { voxelGen.bottomless = true; } var naturalTerrain = voxelGen.Triangulate(data); terrainTiles = MeshCombineUtility.ColorCombine(terrainMeshBuffer, out dontCare, false, naturalTerrain); topTerrainTiles = MeshCombineUtility.ColorCombine(terrainMeshBuffer, out dontCare, true); stencilTiles = MeshCombineUtility.ColorCombine(stencilMeshBuffer, out dontCare, false); topStencilTiles = MeshCombineUtility.ColorCombine(stencilMeshBuffer, out dontCare, true); transparentTiles = MeshCombineUtility.ColorCombine(transparentMeshBuffer, out dontCare, false); topTransparentTiles = MeshCombineUtility.ColorCombine(transparentMeshBuffer, out dontCare, true); topTiles = MeshCombineUtility.ColorCombine(meshBuffer, out dontCare, true); tiles = MeshCombineUtility.ColorCombine(meshBuffer, out success, false); collisionTiles = MeshCombineUtility.ColorCombine(collisionMeshBuffer, out dontCare, false, naturalTerrain); return(success); }
public void CombineChildren() { var target = Selection.activeGameObject; var filters = target.GetComponentsInChildren <MeshFilter>(); var myTransform = target.transform.worldToLocalMatrix; var materialToMesh = new Dictionary <Material, List <MeshCombineUtility.MeshInstance> >(); for (int i = 0; i < filters.Length; ++i) { var filter = filters[i]; if (filter.gameObject.name.Contains("Collider")) { continue; } var curRenderer = filters[i].renderer; var instance = new MeshCombineUtility.MeshInstance(); instance.mesh = filter.sharedMesh; if (curRenderer != null && instance.mesh != null) { instance.transform = myTransform * filter.transform.localToWorldMatrix; var materials = curRenderer.sharedMaterials; for (int m = 0; m < materials.Length; ++m) { instance.subMeshIndex = System.Math.Min(m, instance.mesh.subMeshCount - 1); List <MeshCombineUtility.MeshInstance> objects = null; var gotList = materialToMesh.TryGetValue(materials[m], out objects); if (gotList) { objects.Add(instance); } else { objects = new List <MeshCombineUtility.MeshInstance>(); objects.Add(instance); materialToMesh.Add(materials[m], objects); } } // curRenderer.enabled = true; } } var meshCount = 0; var combinedChildren = new List <GameObject>(); foreach (var keyValuePair in materialToMesh) { var elements = keyValuePair.Value; var instances = elements.ToArray(); Mesh mesh = null; var gameObject = new GameObject("Combined mesh"); gameObject.transform.parent = target.transform; gameObject.transform.localScale = Vector3.one; gameObject.transform.localRotation = Quaternion.identity; gameObject.transform.localPosition = Vector3.zero; gameObject.AddComponent <MeshFilter>(); gameObject.AddComponent <MeshRenderer>(); gameObject.renderer.material = keyValuePair.Key; var filter = gameObject.GetComponent <MeshFilter>(); mesh = MeshCombineUtility.Combine(instances, generateTriangleStrips); filter.mesh = mesh; combinedChildren.Add(gameObject); ++meshCount; AddMeshToAssets(target, mesh, meshCount); } var clone = GameObject.Instantiate(target) as GameObject; clone.name = target.name; combinedChildren.Each(c => DestroyImmediate(c)); clone.GetComponentsInChildren <MeshRenderer>().Where(r => r != null && r.gameObject.name != "Combined mesh" && !r.gameObject.name.Contains("Collider") && !r.gameObject.name.Contains("Collision") && !r.gameObject.name.Contains("Indoors")) .Each(renderer => DestroyImmediate(renderer.gameObject)); var destroyedCompletely = false; do { destroyedCompletely = !DestroyEmptyGameObjectsIn(clone); } while (!destroyedCompletely); var assetName = string.Format("Assets/Prefabs/Combined Prefabs/{0}.prefab", clone.name); // can't catch the folder error, so just create the folder first manually var prefab = EditorUtility.CreateEmptyPrefab(assetName); EditorUtility.ReplacePrefab(clone, prefab); AssetDatabase.Refresh(); DestroyImmediate(clone); // the clone must be manually destroyed because it can never be empty }