PointCloudSub ReadPointCloud(BinaryReader reader, ulong offset)
        {
            PointCloudSub dataset = new PointCloudSub();

            reader.BaseStream.Seek((long)offset, SeekOrigin.Begin);

            dataset.m_numberOfPoints = reader.ReadUInt64();

            dataset.m_pointCloud = new DataBody((int)dataset.m_numberOfPoints);

            for (ulong i = 0; i < dataset.m_numberOfPoints; ++i)
            {
                // position
                float x = reader.ReadSingle();
                float y = reader.ReadSingle();
                float z = reader.ReadSingle();

                // normal
                float nx = reader.ReadSingle();
                float ny = reader.ReadSingle();
                float nz = reader.ReadSingle();

                // color
                byte r = reader.ReadByte();
                byte g = reader.ReadByte();
                byte b = reader.ReadByte();

                dataset.m_pointCloud.AddPoint(x, y, z,
                                              r, g, b, 255);
            }

            return(dataset);
        }
        PointCloudSub[] ReadDataBody(PCModelHeader header, BinaryReader reader)
        {
            PointCloudSub[] pointDatasets = new PointCloudSub[header.nbSubPointCloud];

            for (uint i = 0; i < header.nbSubPointCloud; ++i)
            {
                //ReadKDTree(file, header.map[i].offsetTree, i);
                PointCloudSub dataset = ReadPointCloud(reader, header.map[i].offsetPointCloud);

                if (dataset.m_numberOfPoints > 0)
                {
                    pointDatasets[i] = dataset;
                }
                else
                {
                    pointDatasets[i] = null;
                }
            }

            return(pointDatasets);
        }