protected void ProcessNormalsPerVertex(PointerToVertex[] pointersToVertex, int verticesCount)
 {
     Vector3D[] normalsPerVertex = new Vector3D[verticesCount];
     for (int i = 0; i < this.triangles.Length; i++) {
         normalsPerVertex[pointersToVertex[i].Vertex1 - 1] += this.triangles[i].Normal;
         normalsPerVertex[pointersToVertex[i].Vertex2 - 1] += this.triangles[i].Normal;
         normalsPerVertex[pointersToVertex[i].Vertex3 - 1] += this.triangles[i].Normal;
         int percent = (int) (i * 100 / this.triangles.Length);
         if ((percent % 5) == 0) {
             this.OnElementLoaded((int) ((i * 100 / this.triangles.Length * 0.5)), ElementMesh.VertexNormal);
         }
     }
     for (int i = 0; i < this.triangles.Length; i++) {
         this.triangles[i].NormalOnVertex1 = normalsPerVertex[pointersToVertex[i].Vertex1 - 1];
         this.triangles[i].NormalOnVertex1.Normalize();
         this.triangles[i].NormalOnVertex2 = normalsPerVertex[pointersToVertex[i].Vertex2 - 1];
         this.triangles[i].NormalOnVertex2.Normalize();
         this.triangles[i].NormalOnVertex3 = normalsPerVertex[pointersToVertex[i].Vertex3 - 1];
         this.triangles[i].NormalOnVertex3.Normalize();
         int percent = (int) (i * 100 / this.triangles.Length);
         if ((percent % 5) == 0) {
             this.OnElementLoaded(50 + (int) ((i * 100 / this.triangles.Length * 0.5)), ElementMesh.VertexNormal);
         }
     }
     normalsPerVertex = null;
     //for (int i = 0; i < this.triangles.Length; i++) {
     //    this.triangles[i].NormalOnVertex1 = this.normalsPerVertex[this.pointersToVertex[i].Vertex1];
     //    this.triangles[i].NormalOnVertex2 = this.normalsPerVertex[this.pointersToVertex[i].Vertex2];
     //    this.triangles[i].NormalOnVertex3 = this.normalsPerVertex[this.pointersToVertex[i].Vertex3];
     //}
 }
        private void ParserByuModel()
        {
            Point3D[]         vertices;
            PointerToVertex[] pointersToVertex;
            NumberFormatInfo  nfi = new NumberFormatInfo();

            nfi.NumberDecimalSeparator = ".";
            nfi.NumberGroupSeparator   = ",";
            using (this.sr = new StreamReader(this.path)) {
                string[] str = this.sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                vertices         = new Point3D[Convert.ToInt32(str[0])];
                this.triangles   = new Triangle[Convert.ToInt32(str[1])];
                pointersToVertex = new PointerToVertex[this.triangles.Length];
                Point3D pmin, pmax;
                pmin          = pmax = Point3D.Zero;
                this.BoundBox = new BoundBox(pmin, pmax);
                for (int i = 0; i < vertices.Length; i++)
                {
                    str         = this.sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                    vertices[i] = new Point3D(float.Parse(str[0], nfi), float.Parse(str[1], nfi),
                                              float.Parse(str[2], nfi));
                    //pmin = this.boundBox.PMin;
                    //pmin.X = vertices[i].X < pmin.X ? vertices[i].X : pmin.X;
                    //pmin.Y = vertices[i].Y < pmin.Y ? vertices[i].Y : pmin.Y;
                    //pmin.Z = vertices[i].Z < pmin.Z ? vertices[i].Z : pmin.Z;
                    //pmax = this.boundBox.PMax;
                    //pmax.X = vertices[i].X > pmax.X ? vertices[i].X : pmax.X;
                    //pmax.Y = vertices[i].Y > pmax.Y ? vertices[i].Y : pmax.Y;
                    //pmax.Z = vertices[i].Z > pmax.Z ? vertices[i].Z : pmax.Z;
                    //this.boundBox.PMin = pmin;
                    //this.boundBox.PMax = pmax;
                    this.BoundBox.Include(vertices[i]);
                    int percent = (int)(i * 100 / vertices.Length);
                    if ((percent % 20) == 0)
                    {
                        this.OnElementLoaded((int)((i * 100 / vertices.Length)), ElementMesh.Vertex);
                    }
                }
                for (int i = 0; i < this.triangles.Length; i++)
                {
                    str = this.sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                    pointersToVertex[i] = new PointerToVertex(Convert.ToInt32(str[0]) - 1, Convert.ToInt32(str[1]) - 1,
                                                              Convert.ToInt32(str[2]) - 1);
                    this.triangles[i] = new Triangle(vertices[pointersToVertex[i].Vertex1],
                                                     vertices[pointersToVertex[i].Vertex2],
                                                     vertices[pointersToVertex[i].Vertex3]);
                    int percent = i * 100 / this.triangles.Length;
                    if ((percent % 20) == 0)
                    {
                        this.OnElementLoaded(i * 100 / this.triangles.Length, ElementMesh.Triangle);
                    }
                }
                this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);
                vertices         = null;
                pointersToVertex = null;
                GC.Collect();
            }
        }
        private void ParserASCII(PlyObjectHeader header, String content)
        {
            StringReader sr = new StringReader(content);


            Point3D[]         vertices         = new Point3D[header.Elements["vertex"].Count];
            PointerToVertex[] pointersToVertex = new PointerToVertex[header.Elements["face"].Count];
            //int headerLength = header.Count + 1;
            //while (sr.ReadLine().ToLower() != "end_header") { } //Pass header...
            NumberFormatInfo nfi = new NumberFormatInfo();

            nfi.NumberDecimalSeparator = ".";
            nfi.NumberGroupSeparator   = ",";
            String[] str;

            //for number of vertices readed in header do...
            for (int i = 0; i < vertices.Length; i++)
            {
                str         = sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                vertices[i] = new Point3D(float.Parse(str[0], nfi), float.Parse(str[1], nfi), float.Parse(str[2], nfi));
                //Adjusting BoundBox...
                this.BoundBox.Include(vertices[i]);
                //Reporting progress
                int percent = (int)(((float)i / vertices.Length) * 100.0f);
                if ((percent % 20) == 0)
                {
                    this.OnElementLoaded(percent, ElementMesh.Vertex);
                }
            }

            for (int i = 0; i < this.triangles.Length; i++)
            {
                str = sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                pointersToVertex[i] = new PointerToVertex(Int32.Parse(str[1], nfi), Int32.Parse(str[2], nfi),
                                                          Int32.Parse(str[3], nfi));
                this.triangles[i] = new Triangle(vertices[pointersToVertex[i].Vertex1],
                                                 vertices[pointersToVertex[i].Vertex2],
                                                 vertices[pointersToVertex[i].Vertex3]);
                int percent = (int)(((float)i / this.triangles.Length) * 100.0f);
                if ((percent % 20) == 0)
                {
                    this.OnElementLoaded(percent, ElementMesh.Triangle);
                }
            }
            //System.Windows.Forms.MessageBox.Show("Degenerate Triangles: " + RemoveDegenerateTriangles(ref pointersToVertex));
            //RemoveUnusedVertices(ref vertices, pointersToVertex);

            this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);

            vertices         = null;
            pointersToVertex = null;
            GC.Collect();
            GC.WaitForPendingFinalizers();
        }
        private void ParserASCII(PlyObjectHeader header, Stream sr)
        {
            Point3D[]         vertices         = new Point3D[header.Elements["vertex"].Count];;
            PointerToVertex[] pointersToVertex = new PointerToVertex[header.Elements["face"].Count];
            //int headerLength = header.Count + 1;
            //while (sr.ReadLine().ToLower() != "end_header") { } //Pass header...
            NumberFormatInfo nfi = new NumberFormatInfo();

            nfi.NumberDecimalSeparator = ".";
            nfi.NumberGroupSeparator   = ",";
            //Initialize bound box calculation
            Point3D pmin, pmax;

            pmin          = pmax = Point3D.Zero;
            this.boundBox = new BoundBox();
            String[] str;
            //for number of vertices readed in header do...
            for (int i = 0; i < vertices.Length; i++)
            {
                str         = sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                vertices[i] = new Point3D(float.Parse(str[0], nfi), float.Parse(str[1], nfi),
                                          float.Parse(str[2], nfi));
                //Adjusting BoundBox...
                this.boundBox.Include(vertices[i]);
                //Reporting progress
                int percent = (int)(((float)i / vertices.Length) * 100.0f);
                if ((percent % 20) == 0)
                {
                    this.OnElementLoaded(percent, ElementMesh.Vertex);
                }
            }
            for (int i = 0; i < this.triangles.Length; i++)
            {
                str = sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                pointersToVertex[i] = new PointerToVertex(Int32.Parse(str[1], nfi), Int32.Parse(str[2], nfi),
                                                          Int32.Parse(str[3], nfi));
                this.triangles[i] = new Triangle(vertices[pointersToVertex[i].Vertex1],
                                                 vertices[pointersToVertex[i].Vertex2],
                                                 vertices[pointersToVertex[i].Vertex3]);
                int percent = (int)(((float)i / this.triangles.Length) * 100.0f);
                if ((percent % 20) == 0)
                {
                    this.OnElementLoaded(percent, ElementMesh.Triangle);
                }
            }
            this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);
            vertices         = null;
            pointersToVertex = null;
            GC.Collect();
        }
 private void ParserByuModel()
 {
     Point3D[] vertices;
     PointerToVertex[] pointersToVertex;
     NumberFormatInfo nfi = new NumberFormatInfo();
     nfi.NumberDecimalSeparator = ".";
     nfi.NumberGroupSeparator = ",";
     using (this.sr = new StreamReader(this.path)) {
         string[] str = this.sr.ReadLine().Split(new char[] {' '}, StringSplitOptions.RemoveEmptyEntries);
         vertices = new Point3D[Convert.ToInt32(str[0])];
         this.triangles = new Triangle[Convert.ToInt32(str[1])];
         pointersToVertex = new PointerToVertex[this.triangles.Length];
         Point3D pmin, pmax;
         pmin = pmax = Point3D.Zero;
         this.BoundBox = new BoundBox(pmin, pmax);
         for (int i = 0; i < vertices.Length; i++) {
             str = this.sr.ReadLine().Split(new char[] {' '}, StringSplitOptions.RemoveEmptyEntries);
             vertices[i] = new Point3D(float.Parse(str[0], nfi), float.Parse(str[1], nfi),
                                       float.Parse(str[2], nfi));
             //pmin = this.boundBox.PMin;
             //pmin.X = vertices[i].X < pmin.X ? vertices[i].X : pmin.X;
             //pmin.Y = vertices[i].Y < pmin.Y ? vertices[i].Y : pmin.Y;
             //pmin.Z = vertices[i].Z < pmin.Z ? vertices[i].Z : pmin.Z;
             //pmax = this.boundBox.PMax;
             //pmax.X = vertices[i].X > pmax.X ? vertices[i].X : pmax.X;
             //pmax.Y = vertices[i].Y > pmax.Y ? vertices[i].Y : pmax.Y;
             //pmax.Z = vertices[i].Z > pmax.Z ? vertices[i].Z : pmax.Z;
             //this.boundBox.PMin = pmin;
             //this.boundBox.PMax = pmax;
             this.BoundBox.Include(vertices[i]);
             int percent = (int) (i * 100 / vertices.Length);
             if ((percent % 20) == 0) {
                 this.OnElementLoaded((int) ((i * 100 / vertices.Length)), ElementMesh.Vertex);
             }
         }
         for (int i = 0; i < this.triangles.Length; i++) {
             str = this.sr.ReadLine().Split(new char[] {' '}, StringSplitOptions.RemoveEmptyEntries);
             pointersToVertex[i] = new PointerToVertex(Convert.ToInt32(str[0]) - 1, Convert.ToInt32(str[1]) - 1,
                                                       Convert.ToInt32(str[2]) - 1);
             this.triangles[i] = new Triangle(vertices[pointersToVertex[i].Vertex1],
                                              vertices[pointersToVertex[i].Vertex2],
                                              vertices[pointersToVertex[i].Vertex3]);
             int percent = i * 100 / this.triangles.Length;
             if ((percent % 20) == 0) {
                 this.OnElementLoaded(i * 100 / this.triangles.Length, ElementMesh.Triangle);
             }
         }
         this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);
         vertices = null;
         pointersToVertex = null;
         GC.Collect();
     }
 }
        private void ParserBinary(PlyObjectHeader header, BinaryReader ebr)
        {
            Point3D[]         vertices         = new Point3D[header.Elements["vertex"].Count];
            PointerToVertex[] pointersToVertex = new PointerToVertex[header.Elements["face"].Count];
            for (int i = 0; i < header.Elements.Count; i++)
            {
                ElementDescription element = header.Elements[i];
                for (int e = 0; e < element.Count; e++)
                {
                    for (int p = 0; p < element.Properties.Count; p++)
                    {
                        PropertyDescription property = element.Properties[p];
                        if (property.IsList)
                        {
                            int listCount = 0;
                            if (property.CountType == PropertyType.uchar || property.CountType == PropertyType.uint8)
                            {
                                listCount = ebr.ReadByte();
                            }
                            else
                            {
                                throw new ArgumentException(
                                          "The type expected for List Count is 'uchar'. Type in file: '" + property.CountType +
                                          "'");
                            }

                            if (property.TypeOfList == PropertyType.@int || property.TypeOfList == PropertyType.int32)
                            {
                                if (element.Name == "face")
                                {
                                    for (int j = 0; j < listCount; j += 3)
                                    {
                                        pointersToVertex[e].Vertex1 = ebr.ReadInt32();
                                        pointersToVertex[e].Vertex2 = ebr.ReadInt32();
                                        pointersToVertex[e].Vertex3 = ebr.ReadInt32();

                                        this.triangles[e] = new Triangle(vertices[pointersToVertex[e].Vertex1],
                                                                         vertices[pointersToVertex[e].Vertex2],
                                                                         vertices[pointersToVertex[e].Vertex3]);


                                        int percent = (int)(((float)e / this.triangles.Length) * 100.0f);
                                        if ((percent % 20) == 0)
                                        {
                                            this.OnElementLoaded(percent, ElementMesh.Triangle);
                                        }
                                    }
                                }
                                else if (element.Name == "vertex")
                                {
                                    #region Ignore other properties for vertex

                                    //for (int j = 0; j < listCount; j += 3)
                                    //{
                                    //    ebr.ReadInt32();
                                    //    ebr.ReadInt32();
                                    //    ebr.ReadInt32();
                                    //}

                                    #endregion

                                    ebr.ReadBytes(element.Properties.SumTypesLength);
                                    break;
                                }
                            }
                            else
                            {
                                throw new ArgumentException(
                                          "The type expected for List elements is 'int'. Type in file: '" +
                                          property.TypeOfList + "'");
                            }
                        }
                        else
                        {
                            if (element.Name == "face")
                            {
                                ebr.ReadBytes(element.Properties.SumTypesLength);
                                break;
                            }
                            else if (element.Name == "vertex")
                            {
                                if (property.Name.ToLowerInvariant() == "x")
                                {
                                    vertices[e].X = ebr.ReadSingle();
                                    vertices[e].Y = ebr.ReadSingle();
                                    vertices[e].Z = ebr.ReadSingle();
                                    p            += (2 + element.Properties.Count - p);
                                    ebr.ReadBytes(element.Properties.SumTypesLength - 12);
                                    //Adjusting BoundBox...
                                    this.BoundBox.Include(vertices[e]);
                                    //Reporting progress
                                    int percent = (int)(((float)e / vertices.Length) * 100.0f);
                                    if ((percent % 20) == 0)
                                    {
                                        this.OnElementLoaded(percent, ElementMesh.Vertex);
                                    }
                                }

                                #region Antigo

                                //switch (property.Type)
                                //{
                                //    case PropertyType.@char:
                                //    case PropertyType.int8:
                                //        ebr.ReadSByte();
                                //        break;
                                //    case PropertyType.uchar:
                                //    case PropertyType.uint8:
                                //        ebr.ReadByte();
                                //        break;
                                //    case PropertyType.@short:
                                //    case PropertyType.int16:
                                //        ebr.ReadInt16();
                                //        break;
                                //    case PropertyType.@ushort:
                                //    case PropertyType.uint16:
                                //        ebr.ReadUInt16();
                                //        break;
                                //    case PropertyType.@int:
                                //    case PropertyType.int32:
                                //        ebr.ReadInt32();
                                //        break;
                                //    case PropertyType.@uint:
                                //    case PropertyType.uint32:
                                //        ebr.ReadUInt32();
                                //        break;
                                //    case PropertyType.@float:
                                //    case PropertyType.float32:
                                //        vertices[e].X = ebr.ReadSingle();
                                //        vertices[e].Y = ebr.ReadSingle();
                                //        vertices[e].Z = ebr.ReadSingle();
                                //        p += 2;
                                //        //Adjusting BoundBox...
                                //        this.BoundBox.Include(vertices[e]);
                                //        //Reporting progress
                                //        int percent = (int)(((float)e / vertices.Length) * 100.0f);
                                //        if ((percent % 20) == 0)
                                //        {
                                //            this.OnElementLoaded(percent, ElementMesh.Vertex);
                                //        }
                                //        break;
                                //    case PropertyType.@double:
                                //    case PropertyType.float64:
                                //        ebr.ReadDouble();
                                //        break;
                                //    default:
                                //        break;
                                //}

                                #endregion
                            }
                        }
                    }
                }
            }
            this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);
            vertices         = null;
            pointersToVertex = null;
            GC.Collect();
            GC.WaitForPendingFinalizers();
        }
