[Liblas-commits] hg-main-tree: Read the new 8-dimension full layout that las2oci ...

liblas-commits at liblas.org liblas-commits at liblas.org
Wed Apr 20 14:54:02 EDT 2011


details:   http://hg.libpc.orghg-main-tree/rev/29125c5e887b
changeset: 605:29125c5e887b
user:      Howard Butler <hobu.inc at gmail.com>
date:      Wed Apr 20 13:53:53 2011 -0500
description:
Read the new 8-dimension full layout that las2oci writes... libPC doesn't write this yet, however

diffstat:

 include/libpc/drivers/oci/Common.hpp |   27 +++++-
 src/drivers/oci/Iterator.cpp         |   61 +++++++++++-
 src/drivers/oci/Reader.cpp           |  166 ++++++++++++++++++++++++++++++++--
 3 files changed, 230 insertions(+), 24 deletions(-)

diffs (truncated from 320 to 300 lines):

diff -r 6e8f75b35eaf -r 29125c5e887b include/libpc/drivers/oci/Common.hpp
--- a/include/libpc/drivers/oci/Common.hpp	Wed Apr 20 12:32:13 2011 -0500
+++ b/include/libpc/drivers/oci/Common.hpp	Wed Apr 20 13:53:53 2011 -0500
@@ -125,8 +125,31 @@
     double z;
     double t;
     double c;
-    uint32_t blk_id;
-    uint32_t pc_id;
+    boost::uint32_t blk_id;
+    boost::uint32_t pc_id;
+};
+
+struct EightDimensionOCI
+{
+    double x;
+    double y;
+    double z;
+    double time;
+    double cls;
+    double intensity;
+    boost::int8_t returnNumber;
+    boost::int8_t numberOfReturns;
+    boost::int8_t scanDirFlag;
+    boost::int8_t edgeOfFlightLine;
+    boost::int8_t scanAngleRank;
+    boost::int8_t userData;
+    boost::int16_t pointSourceId;
+    boost::uint16_t red;
+    boost::uint16_t green;
+    boost::uint16_t blue;
+    boost::uint16_t alpha;
+    boost::uint32_t blk_id;
+    boost::uint32_t pc_id;
 };
 
 
diff -r 6e8f75b35eaf -r 29125c5e887b src/drivers/oci/Iterator.cpp
--- a/src/drivers/oci/Iterator.cpp	Wed Apr 20 12:32:13 2011 -0500
+++ b/src/drivers/oci/Iterator.cpp	Wed Apr 20 13:53:53 2011 -0500
@@ -121,6 +121,21 @@
     const int indexZ = schema.getDimensionIndex(Dimension::Field_Z, Dimension::Int32);
     const int indexTime = schema.getDimensionIndex(Dimension::Field_Time, Dimension::Double);
     const int indexClassification = schema.getDimensionIndex(Dimension::Field_Classification, Dimension::Uint8);
+    const int indexIntensity = schema.getDimensionIndex(Dimension::Field_Intensity, Dimension::Uint16);
+
+
+    const int indexReturnNumber = schema.getDimensionIndex(Dimension::Field_ReturnNumber, Dimension::Uint8);
+    const int indexNumberOfReturns = schema.getDimensionIndex(Dimension::Field_NumberOfReturns, Dimension::Uint8);
+    const int indexScanDirectionFlag = schema.getDimensionIndex(Dimension::Field_ScanDirectionFlag, Dimension::Uint8);
+    const int indexEdgeOfFlightLine = schema.getDimensionIndex(Dimension::Field_EdgeOfFlightLine, Dimension::Uint8);
+    const int indexScanAngleRank = schema.getDimensionIndex(Dimension::Field_ScanAngleRank, Dimension::Int8);
+    const int indexUserData = schema.getDimensionIndex(Dimension::Field_UserData, Dimension::Uint8);
+    const int indexPointSourceId = schema.getDimensionIndex(Dimension::Field_PointSourceId, Dimension::Uint16);
+
+    const int indexRed = schema.getDimensionIndex(Dimension::Field_Red, Dimension::Uint16);
+    const int indexGreen = schema.getDimensionIndex(Dimension::Field_Green, Dimension::Uint16);
+    const int indexBlue = schema.getDimensionIndex(Dimension::Field_Blue, Dimension::Uint16);
+    
 
     const Dimension& dimX = schema.getDimension(indexX);
     const Dimension& dimY = schema.getDimension(indexY);
