public _MeshPrimitiveDecoder(Assimp.Mesh mesh, TMaterial material) { _Source = mesh; _Material = material; _ColorCount = 0; if (mesh.HasVertexColors(0)) { _ColorCount = 1; } if (mesh.HasVertexColors(1)) { _ColorCount = 2; } _TexCoordCount = 0; if (mesh.HasTextureCoords(0)) { _TexCoordCount = 1; } if (mesh.HasTextureCoords(1)) { _TexCoordCount = 2; } if (mesh.HasBones) { var influences = new List <(int bone, float weight)> [_Source.VertexCount];
private bool addToVBO(Assimp.Mesh mesh, ref List <float> vboData) { if (getFlags(mesh) != m_currentFlags) { textBoxInfo.Text += Environment.NewLine + "Skipping mesh with invalid vertex data..."; return(false); } for (var i = 0; i < mesh.VertexCount; ++i) { var pos = mesh.Vertices[i]; vboData.Add(pos.X); vboData.Add(pos.Y); vboData.Add(pos.Z); if (mesh.HasVertexColors(0)) { var colour = mesh.VertexColorChannels[0][i]; vboData.Add(colour.R); vboData.Add(colour.G); vboData.Add(colour.B); } var normal = mesh.Normals[i]; vboData.Add(normal.X); vboData.Add(normal.Y); vboData.Add(normal.Z); if (mesh.HasTangentBasis) { var tan = mesh.Tangents[i]; var bitan = mesh.BiTangents[i]; vboData.Add(tan.X); vboData.Add(tan.Y); vboData.Add(tan.Z); vboData.Add(bitan.X); vboData.Add(bitan.Y); vboData.Add(bitan.Z); } if (mesh.HasTextureCoords(0)) { var uv = mesh.TextureCoordinateChannels[0][i]; vboData.Add(uv.X); vboData.Add(uv.Y); } if (mesh.HasTextureCoords(1)) { var uv = mesh.TextureCoordinateChannels[1][i]; vboData.Add(uv.X); vboData.Add(uv.Y); } } return(true); }
public static Onyx3D.Mesh ToOnyx3D(this Assimp.Mesh mesh) { Onyx3D.Mesh newMesh = new Onyx3D.Mesh(); newMesh.Indices = mesh.GetIndices(); for (int vi = 0; vi < mesh.VertexCount; ++vi) { Vertex newVertex = new Vertex(); newVertex.Position = mesh.Vertices[vi].ToOnyx3D(); if (mesh.HasTextureCoords(0)) { Assimp.Vector3D texCoord = mesh.TextureCoordinateChannels[0][vi]; newVertex.TexCoord = texCoord.ToOnyx3D().Xy; } if (mesh.HasNormals) { newVertex.Normal = mesh.Normals[vi].ToOnyx3D().Normalized(); if (mesh.HasTangentBasis) { newVertex.Bitangent = mesh.BiTangents[vi].ToOnyx3D().Normalized(); newVertex.Tangent = mesh.Tangents[vi].ToOnyx3D().Normalized(); } } newMesh.Vertices.Add(newVertex); } newMesh.GenerateVAO(); return(newMesh); }
public void LoadModelVertices(Assimp.Mesh mesh, bool append = false) { var verts = new List <VertVNT>(); bool isTextured = mesh.HasTextureCoords(0); for (int i = 0; i < mesh.VertexCount; i++) { verts.Add(new VertVNT() { Position = mesh.Vertices[i].ToGL(), Normal = mesh.Normals[i].ToGL(), TexCoord = isTextured ? mesh.TextureCoordinateChannels[0][i].ToGL().Xy : Vector2.Zero }); } if (append) { AppendVertices(verts.Select(x => x.Cast <T>())); } else { SetVertices(verts.Select(x => x.Cast <T>())); } var indices = new List <int>(); int indexPerFace = mesh.Faces[0].IndexCount; foreach (var face in mesh.Faces) { if (face.IndexCount == indexPerFace) { indices.AddRange(face.Indices); } } if (append) { AppendIndices(indices); } else { SetIndices(indices); } }
static unsafe void ConvertGeom(float scale, uint offset, Assimp.Mesh mesh, out BoundingBox meshBoundingBox, VertexComponent[] vertexComponents) { meshBoundingBox = new BoundingBox(); for (int v = 0; v < mesh.VertexCount; v++) { foreach (var vc in vertexComponents) { switch (vc) { case VertexComponent.Position: var position = new vec3(mesh.Vertices[v].X, mesh.Vertices[v].Y, mesh.Vertices[v].Z) * scale; vertexBuffer.Add(position.x, 3); meshBoundingBox.Merge(position); break; case VertexComponent.Normal: var normal = new vec3(mesh.Normals[v].X, mesh.Normals[v].Y, mesh.Normals[v].Z); vertexBuffer.Add(normal.x, 3); break; case VertexComponent.Tangent: var tan = new vec3(mesh.Tangents[v].X, mesh.Tangents[v].Y, mesh.Tangents[v].Z); vertexBuffer.Add(tan.x, 3); break; case VertexComponent.Bitangent: var bitan = new vec3(mesh.BiTangents[v].X, mesh.BiTangents[v].Y, mesh.BiTangents[v].Z); vertexBuffer.Add(bitan.x, 3); break; case VertexComponent.Texcoord: vec2 texcoord = vec2.Zero; // Texture coordinates and colors may have multiple channels, we only use the first [0] one if (mesh.HasTextureCoords(0)) { texcoord = new vec2(mesh.TextureCoordinateChannels[0][v].X, mesh.TextureCoordinateChannels[0][v].Y); } vertexBuffer.Add(texcoord.x, 2); break; case VertexComponent.Color: uint color = 0xffffffff; if (mesh.VertexColorChannelCount > 0) { var c = mesh.VertexColorChannels[0][v]; color = (uint)(c.A * 255) << 24 | (uint)(c.B * 255) << 16 | (uint)(c.G * 255) << 8 | (uint)(c.R * 255); } vertexBuffer.Add(Unsafe.AsPointer(ref color), 1); break; } } } for (int f = 0; f < mesh.FaceCount; f++) { for (int i = 0; i < 3; i++) { indexBuffer.Add((uint)(offset + mesh.Faces[f].Indices[i])); } } }
private byte getFlags(Assimp.Mesh mesh) { const int Position = 0; //NOTE this must match the Mesh::Attribute enum of cro const int Colour = 1; const int Normal = 2; const int Tangent = 3; const int Bitangent = 4; const int UV0 = 5; const int UV1 = 6; byte flags = (1 << Position) | (1 << Normal); //append any messages to info label if (!mesh.HasVertices) { if (m_currentFlags == 0) { textBoxInfo.Text += Environment.NewLine + "No vertex positions found. File not written."; } return(0); } if (mesh.HasVertexColors(0)) { flags |= (1 << Colour); textBoxInfo.Text += Environment.NewLine + "Colour data found in vertices."; } if (!mesh.HasNormals) { if (m_currentFlags == 0) { textBoxInfo.Text += Environment.NewLine + "No normals found. File not written."; } return(0); } if (!mesh.HasTangentBasis) { if (m_currentFlags == 0) { textBoxInfo.Text += Environment.NewLine + "Mesh tangents were missing..."; } } else { flags |= (1 << Tangent) | (1 << Bitangent); } if (!mesh.HasTextureCoords(0)) { if (m_currentFlags == 0) { textBoxInfo.Text += Environment.NewLine + "Primary texture coords are missing, textures will appear undefined."; } } else { flags |= (1 << UV0); } if (!mesh.HasTextureCoords(1)) { if (m_currentFlags == 0) { textBoxInfo.Text += Environment.NewLine + "Secondary texture coords are missing, lightmapping will be unavailable for this mesh."; } } else { flags |= (1 << UV1); } return(flags); }
internal static Mesh FromAssimp(Assimp.Mesh mesh) { Mesh newMesh = new Mesh(); newMesh.Indices = mesh.GetUnsignedIndices(); bool hasTexCoords = mesh.HasTextureCoords(0); List <Assimp.Vector3D> uvs = hasTexCoords ? mesh.TextureCoordinateChannels[0] : null; // bounding box values float min_x, max_x, min_y, max_y, min_z, max_z; min_x = max_x = mesh.Vertices[0].X; min_y = max_y = mesh.Vertices[0].Y; min_z = max_z = mesh.Vertices[0].Z; Vertex[] vertices = new Vertex[mesh.VertexCount]; for (int i = 0; i < vertices.Length; i++) { Vector3 vec = mesh.Vertices[i].ToNumeric(); Vector3 norm = mesh.Normals[i].ToNumeric(); if (hasTexCoords) { Assimp.Vector3D uv = uvs[i]; vertices[i] = new Vertex(vec, new Vector2(uv.X, 1.0f - uv.Y), norm); } else { vertices[i] = new Vertex(vec, Vector2.Zero, norm); } if (vec.X < min_x) { min_x = vec.X; } if (vec.X > max_x) { max_x = vec.X; } if (vec.Y < min_y) { min_y = vec.Y; } if (vec.Y > max_y) { max_y = vec.Y; } if (vec.Z < min_z) { min_z = vec.Z; } if (vec.Z > max_z) { max_z = vec.Z; } } newMesh.BoundingBox = new BoundingBox(new Vector3(min_x, min_y, min_z), new Vector3(max_x, max_y, max_z)); newMesh.Vertices = vertices; return(newMesh); }
private bool ParseMeshData(Assimp.Scene scene) { if (!scene.HasMeshes) { return(false); } Assimp.Mesh[] meshes = scene.Meshes; if (meshes.Length == 0) { return(false); } m_meshData = new MeshData[meshes.Length]; m_meshMatInfo = new MeshMaterialInfo[meshes.Length]; for (int i = 0; i < meshes.Length; i++) { Assimp.Mesh mesh = meshes[i]; MeshData md = new MeshData(); MeshMaterialInfo info = new MeshMaterialInfo(); if (mesh.HasVertices) { Assimp.Vector3D[] assimpPos = mesh.Vertices; DataBuffer <Vector3> positions = new DataBuffer <Vector3>(assimpPos.Length); MemoryHelper.Copy(assimpPos, positions.Buffer, Vector3.SizeInBytes * assimpPos.Length); md.Positions = positions; } if (mesh.HasNormals) { Assimp.Vector3D[] assimpNorms = mesh.Normals; DataBuffer <Vector3> normals = new DataBuffer <Vector3>(assimpNorms.Length); MemoryHelper.Copy(assimpNorms, normals.Buffer, Vector3.SizeInBytes * assimpNorms.Length); md.Normals = normals; info.HasNormals = true; } if (mesh.HasTangentBasis) { Assimp.Vector3D[] assimpTangs = mesh.Tangents; Assimp.Vector3D[] assimpBitangs = mesh.BiTangents; DataBuffer <Vector3> tangents = new DataBuffer <Vector3>(assimpTangs.Length); DataBuffer <Vector3> bitangents = new DataBuffer <Vector3>(assimpBitangs.Length); MemoryHelper.Copy(assimpTangs, tangents.Buffer, Vector3.SizeInBytes * assimpTangs.Length); MemoryHelper.Copy(assimpBitangs, bitangents.Buffer, Vector3.SizeInBytes * assimpBitangs.Length); md.Tangents = tangents; md.Binormals = bitangents; info.HasTangentBasis = true; } if (mesh.HasVertexColors(0)) { Assimp.Color4D[] assimpColors = mesh.GetVertexColors(0); md.Colors = new DataBuffer <Color>(ConvertColors(assimpColors)); info.HasVertexColors = true; } if (mesh.HasTextureCoords(0)) { Assimp.Vector3D[] assimpUV = mesh.GetTextureCoords(0); md.TextureCoordinates = new DataBuffer <Vector2>(ConvertVectors(assimpUV)); info.HasTexCoords = true; } md.Indices = new DataBuffer <int>(mesh.GetIntIndices()); md.Reconstruct(); m_meshMatInfo[i] = info; m_meshData[i] = md; } ParseMaterials(scene); return(true); }
public static void AddAiMeshToAQP(AquaObject aqp, Assimp.Mesh mesh, Matrix4x4 nodeMat, float baseScale) { AquaObject.GenericTriangles genTris = new AquaObject.GenericTriangles(); genTris.name = mesh.Name; genTris.baseMeshNodeId = 0; genTris.baseMeshDummyId = -1; var ids = GetMeshIds(mesh.Name); if (ids.Count > 0) { genTris.baseMeshNodeId = ids[0]; if (ids.Count > 1) { genTris.baseMeshDummyId = ids[1]; } } //Iterate through faces to get face and vertex data for (int faceId = 0; faceId < mesh.FaceCount; faceId++) { var face = mesh.Faces[faceId]; var faceVerts = face.Indices; genTris.triList.Add(new Vector3(faceVerts[0], faceVerts[1], faceVerts[2])); genTris.matIdList.Add(mesh.MaterialIndex); AquaObject.VTXL faceVtxl = new AquaObject.VTXL(); foreach (var v in faceVerts) //Expects triangles, not quads or polygons { faceVtxl.rawFaceId.Add(faceId); faceVtxl.rawVertId.Add(v); var vertPos = new Vector3(mesh.Vertices[v].X, mesh.Vertices[v].Y, mesh.Vertices[v].Z); vertPos = Vector3.Transform(vertPos, nodeMat); vertPos = new Vector3(vertPos.X * baseScale, vertPos.Y * baseScale, vertPos.Z * baseScale); faceVtxl.vertPositions.Add(vertPos); if (mesh.HasNormals) { faceVtxl.vertNormals.Add(new Vector3(mesh.Normals[v].X * baseScale, mesh.Normals[v].Y * baseScale, mesh.Normals[v].Z * baseScale)); } if (mesh.HasVertexColors(0)) { var color = mesh.VertexColorChannels[0][v]; faceVtxl.vertColors.Add(new byte[] { floatToColor(color.B), floatToColor(color.G), floatToColor(color.R), floatToColor(color.A) }); } if (mesh.HasVertexColors(1)) { var color = mesh.VertexColorChannels[1][v]; faceVtxl.vertColor2s.Add(new byte[] { floatToColor(color.B), floatToColor(color.G), floatToColor(color.R), floatToColor(color.A) }); } if (mesh.HasTextureCoords(0)) { var uv = mesh.TextureCoordinateChannels[0][v]; faceVtxl.uv1List.Add(new Vector2(uv.X, -uv.Y)); } if (mesh.HasTextureCoords(1)) { var uv = mesh.TextureCoordinateChannels[1][v]; faceVtxl.uv2List.Add(new Vector2(uv.X, -uv.Y)); } if (mesh.HasTextureCoords(2)) { var uv = mesh.TextureCoordinateChannels[2][v]; faceVtxl.uv3List.Add(new Vector2(uv.X, -uv.Y)); } if (mesh.HasTextureCoords(3)) { var uv = mesh.TextureCoordinateChannels[3][v]; faceVtxl.uv4List.Add(new Vector2(uv.X, -uv.Y)); } if (mesh.HasTextureCoords(4)) { var uv = mesh.TextureCoordinateChannels[4][v]; faceVtxl.vert0x22.Add(new short[] { floatToShort(uv.X), floatToShort(uv.Y) }); } if (mesh.HasTextureCoords(5)) { var uv = mesh.TextureCoordinateChannels[5][v]; faceVtxl.vert0x23.Add(new short[] { floatToShort(uv.X), floatToShort(uv.Y) }); } if (mesh.HasTextureCoords(6)) { var uv = mesh.TextureCoordinateChannels[6][v]; faceVtxl.vert0x24.Add(new short[] { floatToShort(uv.X), floatToShort(uv.Y) }); } if (mesh.HasTextureCoords(7)) { var uv = mesh.TextureCoordinateChannels[7][v]; faceVtxl.vert0x25.Add(new short[] { floatToShort(uv.X), floatToShort(uv.Y) }); } //Bone weights and indices if (mesh.HasBones) { List <int> vertWeightIds = new List <int>(); List <float> vertWeights = new List <float>(); foreach (var bone in mesh.Bones) { var boneId = GetNodeNumber(bone.Name); foreach (var weight in bone.VertexWeights) { if (weight.VertexID == v) { vertWeightIds.Add(boneId); vertWeights.Add(weight.Weight); break; } } } faceVtxl.rawVertWeightIds.Add(vertWeightIds); faceVtxl.rawVertWeights.Add(vertWeights); } } genTris.faceVerts.Add(faceVtxl); } aqp.tempTris.Add(genTris); }
private static void AddAiMeshToPRM(PRMModel prm, ref int totalVerts, Assimp.Mesh aiMesh, Matrix4x4 nodeMat) { //Convert vertices for (int vertId = 0; vertId < aiMesh.VertexCount; vertId++) { PRMModel.PRMVert vert = new PRMModel.PRMVert(); var aiPos = aiMesh.Vertices[vertId]; var newPos = (new Vector3(aiPos.X, aiPos.Y, aiPos.Z)); vert.pos = Vector3.Transform(newPos, nodeMat) / 100; if (aiMesh.HasVertexColors(0)) { var aiColor = aiMesh.VertexColorChannels[0][vertId]; vert.color = new byte[] { (byte)(aiColor.B * 255), (byte)(aiColor.G * 255), (byte)(aiColor.R * 255), (byte)(aiColor.A * 255) }; } else { vert.color = new byte[4]; } if (aiMesh.HasNormals) { var aiNorm = aiMesh.Normals[vertId]; var normal = new Vector3(aiNorm.X, aiNorm.Y, aiNorm.Z); vert.normal = Vector3.TransformNormal(normal, nodeMat); } else { vert.normal = new Vector3(); } if (aiMesh.HasTextureCoords(0)) { var aiUV1 = aiMesh.TextureCoordinateChannels[0][vertId]; vert.uv1 = new Vector2(aiUV1.X, aiUV1.Y); } else { vert.uv1 = new Vector2(); } if (aiMesh.HasTextureCoords(1)) { var aiUV2 = aiMesh.TextureCoordinateChannels[1][vertId]; vert.uv2 = new Vector2(aiUV2.X, aiUV2.Y); } else { vert.uv2 = new Vector2(); } prm.vertices.Add(vert); } //Convert Faces foreach (var aiFace in aiMesh.Faces) { prm.faces.Add(new Vector3(aiFace.Indices[0] + totalVerts, aiFace.Indices[1] + totalVerts, aiFace.Indices[2] + totalVerts)); } //Keep count up to date for next potential loop totalVerts = prm.vertices.Count; }