static void SetFaceColors(Color[] colors, int vertOrUVIdx0, int vertOrUVIdx1, int vertOrUVIdx2, Parser.Tr2ObjectTexture texObj) { ushort texTileIdx = texObj.Tile; //bind this textile in material? Parser.Tr2ObjectTextureVertex[] Vertices = texObj.Vertices; colors[vertOrUVIdx0] = new Color(0, 0, 0, 1); colors[vertOrUVIdx1] = new Color(0, 0, 0, 1); colors[vertOrUVIdx2] = new Color(0, 0, 0, 1); }
static void SetFaceUVs(Vector2[] nonSharedUVs, int vertOrUVIdx0, int vertOrUVIdx1, int vertOrUVIdx2, Parser.Tr2ObjectTexture texObj) { ushort texTileIdx = (ushort)(texObj.Tile & 0x7ff); //bind this textile in material? Parser.Tr2ObjectTextureVertex[] Vertices = texObj.Vertices; nonSharedUVs[vertOrUVIdx0].x = (float)TextureUV.AdjustTextureCoordinateX((byte)Vertices[0].Xpixel, (sbyte)Vertices[0].Xcoordinate, texTileIdx); nonSharedUVs[vertOrUVIdx0].y = (float)TextureUV.AdjustTextureCoordinateY((byte)Vertices[0].Ypixel, (sbyte)Vertices[0].Ycoordinate, texTileIdx); nonSharedUVs[vertOrUVIdx1].x = (float)TextureUV.AdjustTextureCoordinateX((byte)Vertices[1].Xpixel, (sbyte)Vertices[1].Xcoordinate, texTileIdx); nonSharedUVs[vertOrUVIdx1].y = (float)TextureUV.AdjustTextureCoordinateY((byte)Vertices[1].Ypixel, (sbyte)Vertices[1].Ycoordinate, texTileIdx); nonSharedUVs[vertOrUVIdx2].x = (float)TextureUV.AdjustTextureCoordinateX((byte)Vertices[2].Xpixel, (sbyte)Vertices[2].Xcoordinate, texTileIdx); nonSharedUVs[vertOrUVIdx2].y = (float)TextureUV.AdjustTextureCoordinateY((byte)Vertices[2].Ypixel, (sbyte)Vertices[2].Ycoordinate, texTileIdx); }
public static Mesh CreateObjectMesh(Parser.Tr2Mesh tr2mesh, Parser.Tr2Level leveldata) { Vector3[] sharedVertices = null; if (tr2mesh.NumVertices > 0) { sharedVertices = new Vector3[tr2mesh.NumVertices]; for (int vertAttribCount = 0; vertAttribCount < tr2mesh.NumVertices; vertAttribCount++) { float x = tr2mesh.Vertices[vertAttribCount].x; float y = tr2mesh.Vertices[vertAttribCount].y; float z = tr2mesh.Vertices[vertAttribCount].z; ////print("chk vtx x y z:" +x+ " " +y + " " +z); sharedVertices[vertAttribCount].x = x; sharedVertices[vertAttribCount].y = -y; sharedVertices[vertAttribCount].z = z; } //uv = new Vector2[leveldata.Rooms[chkRoom].RoomData.NumVertices]; } //warning: a variable lengh array in a structure can cause access violence //selected_texObjectIdx = leveldata.Rooms[chkRoom].RoomData.Rectangles[0].Texture; //selected_texObj = leveldata.ObjectTextures[selected_texObjectIdx]; //selected_texTileIdx = selected_texObj.Tile; int NumTexturedTriangles = tr2mesh.NumTexturedTriangles; int NumTexturedRectangles = tr2mesh.NumTexturedRectangles; int numNonsharedVertices = (NumTexturedRectangles * 4) + (NumTexturedTriangles * 3); int numNonsharedTris = (NumTexturedRectangles * 3 * 2) + (NumTexturedTriangles * 3); Vector3[] nonSharedVertices = new Vector3[numNonsharedVertices]; Vector2[] nonSharedUVs = new Vector2[numNonsharedVertices]; int[] nonSharedTris = new int[numNonsharedTris]; //triangles = new int[leveldata.Rooms[chkRoom].RoomData.NumRectangles * 3 * 2]; Parser.Tr2Face4[] TexturedRectangles = tr2mesh.TexturedRectangles; for (int rectCount = 0; rectCount < NumTexturedRectangles; rectCount++) { int Idx0 = TexturedRectangles[rectCount].Vertices0; int Idx1 = TexturedRectangles[rectCount].Vertices1; int Idx2 = TexturedRectangles[rectCount].Vertices2; int Idx3 = TexturedRectangles[rectCount].Vertices3; int vertOrUVIdx0 = rectCount * 4 + 0; int vertOrUVIdx1 = rectCount * 4 + 1; int vertOrUVIdx2 = rectCount * 4 + 2; int vertOrUVIdx3 = rectCount * 4 + 3; nonSharedVertices[vertOrUVIdx0] = sharedVertices[Idx0]; nonSharedVertices[vertOrUVIdx1] = sharedVertices[Idx1]; nonSharedVertices[vertOrUVIdx2] = sharedVertices[Idx2]; nonSharedVertices[vertOrUVIdx3] = sharedVertices[Idx3]; ushort texObjectIdx = TexturedRectangles[rectCount].Texture; if (texObjectIdx >= leveldata.ObjectTextures.Length) { continue; //fixed: outof bound exception for Parser.Tr2Level.ObjectTextures } Parser.Tr2ObjectTexture texObj = leveldata.ObjectTextures[texObjectIdx]; ushort texTileIdx = texObj.Tile; //bind this textile in material? //if(texTileIdx != prevTexture) //{ //newMatCount +=1; //prevTexture = texTileIdx; ////print("newMatCount:"+ newMatCount); //} SetFaceUVs(nonSharedUVs, vertOrUVIdx0, vertOrUVIdx1, vertOrUVIdx2, vertOrUVIdx3, texObj); ////print("uv[Idx0]"+ uv[Idx0].x + " " + uv[Idx0].y); ////print("uv[Idx1]"+ uv[Idx1].x + " " + uv[Idx1].y); //ushort opacity = texObj.TransparencyFlags; //isItOpacq nonSharedTris[rectCount * 6 + 0] = vertOrUVIdx0; nonSharedTris[rectCount * 6 + 1] = vertOrUVIdx1; nonSharedTris[rectCount * 6 + 2] = vertOrUVIdx2; nonSharedTris[rectCount * 6 + 3] = vertOrUVIdx2; nonSharedTris[rectCount * 6 + 4] = vertOrUVIdx3; nonSharedTris[rectCount * 6 + 5] = vertOrUVIdx0; } Parser.Tr2Face3[] TexturedTriangles = tr2mesh.TexturedTriangles; for (int triCount = 0; triCount < NumTexturedTriangles; triCount++) { int Idx0 = TexturedTriangles[triCount].Vertices0; int Idx1 = TexturedTriangles[triCount].Vertices1; int Idx2 = TexturedTriangles[triCount].Vertices2; int vertOrUVIdx0 = triCount * 3 + 0; int vertOrUVIdx1 = triCount * 3 + 1; int vertOrUVIdx2 = triCount * 3 + 2; int strideVertIdx = (NumTexturedRectangles * 4); int strideTriIdx = (NumTexturedRectangles * 3 * 2); nonSharedVertices[strideVertIdx + vertOrUVIdx0] = sharedVertices[Idx0]; nonSharedVertices[strideVertIdx + vertOrUVIdx1] = sharedVertices[Idx1]; nonSharedVertices[strideVertIdx + vertOrUVIdx2] = sharedVertices[Idx2]; ushort texObjectIdx = tr2mesh.TexturedTriangles[triCount].Texture; if (texObjectIdx >= leveldata.ObjectTextures.Length) { continue; //fixed: outof bound exception for Parser.Tr2Level.ObjectTextures } Parser.Tr2ObjectTexture texObj = leveldata.ObjectTextures[texObjectIdx]; //if(texTileIdx != prevTexture) //{ //newMatCount +=1; //prevTexture = texTileIdx; ////print("newMatCount:"+ newMatCount); //} SetFaceUVs(nonSharedUVs, strideVertIdx + vertOrUVIdx0, strideVertIdx + vertOrUVIdx1, strideVertIdx + vertOrUVIdx2, texObj); ////print("uv[Idx0]"+ uv[Idx0].x + " " + uv[Idx0].y); ////print("uv[Idx1]"+ uv[Idx1].x + " " + uv[Idx1].y); //ushort opacity = texObj.TransparencyFlags; //isItOpacq nonSharedTris[strideTriIdx + vertOrUVIdx0] = strideVertIdx + vertOrUVIdx0; nonSharedTris[strideTriIdx + vertOrUVIdx1] = strideVertIdx + vertOrUVIdx1; nonSharedTris[strideTriIdx + vertOrUVIdx2] = strideVertIdx + vertOrUVIdx2; } for (int i = 0; i < nonSharedVertices.Length; i++) { nonSharedVertices[i] = nonSharedVertices[i] * Settings.SceneScaling; } Mesh mesh = new Mesh(); mesh.Clear(); mesh.vertices = nonSharedVertices; mesh.uv = nonSharedUVs; mesh.triangles = nonSharedTris; MeshModifier.VertexWeild(mesh); #if UNITY_EDITOR Vector4[] tangents = new Vector4[mesh.vertices.Length]; computeTangentsAndBinormals(mesh.vertices, mesh.normals, mesh.uv, mesh.triangles, tangents); mesh.tangents = tangents; tangents = null; #endif //free some memory nonSharedVertices = null; nonSharedUVs = null; nonSharedTris = null; return(mesh); }
public static Mesh CreateRoomMesh(Parser.Tr2Room tr2room, Parser.Tr2Level leveldata, ref bool has_water) { Vector3[] sharedVertices = null; has_water = false; byte[] is_water_vertex = null; bool has_water_face = false; if (tr2room.RoomData.NumVertices > 0) { int LightMode = tr2room.LightMode; int NumVertices = tr2room.RoomData.NumVertices; // optimized for field access Parser.Tr2VertexRoom[] Vertices = tr2room.RoomData.Vertices; sharedVertices = new Vector3[NumVertices]; is_water_vertex = new byte[sharedVertices.Length]; for (int vertAttribCount = 0; vertAttribCount < NumVertices; vertAttribCount++) { float x = Vertices[vertAttribCount].Vertex.x; float y = Vertices[vertAttribCount].Vertex.y; float z = Vertices[vertAttribCount].Vertex.z; ////print("chk vtx x y z:" +x+ " " +y + " " +z); sharedVertices[vertAttribCount].x = x; sharedVertices[vertAttribCount].y = -y; sharedVertices[vertAttribCount].z = z; is_water_vertex[vertAttribCount] = 10; if ((Vertices[vertAttribCount].Attributes & 0x8000L) == 0x8000L) { is_water_vertex[vertAttribCount] = 1; has_water = true; } } //warning: avariable lengh array in a structure can cause access violence //if(tr2room.RoomData.NumRectangles > 0) //{ //selected_texObjectIdx = tr2room.RoomData.Rectangles[0].Texture; //selected_texObj = leveldata.ObjectTextures[selected_texObjectIdx]; //selected_texTileIdx = selected_texObj.Tile; int NumRectangles = tr2room.RoomData.NumRectangles; // optimized for field access int strideVertIdx = (NumRectangles * 4); int strideTriIdx = (NumRectangles * 3 * 2); int numNonsharedVertices = strideVertIdx + (tr2room.RoomData.NumTriangles * 3); int numNonsharedTris = strideTriIdx + (tr2room.RoomData.NumTriangles * 3); Vector3[] nonSharedVertices = new Vector3[numNonsharedVertices]; Vector2[] nonSharedUVs = new Vector2[numNonsharedVertices]; Vector2[] nonSharedUV2s = new Vector2[numNonsharedVertices]; Color[] nonSharedColor = new Color[numNonsharedVertices]; int[] nonSharedTris = new int[numNonsharedTris]; //triangles = new int[num_rectangles * 3 * 2]; Parser.Tr2Face4[] Rectangles = tr2room.RoomData.Rectangles; // optimized for field access for (int rectCount = 0; rectCount < NumRectangles; rectCount++) { int Idx0 = Rectangles[rectCount].Vertices0; int Idx1 = Rectangles[rectCount].Vertices1; int Idx2 = Rectangles[rectCount].Vertices2; int Idx3 = Rectangles[rectCount].Vertices3; ////print ("idx0 - Idx1 - Idx2 - Idx3:" + Idx0 + " " + Idx1 + " " + Idx2 +" " + Idx3); int vertOrUVIdx0 = rectCount * 4 + 0; int vertOrUVIdx1 = rectCount * 4 + 1; int vertOrUVIdx2 = rectCount * 4 + 2; int vertOrUVIdx3 = rectCount * 4 + 3; if (has_water) { if (IsFaceInWater(is_water_vertex, Idx0, Idx1, Idx2, Idx3)) //if all vertices are in water { continue; } } else { if (IsFaceInWater(leveldata, Rectangles[rectCount].Texture)) { has_water_face = true; continue; } } nonSharedVertices[vertOrUVIdx0] = sharedVertices[Idx0]; nonSharedVertices[vertOrUVIdx1] = sharedVertices[Idx1]; nonSharedVertices[vertOrUVIdx2] = sharedVertices[Idx2]; nonSharedVertices[vertOrUVIdx3] = sharedVertices[Idx3]; if (has_water) { //Added vertex color for lighting effect //Debug.Log("Light Atrrib0" + (Vertices[Idx0].Attributes & 0x1f)); //Debug.Log("Light Atrrib1" + (Vertices[Idx1].Attributes & 0x1f)); //Debug.Log("Light Atrrib2" + (Vertices[Idx2].Attributes & 0x1f)); } //Added vertex color for lighting effect nonSharedColor[vertOrUVIdx0] = Color.white * (1 - Vertices[Idx0].Lighting2 * 1.220852154804053e-4f); // ((0.5f - ((float)(Vertices[Idx0].Attributes & 0x1f) / 32f)) + 0.5f); nonSharedColor[vertOrUVIdx1] = Color.white * (1 - Vertices[Idx1].Lighting2 * 1.220852154804053e-4f); // ((0.5f - ((float)(Vertices[Idx1].Attributes & 0x1f) / 32f)) + 0.5f); nonSharedColor[vertOrUVIdx2] = Color.white * (1 - Vertices[Idx2].Lighting2 * 1.220852154804053e-4f); // ((0.5f - ((float)(Vertices[Idx2].Attributes & 0x1f) / 32f)) + 0.5f); nonSharedColor[vertOrUVIdx3] = Color.white * (1 - Vertices[Idx3].Lighting2 * 1.220852154804053e-4f); // ((0.5f - ((float)(Vertices[Idx3].Attributes & 0x1f) / 32f)) + 0.5f); ushort texObjectIdx = Rectangles[rectCount].Texture; if (texObjectIdx >= leveldata.ObjectTextures.Length) { continue; //fixed: outof bound exception for Parser.Tr2Level.ObjectTextures } Parser.Tr2ObjectTexture texObj = leveldata.ObjectTextures[texObjectIdx]; ushort texTileIdx = texObj.Tile; //bind this textile in material? //if(texTileIdx != prevTexture) //{ //newMatCount +=1; //prevTexture = texTileIdx; ////print("newMatCount:"+ newMatCount); //} SetFaceUVs(nonSharedUVs, vertOrUVIdx0, vertOrUVIdx1, vertOrUVIdx2, vertOrUVIdx3, texObj); ////print("uv[Idx0]"+ uv[Idx0].x + " " + uv[Idx0].y); ////print("uv[Idx1]"+ uv[Idx1].x + " " + uv[Idx1].y); //ushort opacity = texObj.TransparencyFlags; //isItOpacq nonSharedTris[rectCount * 6 + 0] = vertOrUVIdx0; nonSharedTris[rectCount * 6 + 1] = vertOrUVIdx1; nonSharedTris[rectCount * 6 + 2] = vertOrUVIdx2; nonSharedTris[rectCount * 6 + 3] = vertOrUVIdx2; nonSharedTris[rectCount * 6 + 4] = vertOrUVIdx3; nonSharedTris[rectCount * 6 + 5] = vertOrUVIdx0; } Parser.Tr2Face3[] Triangles = tr2room.RoomData.Triangles; // optimized for field access int NumTriangles = tr2room.RoomData.NumTriangles; for (int triCount = 0; triCount < NumTriangles; triCount++) { ////print("tr2room.RoomData.NumTriangles"+ tr2room.RoomData.NumTriangles); int Idx0 = Triangles[triCount].Vertices0; int Idx1 = Triangles[triCount].Vertices1; int Idx2 = Triangles[triCount].Vertices2; ////print ("idx0 - Idx1 - Idx2:" + Idx0 + " " + Idx1 + " " + Idx2); //[][][][]+[][][] int vertOrUVIdx0 = triCount * 3 + 0; int vertOrUVIdx1 = triCount * 3 + 1; int vertOrUVIdx2 = triCount * 3 + 2; if (has_water) { if (IsFaceInWater(is_water_vertex, Idx0, Idx1, Idx2)) //if all vertices are in water { continue; } } else { if (IsFaceInWater(leveldata, Triangles[triCount].Texture)) { has_water_face = true; continue; } } nonSharedVertices[strideVertIdx + vertOrUVIdx0] = sharedVertices[Idx0]; nonSharedVertices[strideVertIdx + vertOrUVIdx1] = sharedVertices[Idx1]; nonSharedVertices[strideVertIdx + vertOrUVIdx2] = sharedVertices[Idx2]; if (has_water) { //Added vertex color for lighting effect //Debug.Log("Light Atrrib0" + (Vertices[Idx0].Attributes & 0x1f)); //Debug.Log("Light Atrrib1" + (Vertices[Idx1].Attributes & 0x1f)); //Debug.Log("Light Atrrib2" + (Vertices[Idx2].Attributes & 0x1f)); } nonSharedColor[strideVertIdx + vertOrUVIdx0] = Color.white * (1 - Vertices[Idx0].Lighting2 * 1.220852154804053e-4f); ////Color.white * ((0.5f - ((float)(Vertices[Idx0].Attributes & 0x1f) / 32f)) + 0.5f); nonSharedColor[strideVertIdx + vertOrUVIdx1] = Color.white * (1 - Vertices[Idx1].Lighting2 * 1.220852154804053e-4f); ////Color.white * ((0.5f - ((float)(Vertices[Idx1].Attributes & 0x1f) / 32f)) + 0.5f); nonSharedColor[strideVertIdx + vertOrUVIdx2] = Color.white * (1 - Vertices[Idx2].Lighting2 * 1.220852154804053e-4f); ////Color.white * ((0.5f - ((float)(Vertices[Idx2].Attributes & 0x1f) / 32f)) + 0.5f); ushort texObjectIdx = Triangles[triCount].Texture; if (texObjectIdx >= leveldata.ObjectTextures.Length) { continue; //fixed: outof bound exception for Parser.Tr2Level.ObjectTextures } Parser.Tr2ObjectTexture texObj = leveldata.ObjectTextures[texObjectIdx]; //if(texTileIdx != prevTexture) //{ //newMatCount +=1; //prevTexture = texTileIdx; ////print("newMatCount:"+ newMatCount); //} SetFaceUVs(nonSharedUVs, strideVertIdx + vertOrUVIdx0, strideVertIdx + vertOrUVIdx1, strideVertIdx + vertOrUVIdx2, texObj); ////print("uv[Idx0]"+ uv[Idx0].x + " " + uv[Idx0].y); ////print("uv[Idx1]"+ uv[Idx1].x + " " + uv[Idx1].y); //ushort opacity = texObj.TransparencyFlags; //isItOpacq nonSharedTris[strideTriIdx + vertOrUVIdx0] = strideVertIdx + vertOrUVIdx0; nonSharedTris[strideTriIdx + vertOrUVIdx1] = strideVertIdx + vertOrUVIdx1; nonSharedTris[strideTriIdx + vertOrUVIdx2] = strideVertIdx + vertOrUVIdx2; ////print ("idx0 - Idx1 - Idx2:" + nonSharedTris[strideTriIdx + vertOrUVIdx0] + " " + nonSharedTris[strideTriIdx + vertOrUVIdx1] + " " + nonSharedTris[strideTriIdx + vertOrUVIdx2] ); } if (has_water_face) { has_water = true; } ////print("leveldata.Rooms[5].RoomData.NumRectangles:"+ tr2room.RoomData.NumRectangles); //SetTriangles (triangles : int[], submesh : int) : void //generate secondary uv set for (int i = 0; i < nonSharedVertices.Length; i++) { nonSharedVertices[i] = nonSharedVertices[i] * Settings.SceneScaling; } Mesh mesh = new Mesh(); mesh.Clear(); mesh.vertices = nonSharedVertices; mesh.uv = nonSharedUVs; mesh.uv2 = nonSharedUVs; mesh.colors = nonSharedColor; mesh.triangles = nonSharedTris; //mesh.Optimize(); mesh.RecalculateNormals(); #if UNITY_EDITOR Vector4[] tangents = new Vector4[mesh.vertices.Length]; computeTangentsAndBinormals(nonSharedVertices, mesh.normals, nonSharedUVs, nonSharedTris, tangents); mesh.tangents = tangents; tangents = null; #endif //free some memory nonSharedVertices = null; nonSharedUVs = null; nonSharedUV2s = null; nonSharedTris = null; nonSharedColor = null; //} return(mesh); } return(new Mesh()); //empty mesh }
public static Mesh CreateRoomWaterMesh(Parser.Tr2Room tr2room, Parser.Tr2Level leveldata) { Vector3[] sharedVertices = null; byte[] is_water_vertex = null; bool has_water = false; if (tr2room.RoomData.NumVertices > 0) { int NumVertices = tr2room.RoomData.NumVertices; sharedVertices = new Vector3[NumVertices]; is_water_vertex = new byte[sharedVertices.Length]; Parser.Tr2VertexRoom[] Vertices = tr2room.RoomData.Vertices; for (int vertAttribCount = 0; vertAttribCount < NumVertices; vertAttribCount++) { float x = Vertices[vertAttribCount].Vertex.x; float y = Vertices[vertAttribCount].Vertex.y; float z = Vertices[vertAttribCount].Vertex.z; ////print("chk vtx x y z:" +x+ " " +y + " " +z); sharedVertices[vertAttribCount].x = x; sharedVertices[vertAttribCount].y = -y; sharedVertices[vertAttribCount].z = z; is_water_vertex[vertAttribCount] = 10; if ((Vertices[vertAttribCount].Attributes & 0x8000L) == 0x8000L) { is_water_vertex[vertAttribCount] = 1; has_water = true; } } } //warning: avariable lengh array in a structure can cause access violence //if(tr2room.RoomData.NumRectangles > 0) //{ //selected_texObjectIdx = tr2room.RoomData.Rectangles[0].Texture; //selected_texObj = leveldata.ObjectTextures[selected_texObjectIdx]; //selected_texTileIdx = selected_texObj.Tile; int NumRectangles = tr2room.RoomData.NumRectangles; int strideVertIdx = (NumRectangles * 4); int strideTriIdx = (NumRectangles * 3 * 2); int numNonsharedVertices = strideVertIdx + (tr2room.RoomData.NumTriangles * 3); int numNonsharedTris = strideTriIdx + (tr2room.RoomData.NumTriangles * 3); Vector3[] nonSharedVertices = new Vector3[numNonsharedVertices]; Vector2[] nonSharedUVs = new Vector2[numNonsharedVertices]; Vector2[] nonSharedUV2s = new Vector2[numNonsharedVertices]; int[] nonSharedTris = new int[numNonsharedTris]; Parser.Tr2Face4[] Rectangles = tr2room.RoomData.Rectangles; for (int rectCount = 0; rectCount < NumRectangles; rectCount++) { int Idx0 = Rectangles[rectCount].Vertices0; int Idx1 = Rectangles[rectCount].Vertices1; int Idx2 = Rectangles[rectCount].Vertices2; int Idx3 = Rectangles[rectCount].Vertices3; ////print ("idx0 - Idx1 - Idx2 - Idx3:" + Idx0 + " " + Idx1 + " " + Idx2 +" " + Idx3); int vertOrUVIdx0 = rectCount * 4 + 0; int vertOrUVIdx1 = rectCount * 4 + 1; int vertOrUVIdx2 = rectCount * 4 + 2; int vertOrUVIdx3 = rectCount * 4 + 3; if (has_water) { if (!IsFaceInWater(is_water_vertex, Idx0, Idx1, Idx2, Idx3)) //if not all vertices are in water { continue; } } else { if (!IsFaceInWater(leveldata, Rectangles[rectCount].Texture)) { continue; } } nonSharedVertices[vertOrUVIdx0] = sharedVertices[Idx0]; nonSharedVertices[vertOrUVIdx1] = sharedVertices[Idx1]; nonSharedVertices[vertOrUVIdx2] = sharedVertices[Idx2]; nonSharedVertices[vertOrUVIdx3] = sharedVertices[Idx3]; ushort texObjectIdx = Rectangles[rectCount].Texture; if (texObjectIdx >= leveldata.ObjectTextures.Length) { continue; //fixed: outof bound exception for Parser.Tr2Level.ObjectTextures } Parser.Tr2ObjectTexture texObj = leveldata.ObjectTextures[texObjectIdx]; ushort texTileIdx = texObj.Tile; //bind this textile in material? //if(texTileIdx != prevTexture) //{ //newMatCount +=1; //prevTexture = texTileIdx; ////print("newMatCount:"+ newMatCount); //} SetFaceUVs(nonSharedUVs, vertOrUVIdx0, vertOrUVIdx1, vertOrUVIdx2, vertOrUVIdx3, texObj); ////print("uv[Idx0]"+ uv[Idx0].x + " " + uv[Idx0].y); ////print("uv[Idx1]"+ uv[Idx1].x + " " + uv[Idx1].y); //ushort opacity = texObj.TransparencyFlags; //isItOpacq //generate secondary uv for animation by going through all animated texture group and checking existance of //texObjectIdx in that group //leveldata.AnimatedTextures[] // this is varable length record of animated texture group int texture_idx = GetAnimatedTextureIndex(leveldata.AnimatedTextures, leveldata.NumAnimatedTextures, texObjectIdx); if (texture_idx > -1) { texObj = leveldata.ObjectTextures[texture_idx]; SetFaceUVs(nonSharedUV2s, vertOrUVIdx0, vertOrUVIdx1, vertOrUVIdx2, vertOrUVIdx3, texObj); } nonSharedTris[rectCount * 6 + 0] = vertOrUVIdx0; nonSharedTris[rectCount * 6 + 1] = vertOrUVIdx1; nonSharedTris[rectCount * 6 + 2] = vertOrUVIdx2; nonSharedTris[rectCount * 6 + 3] = vertOrUVIdx2; nonSharedTris[rectCount * 6 + 4] = vertOrUVIdx3; nonSharedTris[rectCount * 6 + 5] = vertOrUVIdx0; } int NumTriangles = tr2room.RoomData.NumTriangles; Parser.Tr2Face3[] Triangles = tr2room.RoomData.Triangles; for (int triCount = 0; triCount < tr2room.RoomData.NumTriangles; triCount++) { ////print("tr2room.RoomData.NumTriangles"+ tr2room.RoomData.NumTriangles); int Idx0 = Triangles[triCount].Vertices0; int Idx1 = Triangles[triCount].Vertices1; int Idx2 = Triangles[triCount].Vertices2; ////print ("idx0 - Idx1 - Idx2:" + Idx0 + " " + Idx1 + " " + Idx2); //[][][][]+[][][] int vertOrUVIdx0 = triCount * 3 + 0; int vertOrUVIdx1 = triCount * 3 + 1; int vertOrUVIdx2 = triCount * 3 + 2; if (has_water) { if (!IsFaceInWater(is_water_vertex, Idx0, Idx1, Idx2)) //if not all vertices are in water { continue; } } else { if (!IsFaceInWater(leveldata, Triangles[triCount].Texture)) { continue; } } nonSharedVertices[strideVertIdx + vertOrUVIdx0] = sharedVertices[Idx0]; nonSharedVertices[strideVertIdx + vertOrUVIdx1] = sharedVertices[Idx1]; nonSharedVertices[strideVertIdx + vertOrUVIdx2] = sharedVertices[Idx2]; ushort texObjectIdx = Triangles[triCount].Texture; if (texObjectIdx >= leveldata.ObjectTextures.Length) { continue; //fixed: outof bound exception for Parser.Tr2Level.ObjectTextures } Parser.Tr2ObjectTexture texObj = leveldata.ObjectTextures[texObjectIdx]; //if(texTileIdx != prevTexture) //{ //newMatCount +=1; //prevTexture = texTileIdx; ////print("newMatCount:"+ newMatCount); //} SetFaceUVs(nonSharedUVs, strideVertIdx + vertOrUVIdx0, strideVertIdx + vertOrUVIdx1, strideVertIdx + vertOrUVIdx2, texObj); int texture_idx = GetAnimatedTextureIndex(leveldata.AnimatedTextures, leveldata.NumAnimatedTextures, texObjectIdx); if (texture_idx > -1) { texObj = leveldata.ObjectTextures[texture_idx]; SetFaceUVs(nonSharedUV2s, strideVertIdx + vertOrUVIdx0, strideVertIdx + vertOrUVIdx1, strideVertIdx + vertOrUVIdx2, texObj); } ////print("uv[Idx0]"+ uv[Idx0].x + " " + uv[Idx0].y); ////print("uv[Idx1]"+ uv[Idx1].x + " " + uv[Idx1].y); //ushort opacity = texObj.TransparencyFlags; //isItOpacq nonSharedTris[strideTriIdx + vertOrUVIdx0] = strideVertIdx + vertOrUVIdx0; nonSharedTris[strideTriIdx + vertOrUVIdx1] = strideVertIdx + vertOrUVIdx1; nonSharedTris[strideTriIdx + vertOrUVIdx2] = strideVertIdx + vertOrUVIdx2; ////print ("idx0 - Idx1 - Idx2:" + nonSharedTris[strideTriIdx + vertOrUVIdx0] + " " + nonSharedTris[strideTriIdx + vertOrUVIdx1] + " " + nonSharedTris[strideTriIdx + vertOrUVIdx2] ); } ////print("leveldata.Rooms[5].RoomData.NumRectangles:"+ tr2room.RoomData.NumRectangles); //SetTriangles (triangles : int[], submesh : int) : void //generate secondary uv set for (int i = 0; i < nonSharedVertices.Length; i++) { nonSharedVertices[i] = nonSharedVertices[i] * Settings.SceneScaling; } Mesh mesh = new Mesh(); mesh.Clear(); mesh.vertices = nonSharedVertices; mesh.uv = nonSharedUVs; mesh.uv2 = nonSharedUV2s; mesh.triangles = nonSharedTris; //mesh.Optimize(); mesh.RecalculateNormals(); #if UNITY_EDITOR Vector4[] tangents = new Vector4[mesh.vertices.Length]; computeTangentsAndBinormals(nonSharedVertices, mesh.normals, nonSharedUVs, nonSharedTris, tangents); mesh.tangents = tangents; tangents = null; #endif //free some memory nonSharedVertices = null; nonSharedUVs = null; nonSharedUV2s = null; nonSharedTris = null; //} return(mesh); }
public static Texture2D GenerateTextureTile(Parser.Tr2Level leveldata) { int c16_index = 0; int c16_pixel_count = 256 * 256; // pixel count optimization Color[][] ColorTable = new Color[leveldata.m_MaxTiles][]; for (int tileCount = 0; tileCount < leveldata.m_MaxTiles; tileCount++) { ColorTable[tileCount] = new Color[c16_pixel_count]; for (int c = 0; c < c16_pixel_count; c++) { ColorTable[tileCount][c] = Color.white; } //if(tileCount == 2) break; ushort[] tmparr = leveldata.Textile16[tileCount].Tile; Color[] cols = ColorTable[tileCount]; for (c16_index = 0; c16_index < c16_pixel_count; c16_index++) { //argb ushort ucolor = tmparr[c16_index]; if ((ucolor & 0x8000) == 0x8000) ////optimized bit shift and & operation ((ucolor >> 15) & 0x1) == 1 with direct & (ucolor & 0x8000) == 1 operation { cols[c16_index].a = 1.0f; } else { cols[c16_index].a = 0.0f; } //fix color conversion with range 0 - 31 cols[c16_index].b = (ucolor & 0x1f) * cmult; cols[c16_index].g = ((ucolor >> 5) & 0x1f) * cmult; cols[c16_index].r = ((ucolor >> 10) & 0x1f) * cmult; //Vector3 alpha_vec = new Vector3(cols[c16_index].r, cols[c16_index].g, cols[c16_index].b); //if(alpha_vec.magnitude <= 0.097) //{ //cols[c16_index].a = 0.0f; //} } //render transparancy information into tile int ntexObj = leveldata.ObjectTextures.Length; for (int i = 0; i < ntexObj; i++) { Parser.Tr2ObjectTexture texobj = leveldata.ObjectTextures[i]; // texobj.TransparencyFlags means geometry level transparancy, not pixel level transparency // this is used for geometry material batching if (texobj.Tile == tileCount && texobj.TransparencyFlags == 0) { //interpolate pixels //generate pixel bound Parser.Tr2ObjectTextureVertex[] vertices = texobj.Vertices; int minxi = vertices[0].Xpixel; int maxxi = vertices[0].Xpixel; int minyi = vertices[0].Ypixel; int maxyi = vertices[0].Ypixel; for (int v = 0; v < vertices.Length - 1; v++) { if (vertices[v].Xcoordinate < minxi) { minxi = vertices[v].Xpixel; } if (vertices[v].Xcoordinate > maxxi) { maxxi = vertices[v].Xpixel; } if (vertices[v].Ycoordinate < minyi) { minyi = vertices[v].Ypixel; } if (vertices[v].Ycoordinate > maxyi) { maxyi = vertices[v].Ypixel; } } //render transparancy in generated bound if (vertices.Length < 4) { Vector3 p0 = new Vector3(vertices[0].Xpixel, 0, vertices[0].Ypixel); Vector3 p1 = new Vector3(vertices[1].Xpixel, 0, vertices[1].Ypixel); Vector3 p2 = new Vector3(vertices[2].Xpixel, 0, vertices[2].Ypixel); for (int y = minyi; y < maxyi; y++) { for (int x = minxi; x < maxxi; x++) { if (IsUVInSide(p2, p1, p0, new Vector3(x, 0, y))) { int idx = y * 256 + x; cols[idx].a = 1; } } } } else { for (int y = minyi; y < maxyi; y++) { for (int x = minxi; x < maxxi; x++) { //if(IsUVInSide( p2, p1,p0, new Vector3(x,0, y) )) //{ int idx = y * 256 + x; cols[idx].a = 1; //} } } } } //end transparancy flag check } } //pack tiles float uvlength = 1.0f / (float)(leveldata.m_MaxTiles); //bug fixed: used leveldata.m_MaxTiles instead of hardcoded value 16 uvRects = new Rect[leveldata.m_MaxTiles]; Texture2D tex = new Texture2D(256, 256 * leveldata.m_MaxTiles, TextureFormat.ARGB32, false, true); tex.filterMode = FilterMode.Bilinear; tex.wrapMode = TextureWrapMode.Clamp; tex.anisoLevel = 9; for (int t = 0; t < leveldata.m_MaxTiles; t++) { Color[] cols = ColorTable[t]; uvRects[t] = new Rect(0, uvlength * t, 1, uvlength); //distorted uv error : reason careless uv stting tex.SetPixels(0, 256 * t, 256, 256, cols, 0); } tex.Apply(true); tex.name = "texAtlas"; tex.hideFlags = 0; return(tex); }