#include "stdafx.h"
#include "lasreader.h"
#include "laspointreader0raw.h"
#include "laspointreader1raw.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
bool LASreader::open(FILE* file, bool skip_variable_header)
{
if (file == 0)
{
fprintf(stderr,"ERROR: file pointer is zero\n");
return false;
}
this->file = file;
// read header variable after variable (to avoid alignment issues)
// 读文件标志("LASF"), 4个字节
if (fread(&(header.file_signature), sizeof(char), 4, file) != 4)
{
fprintf(stderr,"ERROR: reading header.file_signature\n");
return false;
}
// 文件编号
if (fread(&(header.file_source_id), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.file_source_id\n");
return false;
}
// 保留使用
if (fread(&(header.reserved), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.reserved\n");
return false;
}
if (fread(&(header.project_ID_GUID_data_1), sizeof(unsigned int), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.project_ID_GUID_data_1\n");
return false;
}
if (fread(&(header.project_ID_GUID_data_2), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.project_ID_GUID_data_2\n");
return false;
}
if (fread(&(header.project_ID_GUID_data_3), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.project_ID_GUID_data_3\n");
return false;
}
if (fread(&(header.project_ID_GUID_data_4), sizeof(char), 8, file) != 8)
{
fprintf(stderr,"ERROR: reading header.project_ID_GUID_data_4\n");
return false;
}
// 主版本号
if (fread(&(header.version_major), sizeof(char), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.version_major\n");
return false;
}
// 辅版本号
if (fread(&(header.version_minor), sizeof(char), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.version_minor\n");
return false;
}
// 系统标识
if (fread(&(header.system_identifier), sizeof(char), 32, file) != 32)
{
fprintf(stderr,"ERROR: reading header.system_identifier\n");
return false;
}
// 使用软件
if (fread(&(header.generating_software), sizeof(char), 32, file) != 32)
{
fprintf(stderr,"ERROR: reading header.generating_software\n");
return false;
}
// 创建时间
if (fread(&(header.file_creation_day), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.file_creation_day\n");
return false;
}
if (fread(&(header.file_creation_year), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.file_creation_year\n");
return false;
}
// HEAD的大小(这个值可能变化)
if (fread(&(header.header_size), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.header_size\n");
return false;
}
// 数据地址
if (fread(&(header.offset_to_point_data), sizeof(unsigned int), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.offset_to_point_data\n");
return false;
}
// 点数据块的数目
if (fread(&(header.number_of_variable_length_records), sizeof(unsigned int), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.number_of_variable_length_records\n");
return false;
}
// 点数据的格式(0-99)
if (fread(&(header.point_data_format), sizeof(unsigned char), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.point_data_format\n");
return false;
}
// 点数据的长度
if (fread(&(header.point_data_record_length), sizeof(unsigned short), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.point_data_record_length\n");
return false;
}
if (fread(&(header.number_of_point_records), sizeof(unsigned int), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.number_of_point_records\n");
return false;
}
if (fread(&(header.number_of_points_by_return), sizeof(unsigned int), 5, file) != 5)
{
fprintf(stderr,"ERROR: reading header.number_of_points_by_return\n");
return false;
}
// xyz方向的缩放比例
if (fread(&(header.x_scale_factor), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.x_scale_factor\n");
return false;
}
if (fread(&(header.y_scale_factor), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.y_scale_factor\n");
return false;
}
if (fread(&(header.z_scale_factor), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.z_scale_factor\n");
return false;
}
// xyz方向的开始位置
if (fread(&(header.x_offset), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.x_offset\n");
return false;
}
if (fread(&(header.y_offset), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.y_offset\n");
return false;
}
if (fread(&(header.z_offset), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.z_offset\n");
return false;
}
// xyz的值的范围
if (fread(&(header.max_x), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.max_x\n");
return false;
}
if (fread(&(header.min_x), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.min_x\n");
return false;
}
if (fread(&(header.max_y), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.max_y\n");
return false;
}
if (fread(&(header.min_y), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.min_y\n");
return false;
}
if (fread(&(header.max_z), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.max_z\n");
return false;
}
if (fread(&(header.min_z), sizeof(double), 1, file) != 1)
{
fprintf(stderr,"ERROR: reading header.min_z\n");
return false;
}
// check header contents
// 测试HEAD中的信息是否合法
if (strcmp(header.file_signature, "LASF") != 0)
{
fprintf(stderr,"ERROR: wrong file signature '%s'\n", header.file_signature);
return false;
}
// 目前只有1.0和1.0两个版本
if ((header.version_major != 1) || ((header.version_minor != 0) && (header.version_minor != 1)))
{
fprintf(stderr,"ERROR: unknown version %d.%d\n", header.version_major, header.version_minor);
return false;
}
// 结构的大小为LASheader::HEADER_SIZE
// 这个值可能和sizeof(LASheader)的值不相等
// 因为编译器可能对结构体进行了优化
if (header.header_size != LASheader::HEADER_SIZE)
{
fprintf(stderr,
"ERROR: header size is %d but should be %d\n",
header.header_size, LASheader::HEADER_SIZE);
return false;
}
// 数据的起点应该在HEAD之后
if (header.offset_to_point_data < header.header_size)
{
fprintf(stderr,"ERROR: offset to point data %d is smaller than header size %d\n", header.offset_to_point_data, header.header_size);
return false;
}
// 点记录数不为0
if (header.number_of_point_records <= 0)
{
fprintf(stderr,"ERROR: number of point records is %d\n", header.number_of_point_records);
return false;
}
// 点格式的具体定义(1.0和1.1)
// 这里第一个bit和1.0/1.1版本对应
if ((header.point_data_format & 1) == 0)
{
// 1.0版点结构大小为20
if (header.point_data_record_length != 20)
{
fprintf(stderr,"ERROR: wrong point data record length of %d for format 0\n", header.point_data_record_length);
return false;
}
}
else if ((header.point_data_format & 1) == 1)
{
// 1.1版点结构大小为28
if (header.point_data_record_length != 28)
{
fprintf(stderr,"ERROR: wrong point data record length of %d for format 1\n", header.point_data_record_length);
return false;
}
}
else
{
// 这里用不着
fprintf(stderr,"ERROR: unkown point data format %d\n", header.point_data_format);
return false;
}
// xyz方向的比例不为0
if (header.x_scale_factor == 0 || header.y_scale_factor == 0 || header.z_scale_factor == 0)