Skip to content
Snippets Groups Projects
Commit 0764662d authored by Kelvin Rodriguez's avatar Kelvin Rodriguez Committed by Jesse Mapel
Browse files

ISD object without Rotation and State support. (#315)

* version tick

* added headers

* added isd

* updated cmakelists

* added header

* removed print from cmakelists

* changed rotation case

* moved isd test to single module

* added in line isd

* Added failure tests. Commented out distortion tests.

* added more tests to increase coverage

* changed header file naming convention

* updated source files and CMakeLists.txt

* renamed isd_tests.cpp -> IsdTests.cpp

* Updated tests based on comments.

* Capitalized enum values.

* added a few more asserts to check array size
parent 52003c59
Branches
Tags
No related merge requests found
...@@ -21,13 +21,17 @@ find_package(Python REQUIRED COMPONENTS Development) ...@@ -21,13 +21,17 @@ find_package(Python REQUIRED COMPONENTS Development)
find_package(nlohmann_json REQUIRED) find_package(nlohmann_json REQUIRED)
# Library setup # Library setup
set(ALE_BUILD_INCLUDE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/include/")
set(ALE_INSTALL_INCLUDE_DIR "include/ale")
add_library(ale SHARED add_library(ale SHARED
${CMAKE_CURRENT_SOURCE_DIR}/src/ale.cpp ${CMAKE_CURRENT_SOURCE_DIR}/src/ale.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/Rotation.cpp) ${CMAKE_CURRENT_SOURCE_DIR}/src/Rotation.cpp
set(ALE_BUILD_INCLUDE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/include/") ${CMAKE_CURRENT_SOURCE_DIR}/src/Isd.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/Util.cpp)
set(ALE_HEADERS "${ALE_BUILD_INCLUDE_DIR}/ale.h" set(ALE_HEADERS "${ALE_BUILD_INCLUDE_DIR}/ale.h"
"${ALE_BUILD_INCLUDE_DIR}/Rotation.h") "${ALE_BUILD_INCLUDE_DIR}/Rotation.h"
set(ALE_INSTALL_INCLUDE_DIR "include/ale") "${ALE_BUILD_INCLUDE_DIR}/Isd.h"
"${ALE_BUILD_INCLUDE_DIR}/Util.h")
set_target_properties(ale PROPERTIES set_target_properties(ale PROPERTIES
VERSION ${PROJECT_VERSION} VERSION ${PROJECT_VERSION}
SOVERSION 0) SOVERSION 0)
......
#ifndef ALE_DISTORTION_H
#define ALE_DISTORTION_H
namespace ale {
enum DistortionType {
TRANSVERSE,
RADIAL,
KAGUYALISM,
DAWNFC,
LROLROCNAC
};
}
#endif
#ifndef ALE_ISD_H
#define ALE_ISD_H
#include <string>
#include <vector>
#include <map>
#include "Util.h"
#include "Distortion.h"
//#include "Rotation.h"
//#include "State.h"
namespace ale {
using json = nlohmann::json;
class Isd {
public:
Isd(std::string);
std::string usgscsm_name_model;
std::string name_platform;
std::string image_id;
std::string name_sensor;
double semi_major;
double semi_minor;
double detector_sample_summing;
double detector_line_summing;
double focal_length;
double focal_uncertainty;
double detector_center_line;
double detector_center_sample;
// should probably be ints
double starting_detector_line;
double starting_detector_sample;
std::vector<double> focal2pixel_line;
std::vector<double> focal2pixel_sample;
// maybe change
DistortionType distortion_model;
std::vector<double> distortion_coefficients;
unsigned int image_lines;
unsigned int image_samples;
double max_reference_height;
double min_reference_height;
std::vector<std::vector<double>> line_scan_rate;
double starting_ephemeris_time;
double center_ephemeris_time;
double t0_ephemeris_time;
double dt_ephemeris_time;
double t0_quaternions;
double dt_quaternions;
json naif_keywords;
//Positions sensor_pos;
//Positions sun_pos;
//Rotation sensor_orientation;
//Rotation body_orientaion;
};
}
#endif
#ifndef ALE_UTIL_H
#define ALE_UTIL_H
#include <string>
#include <nlohmann/json.hpp>
#include "Isd.h"
#include "Distortion.h"
namespace ale {
using json = nlohmann::json;
double getMinHeight(nlohmann::json isd);
std::string getSensorModelName(json isd);
std::string getImageId(json isd);
std::string getSensorName(json isd);
std::string getPlatformName(json isd);
std::string getLogFile(nlohmann::json isd);
int getTotalLines(json isd);
int getTotalSamples(json isd);
double getStartingTime(json isd);
double getCenterTime(json isd);
std::vector<std::vector<double>> getLineScanRate(json isd);
int getSampleSumming(json isd);
int getLineSumming(json isd);
double getFocalLength(json isd);
double getFocalLengthUncertainty(json isd);
std::vector<double> getFocal2PixelLines(json isd);
std::vector<double> getFocal2PixelSamples(json isd);
double getDetectorCenterLine(json isd);
double getDetectorCenterSample(json isd);
double getDetectorStartingLine(json isd);
double getDetectorStartingSample(json isd);
double getMinHeight(json isd);
double getMaxHeight(json isd);
double getSemiMajorRadius(json isd);
double getSemiMinorRadius(json isd);
DistortionType getDistortionModel(json isd);
std::vector<double> getDistortionCoeffs(json isd);
std::vector<double> getSunPositions(json isd);
std::vector<double> getSensorPositions(json isd);
std::vector<double> getSensorVelocities(json isd);
std::vector<double> getSensorOrientations(json isd);
}
#endif
#ifndef ALE_INCLUDE_ALE_H #ifndef ALE_INCLUDE_ALE_H
#define ALE_INCLUDE_ALE_H #define ALE_INCLUDE_ALE_H
#include <nlohmann/json.hpp>
#include <string> #include <string>
#include <vector> #include <vector>
...@@ -15,9 +14,9 @@ namespace ale { ...@@ -15,9 +14,9 @@ namespace ale {
/// Interpolation enum for defining different methods of interpolation /// Interpolation enum for defining different methods of interpolation
enum interpolation { enum interpolation {
/// Interpolate using linear interpolation /// Interpolate using linear interpolation
linear, LINEAR,
/// Interpolate using spline interpolation /// Interpolate using spline interpolation
spline SPLINE
}; };
/** /**
......
#include "Isd.h"
#include "Util.h"
ale::Isd::Isd(std::string isd_file) {
json isd = json::parse(isd_file);
usgscsm_name_model = getSensorModelName(isd);
image_id = getImageId(isd);
name_platform = getPlatformName(isd);
name_sensor = getSensorName(isd);
image_lines = getTotalLines(isd);
image_samples = getTotalSamples(isd);
starting_ephemeris_time = getStartingTime(isd);
center_ephemeris_time = getCenterTime(isd);
line_scan_rate = getLineScanRate(isd);
detector_sample_summing = getSampleSumming(isd);
detector_line_summing = getLineSumming(isd);
focal_length = getFocalLength(isd);
focal_uncertainty = getFocalLengthUncertainty(isd);
focal2pixel_line = getFocal2PixelLines(isd);
focal2pixel_sample = getFocal2PixelSamples(isd);
detector_center_line = getDetectorCenterLine(isd);
detector_center_sample = getDetectorCenterSample(isd);
starting_detector_line = getDetectorStartingLine(isd);
starting_detector_sample = getDetectorStartingSample(isd);
min_reference_height = getMinHeight(isd);
max_reference_height = getMaxHeight(isd);
semi_major = getSemiMajorRadius(isd);
semi_minor = getSemiMinorRadius(isd);
distortion_model = getDistortionModel(isd);
distortion_coefficients = getDistortionCoeffs(isd);
}
#include <stdexcept>
#include "Util.h"
std::string ale::getSensorModelName(json isd) {
std::string name = "";
try {
name = isd.at("name_model");
} catch (...) {
throw std::runtime_error("Could not parse the sensor model name.");
}
return name;
}
std::string ale::getImageId(json isd) {
std::string id = "";
try {
id = isd.at("image_identifier");
} catch (...) {
throw std::runtime_error("Could not parse the image identifier.");
}
return id;
}
std::string ale::getSensorName(json isd) {
std::string name = "";
try {
name = isd.at("name_sensor");
} catch (...) {
throw std::runtime_error("Could not parse the sensor name.");
}
return name;
}
std::string ale::getPlatformName(json isd) {
std::string name = "";
try {
name = isd.at("name_platform");
} catch (...) {
throw std::runtime_error("Could not parse the platform name.");
}
return name;
}
std::string ale::getLogFile(nlohmann::json isd) {
std::string file = "";
try {
file = isd.at("log_file");
} catch (...) {
throw std::runtime_error("Could not parse the log filename.");
}
return file;
}
int ale::getTotalLines(json isd) {
int lines = 0;
try {
lines = isd.at("image_lines");
} catch (...) {
throw std::runtime_error(
"Could not parse the number of lines in the image.");
}
return lines;
}
int ale::getTotalSamples(json isd) {
int samples = 0;
try {
samples = isd.at("image_samples");
} catch (...) {
throw std::runtime_error(
"Could not parse the number of samples in the image.");
}
return samples;
}
double ale::getStartingTime(json isd) {
double time = 0.0;
try {
time = isd.at("starting_ephemeris_time");
} catch (...) {
throw std::runtime_error("Could not parse the image start time.");
}
return time;
}
double ale::getCenterTime(json isd) {
double time = 0.0;
try {
time = isd.at("center_ephemeris_time");
} catch (...) {
throw std::runtime_error("Could not parse the center image time.");
}
return time;
}
std::vector<std::vector<double>> ale::getLineScanRate(json isd) {
std::vector<std::vector<double>> lines;
try {
for (auto &scanRate : isd.at("line_scan_rate")) {
lines.push_back(scanRate.get<std::vector<double>>());
}
} catch (...) {
throw std::runtime_error("Could not parse the integration start lines in "
"the integration time table.");
}
return lines;
}
int ale::getSampleSumming(json isd) {
int summing = 0;
try {
summing = isd.at("detector_sample_summing");
} catch (...) {
throw std::runtime_error(
"Could not parse the sample direction detector pixel summing.");
}
return summing;
}
int ale::getLineSumming(json isd) {
int summing = 0;
try {
summing = isd.at("detector_line_summing");
} catch (...) {
throw std::runtime_error(
"Could not parse the line direction detector pixel summing.");
}
return summing;
}
double ale::getFocalLength(json isd) {
double length = 0.0;
try {
length = isd.at("focal_length_model").at("focal_length");
} catch (...) {
throw std::runtime_error("Could not parse the focal length.");
}
return length;
}
double ale::getFocalLengthUncertainty(json isd) {
double uncertainty = 1.0;
try {
uncertainty = isd.at("focal_length_model").value("focal_uncertainty", uncertainty);
} catch (...) {
throw std::runtime_error("Could not parse the focal length uncertainty.");
}
return uncertainty;
}
std::vector<double> ale::getFocal2PixelLines(json isd) {
std::vector<double> transformation;
try {
transformation = isd.at("focal2pixel_lines").get<std::vector<double>>();
} catch (...) {
throw std::runtime_error("Could not parse the focal plane coordinate to "
"detector lines transformation.");
}
return transformation;
}
std::vector<double> ale::getFocal2PixelSamples(json isd) {
std::vector<double> transformation;
try {
transformation = isd.at("focal2pixel_samples").get<std::vector<double>>();
} catch (...) {
throw std::runtime_error("Could not parse the focal plane coordinate to "
"detector samples transformation.");
}
return transformation;
}
double ale::getDetectorCenterLine(json isd) {
double line;
try {
line = isd.at("detector_center").at("line");
} catch (...) {
throw std::runtime_error("Could not parse the detector center line.");
}
return line;
}
double ale::getDetectorCenterSample(json isd) {
double sample;
try {
sample = isd.at("detector_center").at("sample");
} catch (...) {
throw std::runtime_error("Could not parse the detector center sample.");
}
return sample;
}
double ale::getDetectorStartingLine(json isd) {
double line;
try {
line = isd.at("starting_detector_line");
} catch (...) {
throw std::runtime_error("Could not parse the detector starting line.");
}
return line;
}
double ale::getDetectorStartingSample(json isd) {
double sample;
try {
sample = isd.at("starting_detector_sample");
} catch (...) {
throw std::runtime_error("Could not parse the detector starting sample.");
}
return sample;
}
double ale::getMinHeight(json isd) {
double height = 0.0;
try {
json referenceHeight = isd.at("reference_height");
json minHeight = referenceHeight.at("minheight");
height = minHeight.get<double>();
} catch (...) {
throw std::runtime_error(
"Could not parse the minimum height above the reference ellipsoid.");
}
return height;
}
double ale::getMaxHeight(json isd) {
double height = 0.0;
try {
json referenceHeight = isd.at("reference_height");
json maxHeight = referenceHeight.at("maxheight");
height = maxHeight.get<double>();
} catch (...) {
throw std::runtime_error(
"Could not parse the maximum height above the reference ellipsoid.");
}
return height;
}
double ale::getSemiMajorRadius(json isd) {
double radius = 0.0;
try {
json radii = isd.at("radii");
json semiMajor = radii.at("semimajor");
radius = semiMajor.get<double>();
} catch (...) {
throw std::runtime_error(
"Could not parse the reference ellipsoid semimajor radius.");
}
return radius;
}
double ale::getSemiMinorRadius(json isd) {
double radius = 0.0;
try {
json radii = isd.at("radii");
json semiMinor = radii.at("semiminor");
radius = semiMinor.get<double>();
} catch (...) {
throw std::runtime_error(
"Could not parse the reference ellipsoid semiminor radius.");
}
return radius;
}
// Converts the distortion model name from the ISD (string) to the enumeration
// type. Defaults to transverse
ale::DistortionType ale::getDistortionModel(json isd) {
try {
json distoriton_subset = isd.at("optical_distortion");
json::iterator it = distoriton_subset.begin();
std::string distortion = (std::string)it.key();
if (distortion.compare("transverse") == 0) {
return DistortionType::TRANSVERSE;
} else if (distortion.compare("radial") == 0) {
return DistortionType::RADIAL;
} else if (distortion.compare("kaguyalism") == 0) {
return DistortionType::KAGUYALISM;
} else if (distortion.compare("dawnfc") == 0) {
return DistortionType::DAWNFC;
} else if (distortion.compare("lrolrocnac") == 0) {
return DistortionType::LROLROCNAC;
}
} catch (...) {
throw std::runtime_error("Could not parse the distortion model.");
}
return DistortionType::TRANSVERSE;
}
std::vector<double> ale::getDistortionCoeffs(json isd) {
std::vector<double> coefficients;
ale::DistortionType distortion = getDistortionModel(isd);
switch (distortion) {
case DistortionType::TRANSVERSE: {
try {
std::vector<double> coefficientsX, coefficientsY;
coefficientsX = isd.at("optical_distortion")
.at("transverse")
.at("x")
.get<std::vector<double>>();
coefficientsX.resize(10, 0.0);
coefficientsY = isd.at("optical_distortion")
.at("transverse")
.at("y")
.get<std::vector<double>>();
coefficientsY.resize(10, 0.0);
coefficients = coefficientsX;
coefficients.insert(coefficients.end(), coefficientsY.begin(),
coefficientsY.end());
return coefficients;
} catch (...) {
throw std::runtime_error(
"Could not parse a set of transverse distortion model coefficients.");
coefficients = std::vector<double>(20, 0.0);
coefficients[1] = 1.0;
coefficients[12] = 1.0;
}
} break;
case DistortionType::RADIAL: {
try {
coefficients = isd.at("optical_distortion")
.at("radial")
.at("coefficients")
.get<std::vector<double>>();
return coefficients;
} catch (...) {
throw std::runtime_error(
"Could not parse the radial distortion model coefficients.");
coefficients = std::vector<double>(3, 0.0);
}
} break;
case DistortionType::KAGUYALISM: {
try {
std::vector<double> coefficientsX = isd.at("optical_distortion")
.at("kaguyalism")
.at("x")
.get<std::vector<double>>();
std::vector<double> coefficientsY = isd.at("optical_distortion")
.at("kaguyalism")
.at("y")
.get<std::vector<double>>();
double boresightX = isd.at("optical_distortion")
.at("kaguyalism")
.at("boresight_x")
.get<double>();
double boresightY = isd.at("optical_distortion")
.at("kaguyalism")
.at("boresight_y")
.get<double>();
coefficientsX.resize(4, 0.0);
coefficientsY.resize(4, 0.0);
coefficientsX.insert(coefficientsX.begin(), boresightX);
coefficientsY.insert(coefficientsY.begin(), boresightY);
coefficientsX.insert(coefficientsX.end(), coefficientsY.begin(),
coefficientsY.end());
return coefficientsX;
} catch (...) {
throw std::runtime_error("Could not parse a set of Kaguya LISM "
"distortion model coefficients.");
coefficients = std::vector<double>(8, 0.0);
}
} break;
case DistortionType::DAWNFC: {
try {
coefficients = isd.at("optical_distortion")
.at("dawnfc")
.at("coefficients")
.get<std::vector<double>>();
return coefficients;
} catch (...) {
throw std::runtime_error(
"Could not parse the dawn radial distortion model coefficients.");
coefficients = std::vector<double>(1, 0.0);
}
} break;
case DistortionType::LROLROCNAC: {
try {
coefficients = isd.at("optical_distortion")
.at("lrolrocnac")
.at("coefficients")
.get<std::vector<double>>();
return coefficients;
} catch (...) {
throw std::runtime_error(
"Could not parse the lrolrocnac distortion model coefficients.");
coefficients = std::vector<double>(1, 0.0);
}
} break;
}
throw std::runtime_error(
"Could not parse the distortion model coefficients.");
return coefficients;
}
std::vector<double> ale::getSunPositions(json isd) {
std::vector<double> positions;
try {
json jayson = isd.at("sun_position");
for (auto &location : jayson.at("positions")) {
positions.push_back(location[0].get<double>());
positions.push_back(location[1].get<double>());
positions.push_back(location[2].get<double>());
}
} catch (...) {
throw std::runtime_error("Could not parse the sun positions.");
}
return positions;
}
std::vector<double> ale::getSensorPositions(json isd) {
std::vector<double> positions;
try {
json jayson = isd.at("sensor_position");
for (auto &location : jayson.at("positions")) {
positions.push_back(location[0].get<double>());
positions.push_back(location[1].get<double>());
positions.push_back(location[2].get<double>());
}
} catch (...) {
throw std::runtime_error("Could not parse the sensor positions.");
}
return positions;
}
std::vector<double> ale::getSensorVelocities(json isd) {
std::vector<double> velocities;
try {
json jayson = isd.at("sensor_position");
for (auto &velocity : jayson.at("velocities")) {
velocities.push_back(velocity[0].get<double>());
velocities.push_back(velocity[1].get<double>());
velocities.push_back(velocity[2].get<double>());
}
} catch (...) {
throw std::runtime_error("Could not parse the sensor velocities.");
}
return velocities;
}
std::vector<double> ale::getSensorOrientations(json isd) {
std::vector<double> quaternions;
try {
for (auto &quaternion : isd.at("sensor_orientation").at("quaternions")) {
quaternions.push_back(quaternion[0]);
quaternions.push_back(quaternion[1]);
quaternions.push_back(quaternion[2]);
quaternions.push_back(quaternion[3]);
}
} catch (...) {
throw std::runtime_error("Could not parse the sensor orientations.");
}
return quaternions;
}
#include "gtest/gtest.h" #include "gtest/gtest.h"
#include "ale.h" #include "ale.h"
#include "Isd.h"
#include <stdexcept> #include <stdexcept>
#include <cmath> #include <cmath>
...@@ -12,13 +13,14 @@ ...@@ -12,13 +13,14 @@
using namespace std; using namespace std;
TEST(PositionInterpTest, LinearInterp) { TEST(PositionInterpTest, LinearInterp) {
vector<double> times = { -3, -2, -1, 0, 1, 2}; vector<double> times = { -3, -2, -1, 0, 1, 2};
vector<vector<double>> data = {{ -3, -2, -1, 0, 1, 2}, vector<vector<double>> data = {{ -3, -2, -1, 0, 1, 2},
{ 9, 4, 1, 0, 1, 4}, { 9, 4, 1, 0, 1, 4},
{-27, -8, -1, 0, 1, 8}}; {-27, -8, -1, 0, 1, 8}};
vector<double> coordinate = ale::getPosition(data, times, -1.5, ale::linear); vector<double> coordinate = ale::getPosition(data, times, -1.5, ale::LINEAR);
ASSERT_EQ(3, coordinate.size()); ASSERT_EQ(3, coordinate.size());
EXPECT_DOUBLE_EQ(-1.5, coordinate[0]); EXPECT_DOUBLE_EQ(-1.5, coordinate[0]);
...@@ -34,7 +36,7 @@ TEST(PositionInterpTest, FourCoordinates) { ...@@ -34,7 +36,7 @@ TEST(PositionInterpTest, FourCoordinates) {
{-27, -8, -1, 0, 1, 8}, {-27, -8, -1, 0, 1, 8},
{ 25, 0, -5, 25, 3, 6}}; { 25, 0, -5, 25, 3, 6}};
EXPECT_THROW(ale::getPosition(data, times, 0.0, ale::linear), EXPECT_THROW(ale::getPosition(data, times, 0.0, ale::LINEAR),
invalid_argument); invalid_argument);
} }
...@@ -43,13 +45,13 @@ TEST(LinearInterpTest, ExampleInterpolation) { ...@@ -43,13 +45,13 @@ TEST(LinearInterpTest, ExampleInterpolation) {
vector<double> times = {0, 1, 2, 3}; vector<double> times = {0, 1, 2, 3};
vector<double> data = {0, 2, 1, 0}; vector<double> data = {0, 2, 1, 0};
EXPECT_DOUBLE_EQ(0.0, ale::interpolate(data, times, 0.0, ale::linear, 0)); EXPECT_DOUBLE_EQ(0.0, ale::interpolate(data, times, 0.0, ale::LINEAR, 0));
EXPECT_DOUBLE_EQ(1.0, ale::interpolate(data, times, 0.5, ale::linear, 0)); EXPECT_DOUBLE_EQ(1.0, ale::interpolate(data, times, 0.5, ale::LINEAR, 0));
EXPECT_DOUBLE_EQ(2.0, ale::interpolate(data, times, 1.0, ale::linear, 0)); EXPECT_DOUBLE_EQ(2.0, ale::interpolate(data, times, 1.0, ale::LINEAR, 0));
EXPECT_DOUBLE_EQ(1.5, ale::interpolate(data, times, 1.5, ale::linear, 0)); EXPECT_DOUBLE_EQ(1.5, ale::interpolate(data, times, 1.5, ale::LINEAR, 0));
EXPECT_DOUBLE_EQ(1.0, ale::interpolate(data, times, 2.0, ale::linear, 0)); EXPECT_DOUBLE_EQ(1.0, ale::interpolate(data, times, 2.0, ale::LINEAR, 0));
EXPECT_DOUBLE_EQ(0.5, ale::interpolate(data, times, 2.5, ale::linear, 0)); EXPECT_DOUBLE_EQ(0.5, ale::interpolate(data, times, 2.5, ale::LINEAR, 0));
EXPECT_DOUBLE_EQ(0.0, ale::interpolate(data, times, 3.0, ale::linear, 0)); EXPECT_DOUBLE_EQ(0.0, ale::interpolate(data, times, 3.0, ale::LINEAR, 0));
} }
...@@ -57,7 +59,7 @@ TEST(LinearInterpTest, NoPoints) { ...@@ -57,7 +59,7 @@ TEST(LinearInterpTest, NoPoints) {
vector<double> times = {}; vector<double> times = {};
vector<double> data = {}; vector<double> data = {};
EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::linear, 0), EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::LINEAR, 0),
invalid_argument); invalid_argument);
} }
...@@ -66,7 +68,7 @@ TEST(LinearInterpTest, DifferentCounts) { ...@@ -66,7 +68,7 @@ TEST(LinearInterpTest, DifferentCounts) {
vector<double> times = { -3, -2, -1, 0, 2}; vector<double> times = { -3, -2, -1, 0, 2};
vector<double> data = { -3, -2, 1, 2}; vector<double> data = { -3, -2, 1, 2};
EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::linear, 0), EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::LINEAR, 0),
invalid_argument); invalid_argument);
} }
...@@ -75,9 +77,9 @@ TEST(LinearInterpTest, Extrapolate) { ...@@ -75,9 +77,9 @@ TEST(LinearInterpTest, Extrapolate) {
vector<double> times = {0, 1, 2, 3}; vector<double> times = {0, 1, 2, 3};
vector<double> data = {0, 2, 1, 0}; vector<double> data = {0, 2, 1, 0};
EXPECT_THROW(ale::interpolate(data, times, -1.0, ale::linear, 0), EXPECT_THROW(ale::interpolate(data, times, -1.0, ale::LINEAR, 0),
invalid_argument); invalid_argument);
EXPECT_THROW(ale::interpolate(data, times, 4.0, ale::linear, 0), EXPECT_THROW(ale::interpolate(data, times, 4.0, ale::LINEAR, 0),
invalid_argument); invalid_argument);
} }
...@@ -93,16 +95,16 @@ TEST(SplineInterpTest, ExampleInterpolation) { ...@@ -93,16 +95,16 @@ TEST(SplineInterpTest, ExampleInterpolation) {
// The spline interpolation is only ~1e-10 so we have to define a tolerance // The spline interpolation is only ~1e-10 so we have to define a tolerance
double tolerance = 1e-10; double tolerance = 1e-10;
EXPECT_NEAR(0.0, ale::interpolate(data, times, 0.0, ale::spline, 0), tolerance); EXPECT_NEAR(0.0, ale::interpolate(data, times, 0.0, ale::SPLINE, 0), tolerance);
EXPECT_NEAR(2.8 * 0.5 - 0.8 * 0.125, EXPECT_NEAR(2.8 * 0.5 - 0.8 * 0.125,
ale::interpolate(data, times, 0.5, ale::spline, 0), tolerance); ale::interpolate(data, times, 0.5, ale::SPLINE, 0), tolerance);
EXPECT_NEAR(2.0, ale::interpolate(data, times, 1.0, ale::spline, 0), tolerance); EXPECT_NEAR(2.0, ale::interpolate(data, times, 1.0, ale::SPLINE, 0), tolerance);
EXPECT_NEAR(3.375 - 5.4 * 2.25 + 8.2 * 1.5 - 1.8, EXPECT_NEAR(3.375 - 5.4 * 2.25 + 8.2 * 1.5 - 1.8,
ale::interpolate(data, times, 1.5, ale::spline, 0), tolerance); ale::interpolate(data, times, 1.5, ale::SPLINE, 0), tolerance);
EXPECT_NEAR(1.0, ale::interpolate(data, times, 2.0, ale::spline, 0), tolerance); EXPECT_NEAR(1.0, ale::interpolate(data, times, 2.0, ale::SPLINE, 0), tolerance);
EXPECT_NEAR(-0.2 * 15.625 + 1.8 * 6.25 - 6.2 * 2.5 + 7.8, EXPECT_NEAR(-0.2 * 15.625 + 1.8 * 6.25 - 6.2 * 2.5 + 7.8,
ale::interpolate(data, times, 2.5, ale::spline, 0), tolerance); ale::interpolate(data, times, 2.5, ale::SPLINE, 0), tolerance);
EXPECT_NEAR(0.0, ale::interpolate(data, times, 3.0, ale::spline, 0), tolerance); EXPECT_NEAR(0.0, ale::interpolate(data, times, 3.0, ale::SPLINE, 0), tolerance);
} }
...@@ -110,7 +112,7 @@ TEST(SplineInterpTest, NoPoints) { ...@@ -110,7 +112,7 @@ TEST(SplineInterpTest, NoPoints) {
vector<double> times = {}; vector<double> times = {};
vector<double> data = {}; vector<double> data = {};
EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::spline, 0), EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::SPLINE, 0),
invalid_argument); invalid_argument);
} }
...@@ -119,7 +121,7 @@ TEST(SplineInterpTest, DifferentCounts) { ...@@ -119,7 +121,7 @@ TEST(SplineInterpTest, DifferentCounts) {
vector<double> times = { -3, -2, -1, 0, 2}; vector<double> times = { -3, -2, -1, 0, 2};
vector<double> data = { -3, -2, 1, 2}; vector<double> data = { -3, -2, 1, 2};
EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::spline, 0), EXPECT_THROW(ale::interpolate(data, times, 0.0, ale::SPLINE, 0),
invalid_argument); invalid_argument);
} }
...@@ -128,9 +130,9 @@ TEST(SplineInterpTest, Extrapolate) { ...@@ -128,9 +130,9 @@ TEST(SplineInterpTest, Extrapolate) {
vector<double> times = {0, 1, 2, 3}; vector<double> times = {0, 1, 2, 3};
vector<double> data = {0, 2, 1, 0}; vector<double> data = {0, 2, 1, 0};
EXPECT_THROW(ale::interpolate(data, times, -1.0, ale::spline, 0), EXPECT_THROW(ale::interpolate(data, times, -1.0, ale::SPLINE, 0),
invalid_argument); invalid_argument);
EXPECT_THROW(ale::interpolate(data, times, 4.0, ale::spline, 0), EXPECT_THROW(ale::interpolate(data, times, 4.0, ale::SPLINE, 0),
invalid_argument); invalid_argument);
} }
...@@ -283,18 +285,23 @@ TEST(RotationInterpTest, ExampleGetRotation) { ...@@ -283,18 +285,23 @@ TEST(RotationInterpTest, ExampleGetRotation) {
// simple test, only checks if API hit correctly and output is normalized // simple test, only checks if API hit correctly and output is normalized
vector<double> times = {0, 1, 2, 3}; vector<double> times = {0, 1, 2, 3};
vector<vector<double>> rots({{1,1,1,1}, {0,0,0,0}, {1,1,1,1}, {0,0,0,0}}); vector<vector<double>> rots({{1,1,1,1}, {0,0,0,0}, {1,1,1,1}, {0,0,0,0}});
vector<double> r = ale::getRotation(rots, times, 2, ale::linear); vector<double> r = ale::getRotation(rots, times, 2, ale::LINEAR);
Eigen::Quaterniond quat(r[0], r[1], r[2], r[3]); Eigen::Quaterniond quat(r[0], r[1], r[2], r[3]);
EXPECT_DOUBLE_EQ(1, quat.norm()); EXPECT_DOUBLE_EQ(1, quat.norm());
} }
TEST(RotationInterpTest, GetRotationDifferentCounts) { TEST(RotationInterpTest, GetRotationDifferentCounts) {
// incorrect params // incorrect params
vector<double> times = {0, 1, 2}; vector<double> times = {0, 1, 2};
vector<vector<double>> rots({{1,1,1,1}, {0,0,0,0}, {1,1,1,1}, {0,0,0,0}}); vector<vector<double>> rots({{1,1,1,1}, {0,0,0,0}, {1,1,1,1}, {0,0,0,0}});
EXPECT_THROW(ale::getRotation(rots, times, 2, ale::linear), invalid_argument); EXPECT_THROW(ale::getRotation(rots, times, 2, ale::LINEAR), invalid_argument);
}
TEST(RotationInterpTest, InvalidTime) {
vector<double> times = {0, 1, 2};
vector<vector<double>> rots({{1,1,1,1}, {0,0,0,0}, {1,1,1,1}});
EXPECT_THROW(ale::getRotation(rots, times, 3, ale::LINEAR), invalid_argument);
} }
TEST(PyInterfaceTest, LoadInvalidLabel) { TEST(PyInterfaceTest, LoadInvalidLabel) {
...@@ -310,9 +317,48 @@ TEST(PyInterfaceTest, LoadValidLabel) { ...@@ -310,9 +317,48 @@ TEST(PyInterfaceTest, LoadValidLabel) {
TEST(AngularVelocityInterpTest, ExampleGetRotation) { TEST(AngularVelocityInterpTest, ExampleGetRotation) {
vector<double> times = {0, 1}; vector<double> times = {0, 1};
vector<vector<double>> rots({{0,0}, {1,0}, {0,1}, {0,0}}); vector<vector<double>> rots({{0,0}, {1,0}, {0,1}, {0,0}});
vector<double> av = ale::getAngularVelocity(rots, times, 0.5, ale::linear); vector<double> av = ale::getAngularVelocity(rots, times, 0.5, ale::LINEAR);
EXPECT_DOUBLE_EQ(0, av[0]); EXPECT_DOUBLE_EQ(0, av[0]);
EXPECT_DOUBLE_EQ(0, av[1]); EXPECT_DOUBLE_EQ(0, av[1]);
EXPECT_DOUBLE_EQ(2 * sqrt(2), av[2]); EXPECT_DOUBLE_EQ(2 * sqrt(2), av[2]);
} }
TEST(AngularVelocityInterpTest, InvalidTime) {
vector<double> times = {0, 1, 2};
vector<vector<double>> rots({{0,0}, {1,0}, {0,1}, {0,0}});
EXPECT_THROW(ale::getAngularVelocity(rots, times, 3, ale::LINEAR), invalid_argument);
}
TEST(VelocityInterpTest, ExampleGetVelocity) {
vector<double> times = {0, 1, 2};
vector<vector<double>> coords({{1, 1, 1}, {2, 2, 2}, {3, 3, 3}});
vector<double> v = ale::getVelocity(coords, times, 1, ale::LINEAR);
//not sure what the values are expected to look like
EXPECT_DOUBLE_EQ(v[0], 0);
EXPECT_DOUBLE_EQ(v[1], 0);
EXPECT_DOUBLE_EQ(v[2], 0);
}
TEST(VelocityInterpTest, InvalidTime) {
vector<double> times = {0, 1, 2};
vector<vector<double>> coords({{1, 1, 1}, {2, 2, 2}, {3, 3, 3}});
EXPECT_THROW(ale::getVelocity(coords, times, 3, ale::LINEAR), invalid_argument);
}
TEST(Interpolation, Derivative2)
{
//only checks that case 2 of the switch block is hit
vector<double> points = {0, 0, 0};
vector<double> times = {0, 1, 2};
EXPECT_DOUBLE_EQ(ale::interpolate(points, times, 1, ale::LINEAR, 2), 0);
}
TEST(Interpolation, InvalidDerivative) {
vector<double> points = {0, 0, 0};
vector<double> times = {0, 1, 2};
EXPECT_THROW(ale::interpolate(points, times, 1, ale::LINEAR, 3), invalid_argument);
}
This diff is collapsed.
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment