public void OnAfterDeserialize() { #region repair if (weightKeys.Count < weightValues.Count) { weightValues.RemoveRange(weightKeys.Count, weightValues.Count - weightKeys.Count); } else if (weightKeys.Count > weightValues.Count) { weightKeys.RemoveRange(weightValues.Count, weightKeys.Count - weightValues.Count); } #endregion { IntVector3 max = IntVector3.zero; for (int i = 0; i < weightKeys.Count; i++) { max = IntVector3.Max(max, weightKeys[i]); } indexTable = new DataTable3 <int>(max.x, max.y, max.z); } for (int i = 0; i < weightKeys.Count; i++) { if (indexTable.Contains(weightKeys[i])) { weightKeys.RemoveAt(i); weightValues.RemoveAt(i); i--; continue; } indexTable.Set(weightKeys[i], i); } }
public void OnAfterDeserialize() { IntVector3 max = IntVector3.zero; for (int i = 0; i < disableList.Count; i++) { max = IntVector3.Max(max, disableList[i]); } indexTable = new DataTable3 <VoxelBase.Face>(max.x + 1, max.y + 1, max.z + 1); for (int i = 0; i < disableList.Count; i++) { indexTable.Set(disableList[i], faceList[i]); } }
public void OnAfterDeserialize() { IntVector3 max = IntVector3.zero; for (int i = 0; i < materialList.Count; i++) { max = IntVector3.Max(max, materialList[i]); } indexTable = new DataTable3 <int>(max.x + 1, max.y + 1, max.z + 1); for (int i = 0; i < materialList.Count; i++) { indexTable.Set(materialList[i], i); } }
public void Set(int x, int y, int z, Type param) { Assert.IsTrue(x >= 0 && y >= 0 && z >= 0); #region Alloc reserve = IntVector3.Max(reserve, new IntVector3(x + 1, y + 1, z + 1)); if (table == null) { table = new Type[reserve.x][][]; } if (x >= table.Length) { var newTmp = new Type[reserve.x][][]; table.CopyTo(newTmp, 0); table = newTmp; } if (table[x] == null) { table[x] = new Type[reserve.y][]; } if (y >= table[x].Length) { var newTmp = new Type[reserve.y][]; table[x].CopyTo(newTmp, 0); table[x] = newTmp; } if (table[x][y] == null) { table[x][y] = new Type[reserve.z]; } if (z >= table[x][y].Length) { var newTmp = new Type[reserve.z]; table[x][y].CopyTo(newTmp, 0); table[x][y] = newTmp; } #endregion table[x][y][z] = param; enable.Set(x, y, z, true); }
protected override bool CreateMesh() { base.CreateMesh(); #region ProgressBar const float MaxProgressCount = 14f; float ProgressCount = 0; Action <string> DisplayProgressBar = (info) => { if (voxelData.voxels.Length > 10000) { EditorUtility.DisplayProgressBar("Create Mesh...", string.Format("{0} / {1}", ProgressCount, MaxProgressCount), (ProgressCount++ / MaxProgressCount)); } }; #endregion DisplayProgressBar(""); { bool reloadVoxelData = false; foreach (var frame in voxelObject.frames) { if (frame.disableData != null && frame.disableData.Count > 0) { reloadVoxelData = true; break; } if (frame.materialData != null) { foreach (var material in frame.materialData) { if (material != null && material.Count > 0) { reloadVoxelData = true; break; } } if (reloadVoxelData) { break; } } } if (reloadVoxelData) { ReadyIndividualVoxelData(); } }; DisplayProgressBar(""); #region Combine VoxelData { voxelBase.voxelData = new VoxelData(); voxelBase.voxelData.chunkTable = new DataTable3 <IntVector3>(voxelBase.voxelData.voxelSize.x, voxelBase.voxelData.voxelSize.y, voxelBase.voxelData.voxelSize.z); chunkDataList = new List <ChunkData>(voxelObject.frames.Count); int totalVoxelCount = 0; { for (int i = 0; i < voxelObject.frames.Count; i++) { totalVoxelCount += voxelObject.frames[i].voxelData.voxels.Length; } } var voxels = new VoxelData.Voxel[totalVoxelCount]; IntVector3 voxelSize = IntVector3.zero; Dictionary <Color, int> paletteTable = new Dictionary <Color, int>(); { int offset = 0; int index = 0; for (int i = 0; i < voxelObject.frames.Count; i++) { var voxelData = voxelObject.frames[i].voxelData; chunkDataList.Add(new ChunkData()); chunkDataList[i].voxelBegin = index; for (int j = 0; j < voxelData.voxels.Length; j++) { var voxel = voxelData.voxels[j]; var color = voxelData.palettes[voxel.palette]; if (!paletteTable.ContainsKey(color)) { paletteTable.Add(color, paletteTable.Count); } voxel.palette = paletteTable[color]; voxel.z += offset; voxels[index++] = voxel; voxelBase.voxelData.chunkTable.Set(voxel.position, new IntVector3(i, 0, 0)); } chunkDataList[i].voxelEnd = index; chunkDataList[i].area = new VoxelData.ChunkArea() { min = new IntVector3(0, 0, offset), max = new IntVector3(voxelData.voxelSize.x, voxelData.voxelSize.y, offset + voxelData.voxelSize.z) }; voxelSize = IntVector3.Max(voxelSize, new IntVector3(voxelData.voxelSize.x, voxelData.voxelSize.y, offset + voxelData.voxelSize.z)); offset += voxelData.voxelSize.z + 1; } } #region Create voxelBase.localOffset = Vector3.zero; voxelBase.fileType = VoxelBase.FileType.vox; voxelBase.voxelData.voxels = voxels; voxelBase.voxelData.palettes = new Color[paletteTable.Count]; foreach (var pair in paletteTable) { voxelBase.voxelData.palettes[pair.Value] = pair.Key; } voxelBase.voxelData.voxelSize = voxelSize; base.CreateVoxelTable(); base.UpdateVisibleFlags(); #endregion } #endregion DisplayProgressBar(""); #region Combine DisableData { #region Erase for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].disableData == null) { continue; } List <IntVector3> removeList = new List <IntVector3>(); voxelObject.frames[i].disableData.AllAction((pos, face) => { if (voxelObject.frames[i].voxelData.VoxelTableContains(pos) < 0) { removeList.Add(pos); } }); for (int k = 0; k < removeList.Count; k++) { voxelObject.frames[i].disableData.RemoveDisable(removeList[k]); } } #endregion for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].disableData == null) { voxelObject.frames[i].disableData = new DisableData(); } } { voxelObject.disableData = new DisableData(); for (int j = 0; j < voxelObject.frames.Count; j++) { if (voxelObject.frames[j].disableData == null) { continue; } voxelObject.frames[j].disableData.AllAction((pos, face) => { voxelObject.disableData.SetDisable(chunkDataList[j].area.min + pos, face); }); } } } #endregion DisplayProgressBar(""); #region Combine MaterialData { #region Erase for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].materialData == null) { continue; } for (int j = 0; j < voxelObject.frames[i].materialData.Count; j++) { List <IntVector3> removeList = new List <IntVector3>(); voxelObject.frames[i].materialData[j].AllAction((pos) => { if (voxelObject.frames[i].voxelData.VoxelTableContains(pos) < 0) { removeList.Add(pos); } }); for (int k = 0; k < removeList.Count; k++) { voxelObject.frames[i].materialData[j].RemoveMaterial(removeList[k]); } } } #endregion voxelObject.materialData = new List <MaterialData>(); int materialCount = 1; for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].materialData != null) { materialCount = Math.Max(materialCount, voxelObject.frames[i].materialData.Count); } } for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].materialData == null) { voxelObject.frames[i].materialData = new List <MaterialData>(); } for (int j = voxelObject.frames[i].materialData.Count; j < materialCount; j++) { voxelObject.frames[i].materialData.Add(new MaterialData()); } } for (int i = 0; i < materialCount; i++) { voxelObject.materialData.Add(new MaterialData()); voxelObject.materialData[i].name = voxelObject.frames[0].materialData[i].name; voxelObject.materialData[i].transparent = voxelObject.frames[0].materialData[i].transparent; voxelObject.materialData[i].material = voxelObject.frames[0].materialData[i].material; for (int j = 0; j < voxelObject.frames.Count; j++) { if (voxelObject.frames[j].materialData[i] == null) { continue; } voxelObject.frames[j].materialData[i].AllAction((pos) => { voxelObject.materialData[i].SetMaterial(chunkDataList[j].area.min + pos); }); } } } #endregion DisplayProgressBar(""); #region Material { if (voxelBase.materialData == null) { voxelBase.materialData = new List <MaterialData>(); } if (voxelBase.materialData.Count == 0) { voxelBase.materialData.Add(null); } for (int i = 0; i < voxelBase.materialData.Count; i++) { if (voxelBase.materialData[i] == null) { voxelBase.materialData[i] = new MaterialData(); } } if (voxelObject.materials == null) { voxelObject.materials = new List <Material>(); } if (voxelObject.materials.Count < voxelObject.materialData.Count) { for (int i = voxelObject.materials.Count; i < voxelObject.materialData.Count; i++) { voxelObject.materials.Add(null); } } else if (voxelObject.materials.Count > voxelObject.materialData.Count) { voxelObject.materials.RemoveRange(voxelObject.materialData.Count, voxelObject.materials.Count - voxelObject.materialData.Count); } } voxelBase.CreateMaterialIndexTable(); #endregion DisplayProgressBar(""); CalcDataCreate(voxelBase.voxelData.voxels); DisplayProgressBar(""); #region CreateFaceAreaTable { for (int i = 0; i < chunkDataList.Count; i++) { VoxelData.Voxel[] voxels = new VoxelData.Voxel[chunkDataList[i].voxelEnd - chunkDataList[i].voxelBegin]; Array.Copy(voxelBase.voxelData.voxels, chunkDataList[i].voxelBegin, voxels, 0, voxels.Length); chunkDataList[i].faceAreaTable = CreateFaceArea(voxels); } } #endregion DisplayProgressBar(""); #region CreateTexture { var tmpFaceAreaTable = new VoxelData.FaceAreaTable(); for (int i = 0; i < chunkDataList.Count; i++) { tmpFaceAreaTable.Merge(chunkDataList[i].faceAreaTable); } { var atlasTextureTmp = voxelObject.atlasTexture; if (!CreateTexture(tmpFaceAreaTable, voxelBase.voxelData.palettes, ref atlasRectTable, ref atlasTextureTmp, ref atlasRects)) { EditorUtility.ClearProgressBar(); return(false); } voxelObject.atlasTexture = atlasTextureTmp; if (!AssetDatabase.IsMainAsset(voxelObject.atlasTexture)) { if (voxelBase.legacyAssetNaming) { voxelObject.atlasTexture.name = "tex"; } else { voxelObject.atlasTexture.name = Path.GetFileNameWithoutExtension(voxelBase.voxelFilePath); } } if (!AssetDatabase.Contains(voxelObject.atlasTexture)) { AddObjectToPrefabAsset(voxelObject.atlasTexture); } } } #endregion DisplayProgressBar(""); #region CreateMesh DisplayProgressBar(""); if (voxelObject.importMode == VoxelBase.ImportMode.LowPoly) { int forward = 0; int up = 0; int right = 0; int left = 0; int down = 0; int back = 0; for (int i = 0; i < chunkDataList.Count; i++) { AtlasRectTable atlasRectTableTmp = new AtlasRectTable(); { atlasRectTableTmp.forward = atlasRectTable.forward.GetRange(forward, chunkDataList[i].faceAreaTable.forward.Count); forward += chunkDataList[i].faceAreaTable.forward.Count; atlasRectTableTmp.up = atlasRectTable.up.GetRange(up, chunkDataList[i].faceAreaTable.up.Count); up += chunkDataList[i].faceAreaTable.up.Count; atlasRectTableTmp.right = atlasRectTable.right.GetRange(right, chunkDataList[i].faceAreaTable.right.Count); right += chunkDataList[i].faceAreaTable.right.Count; atlasRectTableTmp.left = atlasRectTable.left.GetRange(left, chunkDataList[i].faceAreaTable.left.Count); left += chunkDataList[i].faceAreaTable.left.Count; atlasRectTableTmp.down = atlasRectTable.down.GetRange(down, chunkDataList[i].faceAreaTable.down.Count); down += chunkDataList[i].faceAreaTable.down.Count; atlasRectTableTmp.back = atlasRectTable.back.GetRange(back, chunkDataList[i].faceAreaTable.back.Count); back += chunkDataList[i].faceAreaTable.back.Count; } var extraOffset = new Vector3(0, 0f, -chunkDataList[i].area.min.z); voxelBase.localOffset = voxelObject.frames[i].localOffset; voxelObject.frames[i].mesh = CreateMeshOnly(voxelObject.frames[i].mesh, chunkDataList[i].faceAreaTable, voxelObject.atlasTexture, atlasRects, atlasRectTableTmp, extraOffset, out voxelObject.frames[i].materialIndexes); } } else { for (int i = 0; i < chunkDataList.Count; i++) { var extraOffset = new Vector3(0, 0f, -chunkDataList[i].area.min.z); voxelBase.localOffset = voxelObject.frames[i].localOffset; voxelObject.frames[i].mesh = CreateMeshOnly(voxelObject.frames[i].mesh, chunkDataList[i].faceAreaTable, voxelObject.atlasTexture, atlasRects, atlasRectTable, extraOffset, out voxelObject.frames[i].materialIndexes); } } { HashSet <int> combineMaterialIndexes = new HashSet <int>(); for (int i = 0; i < chunkDataList.Count; i++) { foreach (var index in voxelObject.frames[i].materialIndexes) { combineMaterialIndexes.Add(index); } } voxelObject.materialIndexes = combineMaterialIndexes.ToList(); } #endregion DisplayProgressBar(""); #region CreateMaterial { if (voxelObject.materialData == null) { voxelObject.materialData = new List <MaterialData>(); } if (voxelObject.materialData.Count == 0) { voxelObject.materialData.Add(null); } for (int i = 0; i < voxelObject.materialData.Count; i++) { if (voxelObject.materialData[i] == null) { voxelObject.materialData[i] = new MaterialData(); } } if (voxelObject.materials == null) { voxelObject.materials = new List <Material>(); } if (voxelObject.materials.Count < voxelObject.materialData.Count) { for (int i = voxelObject.materials.Count; i < voxelObject.materialData.Count; i++) { voxelObject.materials.Add(null); } } else if (voxelObject.materials.Count > voxelObject.materialData.Count) { voxelObject.materials.RemoveRange(voxelObject.materialData.Count, voxelObject.materials.Count - voxelObject.materialData.Count); } for (int i = 0; i < voxelObject.materials.Count; i++) { if (!voxelObject.materialIndexes.Contains(i)) { if (voxelObject.materials[i] != null) { voxelObject.materials[i] = null; DestroyUnusedObjectInPrefabObject(); } continue; } if (voxelObject.materials[i] == null) { voxelObject.materials[i] = EditorCommon.CreateStandardMaterial(); } if (!AssetDatabase.IsMainAsset(voxelObject.materials[i])) { if (voxelBase.legacyAssetNaming) { voxelObject.materials[i].name = string.Format("mat{0}", i); } else { voxelObject.materials[i].name = Path.GetFileNameWithoutExtension(voxelBase.voxelFilePath) + string.Format("_{0}", i); } } if (!AssetDatabase.Contains(voxelObject.materials[i])) { AddObjectToPrefabAsset(voxelObject.materials[i]); } } } #endregion DisplayProgressBar(""); { if (voxelBase.generateLightmapUVs) { var param = voxelBase.GetLightmapParam(); for (int i = 0; i < chunkDataList.Count; i++) { if (voxelObject.frames[i].mesh.uv.Length > 0) { Unwrapping.GenerateSecondaryUVSet(voxelObject.frames[i].mesh, param); } } } if (voxelBase.generateTangents) { for (int i = 0; i < chunkDataList.Count; i++) { voxelObject.frames[i].mesh.RecalculateTangents(); } } for (int i = 0; i < chunkDataList.Count; i++) { if (!AssetDatabase.IsMainAsset(voxelObject.frames[i].mesh)) { if (voxelBase.legacyAssetNaming) { voxelObject.frames[i].mesh.name = string.Format("mesh_{0}", voxelObject.frames[i].name); } else { voxelObject.frames[i].mesh.name = Path.GetFileNameWithoutExtension(voxelBase.voxelFilePath) + string.Format("_{0}", voxelObject.frames[i].name); } } if (!AssetDatabase.Contains(voxelObject.frames[i].mesh)) { AddObjectToPrefabAsset(voxelObject.frames[i].mesh); } } } DisplayProgressBar(""); SetRendererCompornent(); EditorUtility.ClearProgressBar(); voxelObject.Edit_SetFrameCurrentVoxelOtherData(); return(true); }
public void Set(int x, int y, int z, bool flag) { Assert.IsTrue(x >= 0 && y >= 0 && z >= 0); int bIndex = Mathf.FloorToInt(z / 64f); var cIndex = z % 64; if (!flag) { if (table == null || x >= table.Length) { return; } if (table[x] == null || y >= table[x].Length) { return; } if (table[x][y] == null || bIndex >= table[x][y].Length) { return; } } #region Alloc reserve = IntVector3.Max(reserve, new IntVector3(x + 1, y + 1, z + 1)); if (table == null) { table = new UInt64[reserve.x][][]; } if (x >= table.Length) { var newTmp = new UInt64[x + 1][][]; table.CopyTo(newTmp, 0); table = newTmp; } if (table[x] == null) { table[x] = new UInt64[reserve.y][]; } if (y >= table[x].Length) { var newTmp = new UInt64[y + 1][]; table[x].CopyTo(newTmp, 0); table[x] = newTmp; } if (table[x][y] == null) { table[x][y] = new UInt64[reserve.z]; } if (bIndex >= table[x][y].Length) { var newTmp = new UInt64[bufferSize]; table[x][y].CopyTo(newTmp, 0); table[x][y] = newTmp; } #endregion if (flag) { table[x][y][bIndex] |= ((UInt64)1 << cIndex); } else { table[x][y][bIndex] &= ~((UInt64)1 << cIndex); } }
protected override bool LoadVoxelDataFromQB(BinaryReader br) { if (voxelObject.splitMode == VoxelChunksObject.SplitMode.QubicleMatrix) { br.BaseStream.Seek(4, SeekOrigin.Current); //version var colorFormat = br.ReadUInt32(); var zAxisOrientation = br.ReadUInt32(); var compressed = br.ReadUInt32(); br.BaseStream.Seek(4, SeekOrigin.Current); //visibilityMaskEncoded var numMatrices = br.ReadUInt32(); List <VoxelData.Voxel> voxelList = new List <VoxelData.Voxel>(); Dictionary <Color, int> paletteList = new Dictionary <Color, int>(); Dictionary <int, Dictionary <int, HashSet <int> > > doneTable = new Dictionary <int, Dictionary <int, HashSet <int> > >(); //Chunk int chunkIndex = -1; List <int> chunkVoxelList = new List <int>(); List <string> chunkNameList = new List <string>(); Action <int, int, int, UInt32> AddVoxel = (x, y, z, data) => { Color color; if (colorFormat == 0) { var a = (byte)((data & 0xff000000) >> 24); var b = (byte)((data & 0x00ff0000) >> 16); var g = (byte)((data & 0x0000ff00) >> 8); var r = (byte)((data & 0x000000ff)); color = new Color32(r, g, b, a); } else { var a = (byte)((data & 0xff000000) >> 24); var r = (byte)((data & 0x00ff0000) >> 16); var g = (byte)((data & 0x0000ff00) >> 8); var b = (byte)((data & 0x000000ff)); color = new Color32(r, g, b, a); } if (color.a > 0f) { if (!doneTable.ContainsKey(x) || !doneTable[x].ContainsKey(y) || !doneTable[x][y].Contains(z)) { if (!doneTable.ContainsKey(x)) { doneTable.Add(x, new Dictionary <int, HashSet <int> >()); } if (!doneTable[x].ContainsKey(y)) { doneTable[x].Add(y, new HashSet <int>()); } doneTable[x][y].Add(z); color.a = 1f; int palette; if (paletteList.ContainsKey(color)) { palette = paletteList[color]; } else { palette = paletteList.Count; paletteList.Add(color, palette); } voxelList.Add(new VoxelData.Voxel(x, y, z, palette)); //Chunk chunkVoxelList.Add(chunkIndex); } } }; for (int i = 0; i < numMatrices; i++) { var nameLength = br.ReadByte(); var name = new string(br.ReadChars(nameLength)); var sizeX = br.ReadUInt32(); var sizeY = br.ReadUInt32(); var sizeZ = br.ReadUInt32(); var posX = br.ReadInt32(); var posY = br.ReadInt32(); var posZ = br.ReadInt32(); //Chunk chunkIndex = i; chunkNameList.Add(name); if (compressed == 0) { for (int zi = 0; zi < sizeZ; zi++) { for (int yi = 0; yi < sizeY; yi++) { for (int xi = 0; xi < sizeX; xi++) { var x = (posX + xi); var y = (posY + yi); var z = (zAxisOrientation == 0 ? -(posZ + zi + 1) : (posZ + zi)); AddVoxel(x, y, z, br.ReadUInt32()); } } } } else { const UInt32 CODEFLAG = 2; const UInt32 NEXTSLICEFLAG = 6; int zi = 0; while (zi < sizeZ) { zi++; int index = 0; while (true) { var data = br.ReadUInt32(); if (data == NEXTSLICEFLAG) { break; } else if (data == CODEFLAG) { var count = br.ReadUInt32(); data = br.ReadUInt32(); for (int j = 0; j < count; j++) { int xi = (int)(index % sizeX) + 1; int yi = (int)(index / sizeX) + 1; index++; var x = (posX + xi) - 1; var y = (posY + yi) - 1; var z = (zAxisOrientation == 0 ? -(posZ + zi) : (posZ + zi) - 1); AddVoxel(x, y, z, data); } } else { int xi = (int)(index % sizeX) + 1; int yi = (int)(index / sizeX) + 1; index++; var x = (posX + xi) - 1; var y = (posY + yi) - 1; var z = (zAxisOrientation == 0 ? -(posZ + zi) : (posZ + zi) - 1); AddVoxel(x, y, z, data); } } } } } IntVector3 voxelSize; { IntVector3 min = new IntVector3(int.MaxValue, int.MaxValue, int.MaxValue); IntVector3 max = new IntVector3(int.MinValue, int.MinValue, int.MinValue); for (int i = 0; i < voxelList.Count; i++) { //invert { var voxel = voxelList[i]; voxel.x = -voxel.x - 1; voxel.z = -voxel.z - 1; voxelList[i] = voxel; } min = IntVector3.Min(min, voxelList[i].position); max = IntVector3.Max(max, voxelList[i].position); } voxelSize = max - min + IntVector3.one; for (int i = 0; i < voxelList.Count; i++) { var v = voxelList[i]; v.position -= min; voxelList[i] = v; } voxelBase.localOffset = new Vector3(min.x, min.y, min.z); } var voxels = voxelList.ToArray(); var palettes = new Color[paletteList.Count]; foreach (var pair in paletteList) { palettes[pair.Value] = pair.Key; } voxelBase.fileType = VoxelBase.FileType.qb; voxelBase.voxelData = new VoxelData(); voxelBase.voxelData.voxels = voxels; voxelBase.voxelData.palettes = palettes; voxelBase.voxelData.voxelSize = voxelSize; ApplyImportFlags(); voxelBase.voxelData.CreateVoxelTable(); UpdateVisibleFlags(); #region CreateChunkData { Dictionary <int, ChunkArea> chunkAreaList = new Dictionary <int, ChunkArea>(); for (int i = 0; i < voxelList.Count; i++) { if (!chunkAreaList.ContainsKey(chunkVoxelList[i])) { chunkAreaList.Add(chunkVoxelList[i], new ChunkArea() { min = new IntVector3(int.MaxValue, int.MaxValue, int.MaxValue), max = new IntVector3(int.MinValue, int.MinValue, int.MinValue) }); } var chunkArea = chunkAreaList[chunkVoxelList[i]]; chunkArea.min = IntVector3.Min(chunkArea.min, voxelList[i].position); chunkArea.max = IntVector3.Max(chunkArea.max, voxelList[i].position); chunkAreaList[chunkVoxelList[i]] = chunkArea; } var chunkVoxels = new Dictionary <int, List <int> >(); var chunkPalettes = new Dictionary <int, HashSet <Color> >(); voxelChunkPositionTable = new IntVector3[voxelObject.voxelData.voxelSize.x, voxelObject.voxelData.voxelSize.y, voxelObject.voxelData.voxelSize.z]; for (int i = 0; i < voxelObject.voxelData.voxels.Length; i++) { chunkIndex = chunkVoxelList[i]; //voxel if (!chunkVoxels.ContainsKey(chunkIndex)) { chunkVoxels.Add(chunkIndex, new List <int>()); } chunkVoxels[chunkIndex].Add(i); //palette if (!chunkPalettes.ContainsKey(chunkIndex)) { chunkPalettes.Add(chunkIndex, new HashSet <Color>()); } chunkPalettes[chunkIndex].Add(voxelObject.voxelData.palettes[voxelObject.voxelData.voxels[i].palette]); // voxelChunkPositionTable[voxelObject.voxelData.voxels[i].x, voxelObject.voxelData.voxels[i].y, voxelObject.voxelData.voxels[i].z] = new IntVector3(chunkIndex, 0, 0); } { chunkDataList = new List <ChunkData>(chunkVoxels.Count); var enu = chunkVoxels.GetEnumerator(); while (enu.MoveNext()) { chunkDataList.Add(new ChunkData() { position = new IntVector3(enu.Current.Key, int.MinValue, int.MinValue), name = string.Format("Chunk({0})", chunkNameList[enu.Current.Key]), area = chunkAreaList[enu.Current.Key], voxels = enu.Current.Value, palettes = chunkPalettes[enu.Current.Key].ToArray() }); } chunkDataList.Sort((a, b) => string.Compare(a.name, b.name)); } } #endregion return(true); } else { return(base.LoadVoxelDataFromQB(br)); } }
protected override bool CreateMesh() { base.CreateMesh(); #region ProgressBar const float MaxProgressCount = 7f; float ProgressCount = 0; Action <string> DisplayProgressBar = (info) => { if (voxelData.voxels.Length > 10000) { EditorUtility.DisplayProgressBar("Create Mesh...", string.Format("{0} / {1}", ProgressCount, MaxProgressCount), (ProgressCount++ / MaxProgressCount)); } }; #endregion DisplayProgressBar(""); #region Combine VoxelData { voxelBase.voxelData = new VoxelData(); voxelBase.voxelData.chunkTable = new DataTable3 <IntVector3>(voxelBase.voxelData.voxelSize.x, voxelBase.voxelData.voxelSize.y, voxelBase.voxelData.voxelSize.z); chunkDataList = new List <ChunkData>(voxelObject.frames.Count); List <VoxelData.Voxel> voxels = new List <VoxelData.Voxel>(); IntVector3 voxelSize = IntVector3.zero; Dictionary <Color, int> paletteTable = new Dictionary <Color, int>(); int offset = 0; for (int i = 0; i < voxelObject.frames.Count; i++) { chunkDataList.Add(new ChunkData()); chunkDataList[i].voxelBegin = voxels.Count; for (int j = 0; j < voxelObject.frames[i].voxelData.voxels.Length; j++) { var voxel = voxelObject.frames[i].voxelData.voxels[j]; var color = voxelObject.frames[i].voxelData.palettes[voxel.palette]; if (!paletteTable.ContainsKey(color)) { paletteTable.Add(color, paletteTable.Count); } voxel.palette = paletteTable[color]; voxel.z += offset; voxels.Add(voxel); voxelBase.voxelData.chunkTable.Set(voxel.position, new IntVector3(i, 0, 0)); } chunkDataList[i].voxelEnd = voxels.Count; chunkDataList[i].area = new VoxelData.ChunkArea() { min = new IntVector3(0, 0, offset), max = new IntVector3(voxelObject.frames[i].voxelData.voxelSize.x, voxelObject.frames[i].voxelData.voxelSize.y, offset + voxelObject.frames[i].voxelData.voxelSize.z) }; voxelSize = IntVector3.Max(voxelSize, new IntVector3(voxelObject.frames[i].voxelData.voxelSize.x, voxelObject.frames[i].voxelData.voxelSize.y, offset + voxelObject.frames[i].voxelData.voxelSize.z)); offset += voxelObject.frames[i].voxelData.voxelSize.z + 1; } #region Create voxelBase.localOffset = Vector3.zero; voxelBase.fileType = VoxelBase.FileType.vox; voxelBase.voxelData.voxels = voxels.ToArray(); voxelBase.voxelData.palettes = new Color[paletteTable.Count]; foreach (var pair in paletteTable) { voxelBase.voxelData.palettes[pair.Value] = pair.Key; } voxelBase.voxelData.voxelSize = voxelSize; voxelBase.voxelData.CreateVoxelTable(); UpdateVisibleFlags(); #endregion } #endregion DisplayProgressBar(""); #region Combine MaterialData { #region Erase for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].materialData == null) { continue; } for (int j = 0; j < voxelObject.frames[i].materialData.Count; j++) { List <IntVector3> removeList = new List <IntVector3>(); voxelObject.frames[i].materialData[j].AllAction((pos) => { if (voxelObject.frames[i].voxelData.VoxelTableContains(pos) < 0) { removeList.Add(pos); } }); for (int k = 0; k < removeList.Count; k++) { voxelObject.frames[i].materialData[j].RemoveMaterial(removeList[k]); } } } #endregion voxelObject.materialData = new List <MaterialData>(); int materialCount = 1; for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].materialData != null) { materialCount = Math.Max(materialCount, voxelObject.frames[i].materialData.Count); } } for (int i = 0; i < voxelObject.frames.Count; i++) { if (voxelObject.frames[i].materialData == null) { voxelObject.frames[i].materialData = new List <MaterialData>(); } for (int j = voxelObject.frames[i].materialData.Count; j < materialCount; j++) { voxelObject.frames[i].materialData.Add(new MaterialData()); } } for (int i = 0; i < materialCount; i++) { voxelObject.materialData.Add(new MaterialData()); voxelObject.materialData[i].name = voxelObject.frames[0].materialData[i].name; voxelObject.materialData[i].transparent = voxelObject.frames[0].materialData[i].transparent; voxelObject.materialData[i].material = voxelObject.frames[0].materialData[i].material; for (int j = 0; j < voxelObject.frames.Count; j++) { if (voxelObject.frames[j].materialData[i] == null) { continue; } voxelObject.frames[j].materialData[i].AllAction((pos) => { voxelObject.materialData[i].SetMaterial(chunkDataList[j].area.min + pos); }); } } } #endregion DisplayProgressBar(""); #region Material { if (voxelBase.materialData == null) { voxelBase.materialData = new List <MaterialData>(); } if (voxelBase.materialData.Count == 0) { voxelBase.materialData.Add(null); } for (int i = 0; i < voxelBase.materialData.Count; i++) { if (voxelBase.materialData[i] == null) { voxelBase.materialData[i] = new MaterialData(); } } if (voxelObject.materials == null) { voxelObject.materials = new List <Material>(); } if (voxelObject.materials.Count < voxelObject.materialData.Count) { for (int i = voxelObject.materials.Count; i < voxelObject.materialData.Count; i++) { voxelObject.materials.Add(null); } } else if (voxelObject.materials.Count > voxelObject.materialData.Count) { voxelObject.materials.RemoveRange(voxelObject.materialData.Count, voxelObject.materials.Count - voxelObject.materialData.Count); } } voxelBase.CreateMaterialIndexTable(); #endregion CalcDataCreate(voxelBase.voxelData.voxels); #region CreateFaceAreaTable { for (int i = 0; i < chunkDataList.Count; i++) { VoxelData.Voxel[] voxels = new VoxelData.Voxel[chunkDataList[i].voxelEnd - chunkDataList[i].voxelBegin]; Array.Copy(voxelBase.voxelData.voxels, chunkDataList[i].voxelBegin, voxels, 0, voxels.Length); chunkDataList[i].faceAreaTable = CreateFaceArea(voxels); } } #endregion #region CreateTexture { var tmpFaceAreaTable = new VoxelData.FaceAreaTable(); for (int i = 0; i < chunkDataList.Count; i++) { tmpFaceAreaTable.Merge(chunkDataList[i].faceAreaTable); } { var atlasTextureTmp = voxelObject.atlasTexture; if (!CreateTexture(tmpFaceAreaTable, voxelBase.voxelData.palettes, ref atlasRectTable, ref atlasTextureTmp, ref atlasRects)) { EditorUtility.ClearProgressBar(); return(false); } voxelObject.atlasTexture = atlasTextureTmp; { if (voxelObject.materialData == null) { voxelObject.materialData = new List <MaterialData>(); } if (voxelObject.materialData.Count == 0) { voxelObject.materialData.Add(null); } for (int i = 0; i < voxelObject.materialData.Count; i++) { if (voxelObject.materialData[i] == null) { voxelObject.materialData[i] = new MaterialData(); } } if (voxelObject.materials == null) { voxelObject.materials = new List <Material>(); } if (voxelObject.materials.Count < voxelObject.materialData.Count) { for (int i = voxelObject.materials.Count; i < voxelObject.materialData.Count; i++) { voxelObject.materials.Add(null); } } else if (voxelObject.materials.Count > voxelObject.materialData.Count) { voxelObject.materials.RemoveRange(voxelObject.materialData.Count, voxelObject.materials.Count - voxelObject.materialData.Count); } for (int i = 0; i < voxelObject.materials.Count; i++) { if (voxelObject.materials[i] == null) { voxelObject.materials[i] = new Material(Shader.Find("Standard")); } if (!AssetDatabase.Contains(voxelObject.materials[i])) { AddObjectToPrefabAsset(voxelObject.materials[i], "mat", i); } } if (!AssetDatabase.Contains(voxelObject.atlasTexture)) { AddObjectToPrefabAsset(voxelObject.atlasTexture, "tex"); } } } } #endregion #region CreateMesh DisplayProgressBar(""); if (voxelObject.importMode == VoxelBase.ImportMode.LowPoly) { int forward = 0; int up = 0; int right = 0; int left = 0; int down = 0; int back = 0; for (int i = 0; i < chunkDataList.Count; i++) { AtlasRectTable atlasRectTableTmp = new AtlasRectTable(); { atlasRectTableTmp.forward = atlasRectTable.forward.GetRange(forward, chunkDataList[i].faceAreaTable.forward.Count); forward += chunkDataList[i].faceAreaTable.forward.Count; atlasRectTableTmp.up = atlasRectTable.up.GetRange(up, chunkDataList[i].faceAreaTable.up.Count); up += chunkDataList[i].faceAreaTable.up.Count; atlasRectTableTmp.right = atlasRectTable.right.GetRange(right, chunkDataList[i].faceAreaTable.right.Count); right += chunkDataList[i].faceAreaTable.right.Count; atlasRectTableTmp.left = atlasRectTable.left.GetRange(left, chunkDataList[i].faceAreaTable.left.Count); left += chunkDataList[i].faceAreaTable.left.Count; atlasRectTableTmp.down = atlasRectTable.down.GetRange(down, chunkDataList[i].faceAreaTable.down.Count); down += chunkDataList[i].faceAreaTable.down.Count; atlasRectTableTmp.back = atlasRectTable.back.GetRange(back, chunkDataList[i].faceAreaTable.back.Count); back += chunkDataList[i].faceAreaTable.back.Count; } var extraOffset = new Vector3(0, 0f, -chunkDataList[i].area.min.z); voxelBase.localOffset = voxelObject.frames[i].localOffset; voxelObject.frames[i].mesh = CreateMeshOnly(voxelObject.frames[i].mesh, chunkDataList[i].faceAreaTable, voxelObject.atlasTexture, atlasRects, atlasRectTableTmp, extraOffset, out voxelObject.frames[i].materialIndexes); if (!AssetDatabase.Contains(voxelObject.frames[i].mesh)) { var name = voxelObject.frames[i].voxelFileObject != null ? voxelObject.frames[i].voxelFileObject.name : Path.GetFileNameWithoutExtension(voxelObject.frames[i].voxelFilePath); AddObjectToPrefabAsset(voxelObject.frames[i].mesh, string.Format("mesh_{0}", name)); } } } else { for (int i = 0; i < chunkDataList.Count; i++) { var extraOffset = new Vector3(0, 0f, -chunkDataList[i].area.min.z); voxelBase.localOffset = voxelObject.frames[i].localOffset; voxelObject.frames[i].mesh = CreateMeshOnly(voxelObject.frames[i].mesh, chunkDataList[i].faceAreaTable, voxelObject.atlasTexture, atlasRects, atlasRectTable, extraOffset, out voxelObject.frames[i].materialIndexes); if (!AssetDatabase.Contains(voxelObject.frames[i].mesh)) { var name = voxelObject.frames[i].voxelFileObject != null ? voxelObject.frames[i].voxelFileObject.name : Path.GetFileNameWithoutExtension(voxelObject.frames[i].voxelFilePath); AddObjectToPrefabAsset(voxelObject.frames[i].mesh, string.Format("mesh_{0}", name)); } } } #endregion DisplayProgressBar(""); if (voxelBase.generateLightmapUVs) { for (int i = 0; i < chunkDataList.Count; i++) { if (voxelObject.frames[i].mesh.uv.Length > 0) { Unwrapping.GenerateSecondaryUVSet(voxelObject.frames[i].mesh); } } } DisplayProgressBar(""); SetRendererCompornent(); RefreshCheckerSave(); EditorUtility.ClearProgressBar(); voxelObject.Edit_SetFrameCurrentVoxelMaterialData(); return(true); }