-
Notifications
You must be signed in to change notification settings - Fork 1
/
Object3D.cpp
120 lines (103 loc) · 3.84 KB
/
Object3D.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
//
// Created by Jackson Hall on 4/27/2020.
//
#include "Object3D.h"
#include <utility>
/** ========== Constructors ========== */
Object3D::Object3D() :
Object3D(
std::vector<std::shared_ptr<point3d>>(),
std::vector<std::shared_ptr<edge3d>>()
) {
}
//Object3D::Object3D(const std::vector<edge3d>& edges){
// // Add all vertices from given edges to vertices vector
// for (auto & edge : edges){
//
// }
//}
Object3D::Object3D(const std::vector<point3d>& vertices,
const std::vector<edge3d>& edges) {
// Put all items into new vector of smart pointers
std::vector<std::shared_ptr<point3d>> tempVertices;
tempVertices.reserve(vertices.size());
for (auto & vertex : vertices){
tempVertices.push_back(std::make_shared<point3d>(vertex));
}
this->vertices = tempVertices;
std::vector<std::shared_ptr<edge3d>> tempEdges;
tempEdges.reserve(edges.size());
for (auto & edge : edges){
tempEdges.push_back(std::make_unique<edge3d>(edge));
}
this->edges = tempEdges;
}
Object3D::Object3D(std::vector<std::shared_ptr<point3d>> vertices,
std::vector<std::shared_ptr<edge3d>> edges) {
this->vertices = std::move(vertices);
this->edges = std::move(edges);
}
/** ========== Getters ========== */
const std::vector<std::shared_ptr<point3d>>& Object3D::getVertices() const {
return vertices;
}
const std::vector<std::shared_ptr<edge3d>> &Object3D::getEdges() const {
return edges;
}
/** ========== Other Methods ========== */
/**
* Takes the current set of vertices and extrudes them into the given direction,
* creating edges between the appropriate points.
*/
void Object3D::extrude(const spatialVector &direction) {
if (direction.components.size() <= 3){
// Pad empty dimensions in given vector with 0s
std::vector<double> temp = direction.components;
while (temp.size() < 3){
temp.push_back(0.0);
}
// For every edge, extrude both points in the given direction
// and add 3 new edges to this object:
// 1. Between the 2 extruded points
// 2. Between the first point and the extruded first point
// 3. Between the second point and the extruded second point
//
// Make temp vector of the newly created edges so as not to change
// size of vector while looping
std::vector<std::shared_ptr<edge3d>> newEdges;
for (auto & edge : edges){
point3d extrudedP1(*edge->p1);
extrudedP1.move(direction);
point3d extrudedP2(*edge->p2);
extrudedP2.move(direction);
// Add new points
vertices.push_back(std::make_unique<point3d>(extrudedP1));
vertices.push_back(std::make_unique<point3d>(extrudedP2));
// Add new edges
newEdges.push_back(std::make_shared<edge3d>(extrudedP1, extrudedP2));
newEdges.push_back(std::make_shared<edge3d>(*edge->p1, extrudedP1));
newEdges.push_back(std::make_shared<edge3d>(*edge->p2, extrudedP2));
}
// Add the new edges
for (auto & edge : newEdges){
edges.push_back(edge);
}
} else {
std::cout << "Warning: Invalid input to:\n\tvoid extrude(const "
"spatialVector& direction)\n\t(Object3D.cpp)"
<< std::endl;
}
}
/**
* Draw this object on the screen by projecting them through the given
* camera(s).
*/
void Object3D::draw(const Camera3D& camera3d, const Camera4D& camera4d) const {
// Get drawable (x', y') coordinates for all vertices (x, y, z) in object
for (auto & edge : edges){
// Draw a line on the screen between the vertices of the projected edge
edge2d(
*camera3d.projectPoint(*edge->p1), *camera3d.projectPoint(*edge->p2)
).draw();
}
}