Commit 1fcb7205 authored by JasonPries's avatar JasonPries
Browse files

Translate Pattern tests

Split Pattern.h/Pattern.cpp into multiple h/cpp files
Translate tests for LineSegment/CircularArc method "split()"
parent 63712da2
......@@ -11,6 +11,7 @@
<sourceFolder url="file://$MODULE_DIR$/CMakeLists.txt" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/CMakeLists.txt" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Angle.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Vertical.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Sketch.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Coincident.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Vertical.cpp" isTestSource="false" />
......@@ -18,7 +19,7 @@
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Vertex.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Curve.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Pattern.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Radius.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Length.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Coincident.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Constellation.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Radius.cpp" isTestSource="false" />
......@@ -30,35 +31,39 @@
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Rotation.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Branch.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Branch.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Length.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/RotateCopy.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Constraint.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Star.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Symmetry.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Constraint.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Length.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Length.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Constellation.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Contour.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Fixation.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Vertical.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Radius.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Horizontal.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/CircularArc.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Distance.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Symmetry.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Distance.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Symmetry.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/MirrorCopy.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Pattern.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Star.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/LineSegment.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/MirrorCopy.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Fixation.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Sketch.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/RotateCopy.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Tangency.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Contour.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Pattern.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Distance.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Rotation.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/Horizontal.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/src/CircularArc.h" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/include/Sketch.hpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/src/Sketch/CMakeLists.txt" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/main.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/CMakeLists.txt" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/Sketch/test_LineSegment.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/Sketch/test_Pattern.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/Sketch/test_Sketch.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/Sketch/test_Constraint.cpp" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/Sketch/test_CircularArc.cpp" isTestSource="false" />
......
PROJECT(Oersted_Sketch)
set(SOURCE_FILES
./include/Sketch.hpp ./src/Sketch.h ./src/Sketch.cpp
./include/Sketch.hpp
./src/Vertex.h ./src/Vertex.cpp
./src/Sketch.h ./src/Sketch.cpp
./src/Curve.h ./src/Curve.cpp
./src/Vertex.h ./src/Vertex.cpp
./src/Curve.h ./src/Curve.cpp
./src/LineSegment.h ./src/LineSegment.cpp
./src/CircularArc.h ./src/CircularArc.cpp
./src/Constraint.h ./src/Constraint.cpp
./src/Constraint.h ./src/Constraint.cpp
./src/Angle.h ./src/Angle.cpp
./src/Coincident.cpp ./src/Coincident.h
./src/Distance.cpp ./src/Distance.h
./src/Fixation.cpp ./src/Fixation.h
./src/Horizontal.cpp ./src/Horizontal.h
./src/Length.cpp ./src/Length.h
./src/Radius.cpp ./src/Radius.h
./src/Rotation.cpp ./src/Rotation.h
./src/Symmetry.cpp ./src/Symmetry.h
./src/Tangency.cpp ./src/Tangency.h
./src/Vertical.cpp ./src/Vertical.h
./src/Pattern.h ./src/Pattern.cpp
./src/MirrorCopy.cpp ./src/MirrorCopy.h
./src/RotateCopy.cpp ./src/RotateCopy.h
./src/Branch.h ./src/Branch.cpp
./src/Star.h ./src/Star.cpp
./src/Constellation.h ./src/Constellation.cpp
./src/Branch.h ./src/Branch.cpp
./src/Star.h ./src/Star.cpp
./src/Constellation.h ./src/Constellation.cpp
./src/Contour.h ./src/Contour.cpp src/Horizontal.cpp src/Horizontal.h src/Length.cpp src/Length.h src/Radius.cpp src/Radius.h src/Rotation.cpp src/Rotation.h src/Symmetry.cpp src/Symmetry.h src/Tangency.cpp src/Tangency.h src/Vertical.cpp src/Vertical.h)
./src/Contour.h ./src/Contour.cpp)
add_library(sketch STATIC ${SOURCE_FILES})
......
......@@ -19,5 +19,4 @@ public:
void update(Eigen::MatrixXd &J, Eigen::VectorXd &r) override;
};
#endif //OERSTED_ANGLE_H
#endif //OERSTED_ANGLE_H
\ No newline at end of file
......@@ -21,5 +21,4 @@ public:
#include "Tangency.h"
#include "Vertical.h"
#endif //OERSTED_CONSTRAINT_H
\ No newline at end of file
#include "Sketch.hpp"
MirrorCopy::MirrorCopy(std::vector<const Curve *> &input, LineSegment *l) {
// Creates mirror copies of the input curves about a line
// Assign Properties
Input = input;
SymmetryLine = l;
// Clone input curves and create a list of unique input verticies
Curves.reserve(Input.size());
std::list<Vertex *> input_vlist;
for (auto c : Input) {
if (!(l->is_coincident(c))) {
Curves.push_back(c->clone());
c->get_verticies(input_vlist);
}
}
input_vlist.sort();
input_vlist.unique();
// Mirror input verticies
double x0 = l->start()->x();
double y0 = l->start()->y();
double dx = l->end()->x() - x0;
double dy = l->end()->y() - y0;
double d = sqrt(dx * dx + dy * dy);
dx /= d;
dy /= d;
Verticies.reserve(input_vlist.size());
auto v = input_vlist.begin();
while (v != input_vlist.end()) {
double x = (*v)->x();
double y = (*v)->y();
double px = x - x0;
double py = y - y0;
double pd = dx * px + dy * py;
px -= pd * dx;
py -= pd * dy;
if (sqrt(px * px + py * py) > d * FLT_EPSILON) {
px = x - 2.0 * px;
py = y - 2.0 * py;
Verticies.push_back(new Vertex(px, py));
++v;
} else {
v = input_vlist.erase(v);
}
}
// Replace verticies in mirror curves
std::vector<Vertex *> input_vvector{input_vlist.begin(), input_vlist.end()};
for (auto c : Curves) {
c->replace_verticies(input_vvector, Verticies);
c->reverse();
}
// Constrain mirrored verticies to be symmetric about the SymmetryLine
Constraints.reserve(Verticies.size());
for (size_t i = 0; i != Verticies.size(); ++i) {
Constraints.push_back(new Symmetry(*input_vvector[i], *Verticies[i], *SymmetryLine));
}
}
\ No newline at end of file
#ifndef OERSTED_MIRRORCOPY_H
#define OERSTED_MIRRORCOPY_H
#include "Pattern.h"
class MirrorCopy : public Pattern {
public:
MirrorCopy(std::vector<const Curve *> &input, LineSegment *l);
private:
LineSegment *SymmetryLine;
};
#endif //OERSTED_MIRRORCOPY_H
\ No newline at end of file
#include "Sketch.hpp"
// Pattern
void Pattern::register_elements(Sketch *s) {
for (auto v : Verticies) {
s->add_element(*v);
......@@ -13,196 +12,4 @@ void Pattern::register_elements(Sketch *s) {
for (auto c : Constraints) {
s->add_element(*c);
}
}
// MirrorCopy
MirrorCopy::MirrorCopy(std::vector<const Curve *> &input, LineSegment *l) {
// Creates mirror copies of the input curves about a line
// Assign Properties
Input = input;
SymmetryLine = l;
// Clone input curves and create a list of unique input verticies
Curves.reserve(Input.size());
std::list<Vertex *> input_vlist;
for (auto c : Input) {
if (!(l->is_coincident(c))) {
Curves.push_back(c->clone());
c->get_verticies(input_vlist);
}
}
input_vlist.sort();
input_vlist.unique();
// Mirror input verticies
double x0 = l->start()->x();
double y0 = l->start()->y();
double dx = l->end()->x() - x0;
double dy = l->end()->y() - y0;
double d = sqrt(dx * dx + dy * dy);
dx /= d;
dy /= d;
Verticies.reserve(input_vlist.size());
auto v = input_vlist.begin();
while (v != input_vlist.end()) {
double x = (*v)->x();
double y = (*v)->y();
double px = x - x0;
double py = y - y0;
double pd = dx * px + dy * py;
px -= pd * dx;
py -= pd * dy;
if (sqrt(px * px + py * py) > d * FLT_EPSILON) {
px = x - 2.0 * px;
py = y - 2.0 * py;
Verticies.push_back(new Vertex(px, py));
++v;
} else {
v = input_vlist.erase(v);
}
}
// Replace verticies in mirror curves
std::vector<Vertex *> input_vvector{input_vlist.begin(), input_vlist.end()};
for (auto c : Curves) {
c->replace_verticies(input_vvector, Verticies);
c->reverse();
}
// Constrain mirrored verticies to be symmetric about the SymmetryLine
Constraints.reserve(Verticies.size());
for (size_t i = 0; i != Verticies.size(); ++i) {
Constraints.push_back(new Symmetry(*input_vvector[i], *Verticies[i], *SymmetryLine));
}
}
RotateCopy::RotateCopy(std::vector<const Curve *> &input, Vertex *center, double angle, size_t copies) {
// Creates rotated copies of the input curves about an vertex
// #TODO: Need to rearrange code and reserve vector sizes in a way that makes more sense (much code copied from MirrorCopy constructor)
// #TODO: Restructure to obviate the need for local_curves and local_verticies
// #TODO: Three Groups: Leading Curves, Lagging Curves, Internal Curves
// #TODO: Three Groups (?): Leading Verticies, Lagging Verticies, Internal Verticies
// Assign properties
Input = input;
Center = center;
Angle = angle;
Copies = copies;
Curves.reserve(copies * input.size());
Verticies.reserve(3 * copies * input.size());
Constraints.reserve(3 * copies * input.size());
// Reserve Local Vectors
std::vector<Curve *> local_curves;
local_curves.reserve(Input.size());
std::vector<Vertex *> local_verticies;
local_verticies.reserve(Input.size() * 2);
std::list<Vertex *> input_vlist;
for (size_t i = 0; i != Copies; ++i) {
local_curves.clear();
local_verticies.clear();
input_vlist.clear();
// Clone input curves and create a list of unique input verticies
for (auto c : Input) {
local_curves.push_back(c->clone());
Curves.push_back(local_curves.back());
c->get_verticies(input_vlist);
}
input_vlist.sort();
input_vlist.unique();
// Rewrite
/*
// Get local curves
for (auto c : Input) {
local_curves.push_back(c->clone());
}
// Erase corotational curves
for (size_t j = 0;j != local_curves.size();++j) {
auto k = local_curves.begin();
while (k != local_curves.end()) {
if (local_curves[j].is_corotational(*k, center, angle)) {
k = local_curves.erase(k);
}
else {
++k;
}
}
}
// Get local verticies
for (auto c : local_curves) {
c->get_verticies(input_vlist);
}
// Erase corotational verticies
for (size_t j = 0;j != input_vlist.size();++j) {
auto k = input_vlist.end();
while (k != input_vlist.end()) {
if (input_vlist[j].is_corotational(*k, center, angle)) {
k = input_vlist.erase(k);
}
else {
++k;
}
}
}
*/
// Erase center if it exists
auto j = std::find(input_vlist.begin(), input_vlist.end(), center);
if (j != input_vlist.end()) {
input_vlist.erase(j);
}
// Rotate input verticies
double a = (i + 1.0) * Angle * M_PI / 180.0;
double cosa = cos(a);
double sina = sin(a);
double x0 = Center->x();
double y0 = Center->y();
auto v = input_vlist.begin();
while (v != input_vlist.end()) {
double dx = (*v)->x() - x0;
double dy = (*v)->y() - y0;
double vx = cosa * dx - sina * dy + x0;
double vy = sina * dx + cosa * dy + y0;
local_verticies.push_back(new Vertex(vx, vy));
Verticies.push_back(local_verticies.back());
v++;
}
// Replace verticies in rotated curves
std::vector<Vertex *> input_vvector{input_vlist.begin(), input_vlist.end()};
for (auto c : local_curves) {
c->replace_verticies(input_vvector, local_verticies);
}
// Constrain rotated verticies to be rotated about the origin
for (size_t j = 0; j != local_verticies.size(); ++j) {
Constraints.push_back(new Rotation(*input_vvector[j], *local_verticies[j], *Center, Angle * (i + 1)));
}
}
// Shrink
Curves.shrink_to_fit();
Verticies.shrink_to_fit();
Constraints.shrink_to_fit();
}
\ No newline at end of file
......@@ -24,22 +24,7 @@ protected:
std::vector<Constraint *> Constraints;
};
class MirrorCopy : public Pattern {
public:
MirrorCopy(std::vector<const Curve *> &input, LineSegment *l);
private:
LineSegment *SymmetryLine;
};
class RotateCopy : public Pattern {
public:
RotateCopy(std::vector<const Curve *> &input, Vertex *center, double angle, size_t copies);
private:
Vertex *Center;
double Angle;
size_t Copies;
};
#include "MirrorCopy.h"
#include "RotateCopy.h"
#endif //OERSTED_PATTERN_H
\ No newline at end of file
#include "Sketch.hpp"
RotateCopy::RotateCopy(std::vector<const Curve *> &input, Vertex *center, double angle, size_t copies) {
// Creates rotated copies of the input curves about an vertex
// #TODO: Need to rearrange code and reserve vector sizes in a way that makes more sense (much code copied from MirrorCopy constructor)
// #TODO: Restructure to obviate the need for local_curves and local_verticies
// #TODO: Three Groups: Leading Curves, Lagging Curves, Internal Curves
// #TODO: Three Groups (?): Leading Verticies, Lagging Verticies, Internal Verticies
// Assign properties
Input = input;
Center = center;
Angle = angle;
Copies = copies;
Curves.reserve(copies * input.size());
Verticies.reserve(3 * copies * input.size());
Constraints.reserve(3 * copies * input.size());
// Reserve Local Vectors
std::vector<Curve *> local_curves;
local_curves.reserve(Input.size());
std::vector<Vertex *> local_verticies;
local_verticies.reserve(Input.size() * 2);
std::list<Vertex *> input_vlist;
for (size_t i = 0; i != Copies; ++i) {
local_curves.clear();
local_verticies.clear();
input_vlist.clear();
// Clone input curves and create a list of unique input verticies
for (auto c : Input) {
local_curves.push_back(c->clone());
Curves.push_back(local_curves.back());
c->get_verticies(input_vlist);
}
input_vlist.sort();
input_vlist.unique();
// Rewrite
/*
// Get local curves
for (auto c : Input) {
local_curves.push_back(c->clone());
}
// Erase corotational curves
for (size_t j = 0;j != local_curves.size();++j) {
auto k = local_curves.begin();
while (k != local_curves.end()) {
if (local_curves[j].is_corotational(*k, center, angle)) {
k = local_curves.erase(k);
}
else {
++k;
}
}
}
// Get local verticies
for (auto c : local_curves) {
c->get_verticies(input_vlist);
}
// Erase corotational verticies
for (size_t j = 0;j != input_vlist.size();++j) {
auto k = input_vlist.end();
while (k != input_vlist.end()) {
if (input_vlist[j].is_corotational(*k, center, angle)) {
k = input_vlist.erase(k);
}
else {
++k;
}
}
}
*/
// Erase center if it exists
auto j = std::find(input_vlist.begin(), input_vlist.end(), center);
if (j != input_vlist.end()) {
input_vlist.erase(j);
}
// Rotate input verticies
double a = (i + 1.0) * Angle * M_PI / 180.0;
double cosa = cos(a);
double sina = sin(a);
double x0 = Center->x();
double y0 = Center->y();
auto v = input_vlist.begin();
while (v != input_vlist.end()) {
double dx = (*v)->x() - x0;
double dy = (*v)->y() - y0;
double vx = cosa * dx - sina * dy + x0;
double vy = sina * dx + cosa * dy + y0;
local_verticies.push_back(new Vertex(vx, vy));
Verticies.push_back(local_verticies.back());
v++;
}
// Replace verticies in rotated curves
std::vector<Vertex *> input_vvector{input_vlist.begin(), input_vlist.end()};
for (auto c : local_curves) {
c->replace_verticies(input_vvector, local_verticies);
}
// Constrain rotated verticies to be rotated about the origin
for (size_t j = 0; j != local_verticies.size(); ++j) {
Constraints.push_back(new Rotation(*input_vvector[j], *local_verticies[j], *Center, Angle * (i + 1)));
}
}
// Shrink
Curves.shrink_to_fit();
Verticies.shrink_to_fit();
Constraints.shrink_to_fit();
}
\ No newline at end of file
#ifndef OERSTED_ROTATECOPY_H
#define OERSTED_ROTATECOPY_H
#include "Pattern.h"
class RotateCopy : public Pattern {
public:
RotateCopy(std::vector<const Curve *> &input, Vertex *center, double angle, size_t copies);
private:
Vertex *Center;
double Angle;
size_t Copies;
};
#endif //OERSTED_ROTATECOPY_H
\ No newline at end of file
......@@ -11,7 +11,8 @@ set(SOURCE_FILES
Sketch/test_Star.cpp
Sketch/test_Contour.cpp
Sketch/test_Sketch.cpp
Sketch/test_Constraint.cpp)
Sketch/test_Constraint.cpp
Sketch/test_Pattern.cpp)
add_executable(run_tests ${SOURCE_FILES})
......
......@@ -480,4 +480,25 @@ TEST(CIRCULARARC, METHOD_is_coincident) {
EXPECT_FALSE(c0.is_coincident(&l0));
}
}
TEST(CIRCULARARC, METHOD_split) {
Vertex v0{1.0, 0.0};
Vertex v1{0.0, 1.0};
Vertex vc{0.0, 0.0};
CircularArc c0{v0, v1, vc, 1.0};
Vertex *vs = new Vertex;
Curve *c1 = c0.split(vs, 0.5);
EXPECT_NEAR(M_SQRT1_2, vs->x(), TOL);
EXPECT_NEAR(M_SQRT1_2, vs->y(), TOL);