@@ -134,17 +149,33 @@
     double offsety = dimY.getNumericOffset();
     double offsetz = dimZ.getNumericOffset();
      
-    FiveDimensionOCI* d;
+    EightDimensionOCI* d;
+    
     for (boost::uint32_t i = 0; i < static_cast<boost::uint32_t>(m_block->num_points); i++)
     {
-        boost::uint32_t byte_position = i*sizeof(FiveDimensionOCI);
+        boost::uint32_t byte_position = i*sizeof(EightDimensionOCI);
         
-        d = (FiveDimensionOCI*)(&(*m_block->chunk)[byte_position]);
+        d = (EightDimensionOCI*)(&(*m_block->chunk)[byte_position]);
         SWAP_BE_TO_LE(d->x);
         SWAP_BE_TO_LE(d->y);
         SWAP_BE_TO_LE(d->z);
-        SWAP_BE_TO_LE(d->t);
-        SWAP_BE_TO_LE(d->c);
+        SWAP_BE_TO_LE(d->time);
+        SWAP_BE_TO_LE(d->cls);
+        SWAP_BE_TO_LE(d->intensity);
+
+        SWAP_BE_TO_LE(d->returnNumber);
+        SWAP_BE_TO_LE(d->numberOfReturns);
+        SWAP_BE_TO_LE(d->scanDirFlag);
+        SWAP_BE_TO_LE(d->edgeOfFlightLine);
+        SWAP_BE_TO_LE(d->scanAngleRank);
+        SWAP_BE_TO_LE(d->userData);
+        SWAP_BE_TO_LE(d->pointSourceId);
+
+        SWAP_BE_TO_LE(d->red);
+        SWAP_BE_TO_LE(d->green);
+        SWAP_BE_TO_LE(d->blue);
+        SWAP_BE_TO_LE(d->alpha);
+        
         SWAP_BE_TO_LE(d->blk_id);
         SWAP_BE_TO_LE(d->pc_id);
         
@@ -158,9 +189,23 @@
         data.setField(point_position, indexY, y);
         data.setField(point_position, indexZ, z);
         
-        data.setField(point_position, indexTime, d->t);
-        data.setField(point_position, indexClassification, static_cast<boost::uint8_t>(d->c));
-        
+        data.setField(point_position, indexTime, d->time);
+        data.setField(point_position, indexClassification, static_cast<boost::uint8_t>(d->cls));
+        data.setField<boost::int16_t>(point_position, indexIntensity, static_cast<boost::int16_t>(d->intensity));
+
+        data.setField<boost::int8_t>(point_position, indexReturnNumber, d->returnNumber);
+        data.setField<boost::int8_t>(point_position, indexNumberOfReturns, d->numberOfReturns);
+        data.setField<boost::int8_t>(point_position, indexScanDirectionFlag, d->scanDirFlag);
+        data.setField<boost::int8_t>(point_position, indexEdgeOfFlightLine, d->edgeOfFlightLine);
+        data.setField<boost::int8_t>(point_position, indexScanAngleRank, d->scanAngleRank);
+        data.setField<boost::int8_t>(point_position, indexUserData, d->userData);
+        data.setField<boost::uint16_t>(point_position, indexPointSourceId, d->pointSourceId);
+
+
+        data.setField<boost::uint16_t>(point_position, indexRed, d->red);
+        data.setField<boost::uint16_t>(point_position, indexGreen, d->green);
+        data.setField<boost::uint16_t>(point_position, indexBlue, d->blue);
+                
         point_position++;
         data.setNumPoints(point_position);
     
diff -r 6e8f75b35eaf -r 29125c5e887b src/drivers/oci/Reader.cpp
--- a/src/drivers/oci/Reader.cpp	Wed Apr 20 12:32:13 2011 -0500
+++ b/src/drivers/oci/Reader.cpp	Wed Apr 20 13:53:53 2011 -0500
@@ -121,9 +121,9 @@
 {
     Schema& schema = getSchemaRef();
 
-    Dimension xDim(Dimension::Field_X, Dimension::Int32);
-    Dimension yDim(Dimension::Field_Y, Dimension::Int32);
-    Dimension zDim(Dimension::Field_Z, Dimension::Int32);
+    Dimension x(Dimension::Field_X, Dimension::Int32);
+    Dimension y(Dimension::Field_Y, Dimension::Int32);
+    Dimension z(Dimension::Field_Z, Dimension::Int32);
     
     boost::property_tree::ptree tree = m_options.GetPTree();
     double scalex = tree.get<double>("scale.x");
@@ -134,19 +134,155 @@
     double offsety = tree.get<double>("offset.y");
     double offsetz = tree.get<double>("offset.z");
         
-    xDim.setNumericScale(scalex);
-    yDim.setNumericScale(scaley);
-    zDim.setNumericScale(scalez);
-    xDim.setNumericOffset(offsetx);
-    yDim.setNumericOffset(offsety);
-    zDim.setNumericOffset(offsetz);
+    x.setNumericScale(scalex);
+    y.setNumericScale(scaley);
+    z.setNumericScale(scalez);
+    x.setNumericOffset(offsetx);
+    y.setNumericOffset(offsety);
+    z.setNumericOffset(offsetz);
 
-    schema.addDimension(xDim);
-    schema.addDimension(yDim);
-    schema.addDimension(zDim);
 
-    schema.addDimension(Dimension(Dimension::Field_Time, Dimension::Double));
-    schema.addDimension(Dimension(Dimension::Field_Classification, Dimension::Uint8));
+    std::ostringstream text;
+
+    text << "x coordinate as a long integer.  You must use the scale and "
+         << "offset information of the header to determine the double value.";
+    x.setDescription(text.str());
+    schema.addDimension(x);
+    text.str("");
+
+    text << "y coordinate as a long integer.  You must use the scale and "
+         << "offset information of the header to determine the double value.";
+    y.setDescription(text.str());
+    schema.addDimension(y);
+    text.str("");
+
+    text << "z coordinate as a long integer.  You must use the scale and "
+         << "offset information of the header to determine the double value.";
+    z.setDescription(text.str());
+    schema.addDimension(z);
+    text.str("");
+
+    Dimension intensity(Dimension::Field_Intensity, Dimension::Uint16);
+    text << "The intensity value is the integer representation of the pulse "
+         "return magnitude. This value is optional and system specific. "
+         "However, it should always be included if available.";
+    intensity.setDescription(text.str());
+    schema.addDimension(intensity);
+    text.str("");
+
+    Dimension return_no(Dimension::Field_ReturnNumber, Dimension::Uint8); // 3 bits only
+    text << "Return Number: The Return Number is the pulse return number for "
+         "a given output pulse. A given output laser pulse can have many "
+         "returns, and they must be marked in sequence of return. The first "
+         "return will have a Return Number of one, the second a Return "
+         "Number of two, and so on up to five returns.";
+    return_no.setDescription(text.str());
+    schema.addDimension(return_no);
+    text.str("");
+
+    Dimension no_returns(Dimension::Field_NumberOfReturns, Dimension::Uint8); // 3 bits only
+    text << "Number of Returns (for this emitted pulse): The Number of Returns "
+         "is the total number of returns for a given pulse. For example, "
+         "a laser data point may be return two (Return Number) within a "
+         "total number of five returns.";
+    no_returns.setDescription(text.str());
+    schema.addDimension(no_returns);
+    text.str("");
+
+    Dimension scan_dir(Dimension::Field_ScanDirectionFlag, Dimension::Uint8); // 1 bit only
+    text << "The Scan Direction Flag denotes the direction at which the "
+         "scanner mirror was traveling at the time of the output pulse. "
+         "A bit value of 1 is a positive scan direction, and a bit value "
+         "of 0 is a negative scan direction (where positive scan direction "
+         "is a scan moving from the left side of the in-track direction to "
+         "the right side and negative the opposite). ";
+    scan_dir.setDescription(text.str());
+    schema.addDimension(scan_dir);
+    text.str("");
+
+    Dimension edge(Dimension::Field_EdgeOfFlightLine, Dimension::Uint8); // 1 bit only
+    text << "The Edge of Flight Line data bit has a value of 1 only when "
+         "the point is at the end of a scan. It is the last point on "
+         "a given scan line before it changes direction.";
+    edge.setDescription(text.str());
+    schema.addDimension(edge);
+    text.str("");
+
+    Dimension classification(Dimension::Field_Classification, Dimension::Uint8);
+    text << "Classification in LAS 1.0 was essentially user defined and optional. "
+         "LAS 1.1 defines a standard set of ASPRS classifications. In addition, "
+         "the field is now mandatory. If a point has never been classified, this "
+         "byte must be set to zero. There are no user defined classes since "
+         "both point format 0 and point format 1 supply 8 bits per point for "
+         "user defined operations. Note that the format for classification is a "
+         "bit encoded field with the lower five bits used for class and the "
+         "three high bits used for flags.";
+    classification.setDescription(text.str());
+    schema.addDimension(classification);
+    text.str("");
+
+    Dimension scan_angle(Dimension::Field_ScanAngleRank, Dimension::Int8);
+    text << "The Scan Angle Rank is a signed one-byte number with a "
+         "valid range from -90 to +90. The Scan Angle Rank is the "
+         "angle (rounded to the nearest integer in the absolute "
+         "value sense) at which the laser point was output from the "
+         "laser system including the roll of the aircraft. The scan "
+         "angle is within 1 degree of accuracy from +90 to ñ90 degrees. "
+         "The scan angle is an angle based on 0 degrees being nadir, "
+         "and ñ90 degrees to the left side of the aircraft in the "
+         "direction of flight.";
+    scan_angle.setDescription(text.str());
+    schema.addDimension(scan_angle);
+    text.str("");
+
+    Dimension user_data(Dimension::Field_UserData, Dimension::Uint8);
+    text << "This field may be used at the userís discretion";
+    user_data.setDescription(text.str());
+    schema.addDimension(user_data);
+    text.str("");
+
+    Dimension point_source_id(Dimension::Field_PointSourceId, Dimension::Uint16);
+    text << "This value indicates the file from which this point originated. "
+         "Valid values for this field are 1 to 65,535 inclusive with zero "
+         "being used for a special case discussed below. The numerical value "
+         "corresponds to the File Source ID from which this point originated. "
+         "Zero is reserved as a convenience to system implementers. A Point "
+         "Source ID of zero implies that this point originated in this file. "
+         "This implies that processing software should set the Point Source "
+         "ID equal to the File Source ID of the file containing this point "
+         "at some time during processing. ";
+    point_source_id.setDescription(text.str());
+    schema.addDimension(point_source_id);
+    text.str("");
+
+    Dimension t(Dimension::Field_Time, Dimension::Double);
+    text << "The GPS Time is the double floating point time tag value at "
+        "which the point was acquired. It is GPS Week Time if the "
+        "Global Encoding low bit is clear and Adjusted Standard GPS "
+        "Time if the Global Encoding low bit is set (see Global Encoding "
+        "in the Public Header Block description).";
+    t.setDescription(text.str());
+    schema.addDimension(t);
+    text.str("");
+
+    Dimension red(Dimension::Field_Red, Dimension::Uint16);
+    text << "The red image channel value associated with this point";
+    red.setDescription(text.str());
+    schema.addDimension(red);
+    text.str("");
+
+    Dimension green(Dimension::Field_Green, Dimension::Uint16);
+    text << "The green image channel value associated with this point";
+    green.setDescription(text.str());
+    schema.addDimension(green);


More information about the Liblas-commits mailing list