public MaterialInfoWithFaces(SSWavefrontMTLInfo sourceMtl)
 {
     mtl = sourceMtl;
 }
        /// <summary>
        /// This method is used to load information stored in .mtl files referenced by the .obj file.
        /// </summary>
        /// <param name="d3ddevice"></param>
        /// <param name="file"></param>

        private void parseOBJ(SSAssetManager.Context ctx, string filename)
        {
            MaterialInfoWithFaces currentMaterial = null;

            StreamReader sr = ctx.OpenText(filename);

            //Read the first line of text
            string line = sr.ReadLine();

            //Continue to read until you reach end of file
            while (line != null)
            {
                string[] tokens = line.Split(" ".ToArray(), 2);
                if (tokens.Length < 2)
                {
                    goto next_line;
                }

                string firstToken  = tokens[0];
                string lineContent = tokens[1];

                switch (firstToken)
                {
                case "#":       // Nothing to read, these are comments.
                    break;

                case "v":       // Vertex position
                    positions.Add(WavefrontParser.readVector4(lineContent, null));
                    break;

                case "vn":      // vertex normal direction vector
                    normals.Add(WavefrontParser.readVector3(lineContent, null));
                    break;

                case "vt":      // Vertex texcoordinate
                    texCoords.Add(WavefrontParser.readVector2(lineContent, null));
                    break;

                case "f":       // Face
                    string[] values    = WavefrontParser.FilteredSplit(lineContent, null);
                    int      numPoints = values.Length;

                    Face face = new Face();
                    face.v_idx   = new Int16[numPoints];
                    face.n_idx   = new Int16[numPoints];
                    face.tex_idx = new Int16[numPoints];      // todo: how do outside clients know if there were texcoords or not?!?!

                    for (int i = 0; i < numPoints; i++)
                    {
                        // format is "loc_index[/tex_index[/normal_index]]"  e.g. 3 ; 3/2 ; 3/2/5
                        // but middle part can me empty, e.g. 3//5
                        string[] indexes = values[i].Split('/');

                        int iPosition = (int.Parse(indexes[0]) - 1);      // adjust 1-based index
                        if (iPosition < 0)
                        {
                            iPosition += positions.Count + 1;
                        }                                                            // adjust negative indicies
                        face.v_idx[i] = (Int16)iPosition;
                        numIndices++;

                        // initialize other indicies to not provided, in case they are missing
                        face.n_idx[i]   = -1;
                        face.tex_idx[i] = -1;

                        if (indexes.Length > 1)
                        {
                            string tex_index = indexes[1];
                            if (tex_index != "")
                            {
                                int iTexCoord = int.Parse(tex_index) - 1;     // adjust 1-based index
                                if (iTexCoord < 0)
                                {
                                    iTexCoord += texCoords.Count + 1;
                                }                                                             // adjust negative indicies

                                face.tex_idx[i] = (Int16)iTexCoord;
                            }

                            if (indexes.Length > 2)
                            {
                                hasNormals = true;
                                int iNormal = int.Parse(indexes[2]) - 1;     // adjust 1 based index
                                if (iNormal < 0)
                                {
                                    iNormal += normals.Count + 1;
                                }                                                      // adjust negative indicies

                                face.n_idx[i] = (Int16)iNormal;
                            }
                        }
                    }
                    if (currentMaterial == null)
                    {
                        // no material in file, so create one
                        currentMaterial = createImplicitMaterial();
                    }
                    currentMaterial.faces.Add(face);
                    currentMaterial.nbrIndices += face.v_idx.Length;
                    numFaces++;
                    break;

                case "mtllib":      // load named material file
                    string mtlFile = lineContent;
                    {
                        var mtls = SSWavefrontMTLInfo.ReadMTLs(ctx, mtlFile);
                        foreach (var mtl in mtls)
                        {
                            materials.Add(new MaterialInfoWithFaces(mtl));
                        }
                    }
                    break;

                case "usemtl":      // use named material (from material file previously loaded)
                    bool found = false;

                    string matName = lineContent;

                    for (int i = 0; i < materials.Count; i++)
                    {
                        if (matName.Equals(materials[i].mtl.name))
                        {
                            found           = true;
                            currentMaterial = materials[i];
                        }
                    }

                    if (!found)
                    {
                        throw new WavefrontObjParseException("Materials are already loaded so we should have it!");
                    }
                    break;
                }

next_line:
                //Read the next line
                line = sr.ReadLine();
            }

            //close the file
            sr.Close();
        }