1 /****************************************************************************** 2 * Copyright (c) 2014, Howard Butler, hobu.inc@gmail.com 3 * 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following 8 * conditions are met: 9 * 10 * * Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * * Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in 14 * the documentation and/or other materials provided 15 * with the distribution. 16 * * Neither the name of Hobu, Inc. or Flaxen Geo Consulting nor the 17 * names of its contributors may be used to endorse or promote 18 * products derived from this software without specific prior 19 * written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 24 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 25 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 26 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 27 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 28 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 29 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 30 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 31 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY 32 * OF SUCH DAMAGE. 33 ****************************************************************************/ 34 35 #pragma once 36 37 #include <stdint.h> 38 #include <string> 39 #include <vector> 40 41 #include <pdal/Dimension.hpp> 42 #include <pdal/Log.hpp> 43 #include <pdal/SpatialReference.hpp> 44 45 namespace pdal 46 { 47 48 class ILeStream; 49 class OLeStream; 50 51 struct BpfMuellerMatrix 52 { BpfMuellerMatrixpdal::BpfMuellerMatrix53 BpfMuellerMatrix() 54 { 55 static const double vals[] = {1.0, 0.0, 0.0, 0.0, 56 0.0, 1.0, 0.0, 0.0, 57 0.0, 0.0, 1.0, 0.0, 58 0.0, 0.0, 0.0, 1.0}; 59 memcpy(m_vals, vals, sizeof(vals)); 60 } 61 62 double m_vals[16]; 63 dumppdal::BpfMuellerMatrix64 void dump() 65 { 66 for (size_t i = 0; i < 4; ++i) 67 std::cerr << m_vals[i] << '\t'; 68 std::cerr << "\n"; 69 for (size_t i = 4; i < 8; ++i) 70 std::cerr << m_vals[i] << '\t'; 71 std::cerr << "\n"; 72 for (size_t i = 8; i < 12; ++i) 73 std::cerr << m_vals[i] << '\t'; 74 std::cerr << "\n"; 75 for (size_t i = 12; i < 16; ++i) 76 std::cerr << m_vals[i] << '\t'; 77 std::cerr << "\n\n"; 78 79 } 80 applypdal::BpfMuellerMatrix81 void apply(double& x, double& y, double& z) 82 { 83 double w = x * m_vals[12] + y * m_vals[13] + z * m_vals[14] + 84 m_vals[15]; 85 86 x = (x * m_vals[0] + y * m_vals[1] + z * m_vals[2] + m_vals[3]) / w; 87 y = (x * m_vals[4] + y * m_vals[5] + z * m_vals[6] + m_vals[7]) / w; 88 z = (x * m_vals[8] + y * m_vals[9] + z * m_vals[10] + m_vals[11]) / w; 89 } 90 }; 91 ILeStream& operator >> (ILeStream& stream, BpfMuellerMatrix& m); 92 OLeStream& operator << (OLeStream& stream, BpfMuellerMatrix& m); 93 94 enum class BpfFormat 95 { 96 DimMajor, 97 PointMajor, 98 ByteMajor 99 }; 100 101 std::istream& operator >> (std::istream& in, BpfFormat& format); 102 std::ostream& operator << (std::ostream& in, const BpfFormat& format); 103 104 enum class BpfCoordType 105 { 106 Cartesian, 107 UTM, 108 TCR, 109 ENU 110 }; 111 112 enum class BpfCompression 113 { 114 None, 115 QuickLZ, 116 FastLZ, 117 Zlib 118 }; 119 120 struct BpfDimension 121 { BpfDimensionpdal::BpfDimension122 BpfDimension() : m_offset(0.0), 123 m_min((std::numeric_limits<double>::max)()), 124 m_max(std::numeric_limits<double>::lowest()), 125 m_id(Dimension::Id::Unknown) 126 {} 127 128 double m_offset; 129 double m_min; 130 double m_max; 131 std::string m_label; 132 Dimension::Id m_id; 133 134 static bool read(ILeStream& stream, std::vector<BpfDimension>& dims, 135 size_t start); 136 static bool write(OLeStream& stream, std::vector<BpfDimension>& dims); 137 }; 138 typedef std::vector<BpfDimension> BpfDimensionList; 139 140 struct BpfHeader 141 { 142 struct error : std::runtime_error 143 { errorpdal::BpfHeader::error144 error(const std::string& err) : std::runtime_error(err) 145 {} 146 }; 147 BpfHeaderpdal::BpfHeader148 BpfHeader() : m_version(0), m_len(176), m_numDim(0), 149 m_compression(Utils::toNative(BpfCompression::None)), m_numPts(0), 150 m_coordType(Utils::toNative(BpfCoordType::Cartesian)), m_coordId(0), 151 m_spacing(0.0), m_startTime(0.0), m_endTime(0.0) 152 {} 153 154 int32_t m_version; 155 std::string m_ver; 156 int32_t m_len; 157 int32_t m_numDim; 158 BpfFormat m_pointFormat; 159 uint8_t m_compression; 160 int32_t m_numPts; 161 int32_t m_coordType; 162 int32_t m_coordId; 163 float m_spacing; 164 BpfMuellerMatrix m_xform; 165 double m_startTime; 166 double m_endTime; 167 std::vector<BpfDimension> m_staticDims; 168 LogPtr m_log; 169 setLogpdal::BpfHeader170 PDAL_DLL void setLog(const LogPtr& log) 171 { m_log = log; } 172 PDAL_DLL bool read(ILeStream& stream); 173 bool write(OLeStream& stream); 174 bool readV3(ILeStream& stream); 175 bool readV1(ILeStream& stream); 176 bool trySetSpatialReference(const pdal::SpatialReference&); 177 PDAL_DLL bool readDimensions(ILeStream& stream, 178 std::vector<BpfDimension>& dims, bool fixNames); 179 void writeDimensions(OLeStream& stream, std::vector<BpfDimension>& dims); 180 void dump(); 181 }; 182 183 struct BpfUlemHeader 184 { 185 uint32_t m_numFrames; 186 uint16_t m_year; 187 uint8_t m_month; 188 uint8_t m_day; 189 uint16_t m_lidarMode; 190 uint16_t m_wavelen; // In nm. 191 uint16_t m_pulseFreq; // In Hz. 192 uint16_t m_focalWidth; 193 uint16_t m_focalHeight; 194 float m_pixelPitchWidth; 195 float m_pixelPitchHeight; 196 std::string m_classCode; 197 198 bool read(ILeStream& stream); 199 }; 200 201 struct BpfUlemFrame 202 { 203 int32_t m_num; 204 double m_roll; //x 205 double m_pitch; //y 206 double m_heading; //z 207 BpfMuellerMatrix m_xform; 208 int16_t m_shortEncoder; 209 int16_t m_longEncoder; 210 211 bool read(ILeStream& stream); 212 }; 213 214 struct BpfUlemFile 215 { 216 uint32_t m_len; 217 std::string m_filename; 218 std::vector<char> m_buf; 219 std::string m_filespec; 220 BpfUlemFilepdal::BpfUlemFile221 BpfUlemFile() : m_len(0) 222 {} 223 BpfUlemFilepdal::BpfUlemFile224 BpfUlemFile(uint32_t len, const std::string& filename, 225 const std::string& filespec) : 226 m_len(len), m_filename(filename), m_filespec(filespec) 227 {} 228 229 bool read(ILeStream& stream); 230 bool write(OLeStream& stream); 231 }; 232 233 struct BpfPolarStokesParam 234 { 235 float m_x; 236 float m_y; 237 float m_z; 238 float m_a; 239 240 bool read(ILeStream& stream); 241 }; 242 243 struct BpfPolarHeader 244 { 245 uint32_t m_numFrames; 246 uint16_t m_fpaId; 247 uint32_t m_numXmit; 248 uint32_t m_numRcv; 249 std::vector<BpfPolarStokesParam> m_xmitStates; 250 std::vector<BpfMuellerMatrix> m_psaSettings; 251 252 bool read(ILeStream& stream); 253 }; 254 255 struct BpfPolarFrame 256 { 257 public: 258 uint32_t m_num; 259 int16_t m_stokesIdx; 260 float m_stokesParam[4]; 261 float m_stokesOutParam[4]; 262 BpfMuellerMatrix m_xform; 263 int16_t m_truncation; 264 265 bool read(ILeStream& stream); 266 }; 267 268 } //namespace pdal 269