Beispiel #7
0
        private void ParserOffModel()
        {
            Point3D[]         vertices;
            Vector3D[]        vertexNormals;
            PointerToVertex[] pointersToVertex;
            NumberFormatInfo  nfi = new NumberFormatInfo();

            nfi.NumberDecimalSeparator = ".";
            nfi.NumberGroupSeparator   = ",";
            String[] line;
            char[]   separator = new char[] { ' ' };
            Point3D  p = Point3D.Zero;
            Point3D  pmin = Point3D.Zero, pmax = Point3D.Zero;
            bool     hasNormals = false;

            using (StreamReader sr = new StreamReader(this.path)){
                string header = sr.ReadLine().ToUpper(); //read header (OFF)
                while (String.IsNullOrEmpty(header))
                {
                    header = sr.ReadLine().ToUpper(); //read header (OFF)
                }
                if (header.EndsWith("OFF"))
                {
                    if (header.EndsWith("NOFF"))
                    {
                        hasNormals = true;
                    }
                }
                line = sr.ReadLine().Split(separator, StringSplitOptions.RemoveEmptyEntries);
                while (line.Length == 0)
                {
                    line = sr.ReadLine().Split(separator, StringSplitOptions.RemoveEmptyEntries);
                }
                vertices         = new Point3D[int.Parse(line[0], nfi)];
                this.triangles   = new Triangle[int.Parse(line[1], nfi)];
                vertexNormals    = new Vector3D[vertices.Length];
                pointersToVertex = new PointerToVertex[this.triangles.Length];
                //while (!sr.EndOfStream)
                //{
                int percent = 0;
                for (int i = 0; i < vertices.Length; i++)
                {
                    line = sr.ReadLine().Split(separator, StringSplitOptions.RemoveEmptyEntries);
                    if (line.Length == 0)
                    {
                        i--;
                        continue;
                    }
                    vertices[i].X = float.Parse(line[0], nfi);
                    vertices[i].Y = float.Parse(line[1], nfi);
                    vertices[i].Z = float.Parse(line[2], nfi);
                    //Adjusting BoundBox...
                    this.boundBox.Include(vertices[i]);
                    //Reporting progress
                    percent = (int)(((float)i / vertices.Length) * 100.0f);
                    if ((percent % 20) == 0)
                    {
                        this.OnElementLoaded(percent, ElementMesh.Vertex);
                    }
                    if (hasNormals)
                    {
                        vertexNormals[i].X = float.Parse(line[3], nfi);
                        vertexNormals[i].Y = float.Parse(line[4], nfi);
                        vertexNormals[i].Z = float.Parse(line[5], nfi);
                        percent            = (int)(((float)i / vertices.Length) * 100.0f);
                        if ((percent % 20) == 0)
                        {
                            this.OnElementLoaded(percent, ElementMesh.VertexNormal);
                        }
                    }
                }
                for (int i = 0; i < this.triangles.Length; i++)
                {
                    line = sr.ReadLine().Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                    pointersToVertex[i] = new PointerToVertex(Int32.Parse(line[1], nfi), Int32.Parse(line[2], nfi),
                                                              Int32.Parse(line[3], nfi));
                    this.triangles[i] = new Triangle(vertices[pointersToVertex[i].Vertex1],
                                                     vertices[pointersToVertex[i].Vertex2],
                                                     vertices[pointersToVertex[i].Vertex3]);
                    percent = (int)(((float)i / this.triangles.Length) * 100.0f);
                    if ((percent % 20) == 0)
                    {
                        this.OnElementLoaded(percent, ElementMesh.Triangle);
                    }
                }
            }
            if (!hasNormals)
            {
                this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);
            }
            Array.Clear(vertices, 0, vertices.Length);
            Array.Clear(vertexNormals, 0, vertexNormals.Length);
            vertices = null;
            GC.Collect();
        }
        private void ParserOffModel()
        {
            Point3D[] vertices;
            Vector3D[] vertexNormals = null;
            PointerToVertex[] pointersToVertex;
            NumberFormatInfo nfi = new NumberFormatInfo();
            nfi.NumberDecimalSeparator = ".";
            nfi.NumberGroupSeparator = ",";
            String[] line;
            char[] separator = new char[] {' '};
            bool hasNormals = false;

            using (StreamReader sr = new StreamReader(this.path)) {
                string header = sr.ReadLine().ToUpper(); //read header (OFF)
                while (String.IsNullOrEmpty(header)) {
                    header = sr.ReadLine().ToUpper(); //read header (OFF)
                }
                if (header.EndsWith("OFF")) {
                    if (header.EndsWith("NOFF")) {
                        hasNormals = true;
                    }
                }
                line = sr.ReadLine().Split(separator, StringSplitOptions.RemoveEmptyEntries);
                while (line.Length == 0) {
                    line = sr.ReadLine().Split(separator, StringSplitOptions.RemoveEmptyEntries);
                }
                vertices = new Point3D[int.Parse(line[0], nfi)];
                this.triangles = new Triangle[int.Parse(line[1], nfi)];
                pointersToVertex = new PointerToVertex[this.triangles.Length];
                if (hasNormals) {
                    vertexNormals = new Vector3D[vertices.Length];
                }
                int percent = 0;
                for (int i = 0; i < vertices.Length; i++) {
                    line = sr.ReadLine().Split(separator, StringSplitOptions.RemoveEmptyEntries);
                    if (line.Length == 0) {
                        i--;
                        continue;
                    }
                    vertices[i].X = float.Parse(line[0], nfi);
                    vertices[i].Y = float.Parse(line[1], nfi);
                    vertices[i].Z = float.Parse(line[2], nfi);
                    //Adjusting BoundBox...
                    this.BoundBox.Include(vertices[i]);
                    //Reporting progress
                    percent = (int) (((float) i / vertices.Length) * 100.0f);
                    if ((percent % 10) == 0) {
                        this.OnElementLoaded(percent, ElementMesh.Vertex);
                    }
                    if (hasNormals) {
                        vertexNormals[i].X = float.Parse(line[3], nfi);
                        vertexNormals[i].Y = float.Parse(line[4], nfi);
                        vertexNormals[i].Z = float.Parse(line[5], nfi);
                        percent = (int) (((float) i / vertices.Length) * 100.0f);
                        if ((percent % 10) == 0) {
                            this.OnElementLoaded(percent, ElementMesh.VertexNormal);
                        }
                    }
                }
                for (int i = 0; i < this.triangles.Length; i++) {
                    line = sr.ReadLine().Split(new char[] {' '}, StringSplitOptions.RemoveEmptyEntries);
                    pointersToVertex[i] = new PointerToVertex(Int32.Parse(line[1], nfi), Int32.Parse(line[2], nfi),
                                                              Int32.Parse(line[3], nfi));
                    this.triangles[i] = new Triangle(vertices[pointersToVertex[i].Vertex1],
                                                     vertices[pointersToVertex[i].Vertex2],
                                                     vertices[pointersToVertex[i].Vertex3]);
                    percent = (int) (((float) i / this.triangles.Length) * 100.0f);
                    if ((percent % 10) == 0) {
                        this.OnElementLoaded(percent, ElementMesh.Triangle);
                    }
                }
            }
            if (!hasNormals) {
                this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);
            }
            vertices = null;
            vertexNormals = null;
            GC.Collect();
            GC.WaitForPendingFinalizers();
        }
 private void ProcessNormalsPerVertex(PointerToVertex[] pointersToVertex, int verticesCount)
 {
     Vector3D[] normalsPerVertex = new Vector3D[verticesCount];
     for (int i = 0; i < this.triangles.Length; i++) {
         normalsPerVertex[pointersToVertex[i].Vertex1] += this.triangles[i].Normal;
         normalsPerVertex[pointersToVertex[i].Vertex2] += this.triangles[i].Normal;
         normalsPerVertex[pointersToVertex[i].Vertex3] += this.triangles[i].Normal;
         int percent = (int) (((float) i / this.triangles.Length) * 100.0f);
         if ((percent % 20) == 0) {
             this.OnElementLoaded(percent / 2, ElementMesh.VertexNormal);
         }
     }
     for (int i = 0; i < this.triangles.Length; i++) {
         this.triangles[i].NormalOnVertex1 = normalsPerVertex[pointersToVertex[i].Vertex1];
         this.triangles[i].NormalOnVertex1.Normalize();
         this.triangles[i].NormalOnVertex2 = normalsPerVertex[pointersToVertex[i].Vertex2];
         this.triangles[i].NormalOnVertex2.Normalize();
         this.triangles[i].NormalOnVertex3 = normalsPerVertex[pointersToVertex[i].Vertex3];
         this.triangles[i].NormalOnVertex3.Normalize();
         int percent = (int) (( i / (float)this.triangles.Length) * 100.0f);
         if ((percent % 20) == 0) {
             this.OnElementLoaded((percent / 2) + 50, ElementMesh.VertexNormal);
         }
     }
     pointersToVertex = null;
     normalsPerVertex = null;
     GC.Collect();
     GC.WaitForPendingFinalizers();
 }
        private void ParserBinary(PlyObjectHeader header, BinaryReader ebr)
        {
            Point3D[]         vertices         = new Point3D[header.Elements["vertex"].Count];;
            PointerToVertex[] pointersToVertex = new PointerToVertex[header.Elements["face"].Count];
            //Initialize bound box calculation
            Point3D pmin, pmax;

            pmin          = pmax = Point3D.Zero;
            this.boundBox = new BoundBox();
            for (int i = 0; i < header.Elements.Count; i++)
            {
                ElementDescription element = header.Elements[i];
                for (int e = 0; e < element.Count; e++)
                {
                    for (int p = 0; p < element.Properties.Count; p++)
                    {
                        PropertyDescription property = element.Properties[p];

                        if (property.IsList)
                        {
                            int listCount = 0;
                            if (property.CountType == PropertyType.uchar || property.CountType == PropertyType.uint8)
                            {
                                listCount = ebr.ReadByte();
                            }
                            else
                            {
                                throw new ArgumentException("The type expected for List Count is 'uchar'. Type in file: '" + property.CountType + "'");
                            }

                            if (property.TypeOfList == PropertyType.@int || property.TypeOfList == PropertyType.int32)
                            {
                                if (element.Name == "face")
                                {
                                    for (int j = 0; j < listCount; j += 3)
                                    {
                                        pointersToVertex[e].Vertex1 = ebr.ReadInt32();
                                        pointersToVertex[e].Vertex2 = ebr.ReadInt32();
                                        pointersToVertex[e].Vertex3 = ebr.ReadInt32();

                                        this.triangles[e] = new Triangle(vertices[pointersToVertex[e].Vertex1],
                                                                         vertices[pointersToVertex[e].Vertex2],
                                                                         vertices[pointersToVertex[e].Vertex3]);

                                        int percent = (int)(((float)e / this.triangles.Length) * 100.0f);
                                        if ((percent % 20) == 0)
                                        {
                                            this.OnElementLoaded(percent, ElementMesh.Triangle);
                                        }
                                    }
                                }
                                else if (element.Name == "vertex")
                                {
                                    #region Ignore other properties for vertex
                                    for (int j = 0; j < listCount; j += 3)
                                    {
                                        ebr.ReadInt32();
                                        ebr.ReadInt32();
                                        ebr.ReadInt32();
                                    }
                                    #endregion
                                }
                            }
                            else
                            {
                                throw new ArgumentException("The type expected for List elements is 'int'. Type in file: '" + property.TypeOfList + "'");
                            }
                        }
                        else
                        {
                            if (element.Name == "face")
                            {
                                #region Ignore other properties for face
                                switch (property.Type)
                                {
                                case PropertyType.@char:
                                case PropertyType.int8:
                                    ebr.ReadSByte();
                                    break;

                                case PropertyType.uchar:
                                case PropertyType.uint8:
                                    ebr.ReadByte();
                                    break;

                                case PropertyType.@short:
                                case PropertyType.int16:
                                    ebr.ReadInt16();
                                    break;

                                case PropertyType.@ushort:
                                case PropertyType.uint16:
                                    ebr.ReadUInt16();
                                    break;

                                case PropertyType.@int:
                                case PropertyType.int32:
                                    ebr.ReadInt32();
                                    break;

                                case PropertyType.@uint:
                                case PropertyType.uint32:
                                    ebr.ReadUInt32();
                                    break;

                                case PropertyType.@float:
                                case PropertyType.float32:
                                    ebr.ReadSingle();
                                    break;

                                case PropertyType.@double:
                                case PropertyType.float64:
                                    ebr.ReadDouble();
                                    break;

                                default:
                                    break;
                                }
                                #endregion
                            }
                            else if (element.Name == "vertex")
                            {
                                switch (property.Type)
                                {
                                case PropertyType.@char:
                                case PropertyType.int8:
                                    ebr.ReadSByte();
                                    break;

                                case PropertyType.uchar:
                                case PropertyType.uint8:
                                    ebr.ReadByte();
                                    break;

                                case PropertyType.@short:
                                case PropertyType.int16:
                                    ebr.ReadInt16();
                                    break;

                                case PropertyType.@ushort:
                                case PropertyType.uint16:
                                    ebr.ReadUInt16();
                                    break;

                                case PropertyType.@int:
                                case PropertyType.int32:
                                    ebr.ReadInt32();
                                    break;

                                case PropertyType.@uint:
                                case PropertyType.uint32:
                                    ebr.ReadUInt32();
                                    break;

                                case PropertyType.@float:
                                case PropertyType.float32:
                                    vertices[e].X = ebr.ReadSingle();
                                    vertices[e].Y = ebr.ReadSingle();
                                    vertices[e].Z = ebr.ReadSingle();
                                    p            += 2;
                                    //Adjusting BoundBox...
                                    this.boundBox.Include(vertices[e]);
                                    //Reporting progress
                                    int percent = (int)(((float)e / vertices.Length) * 100.0f);
                                    if ((percent % 20) == 0)
                                    {
                                        this.OnElementLoaded(percent, ElementMesh.Vertex);
                                    }
                                    break;

                                case PropertyType.@double:
                                case PropertyType.float64:
                                    ebr.ReadDouble();
                                    break;

                                default:
                                    break;
                                }
                            }
                        }
                    }
                }
            }
            this.ProcessNormalsPerVertex(pointersToVertex, vertices.Length);
            vertices         = null;
            pointersToVertex = null;
            GC.Collect();
        }