151 lines
5.4 KiB
C++
151 lines
5.4 KiB
C++
#include <set>
|
|
#include "monochrome_mesh.h"
|
|
|
|
MonochromeMesh::MonochromeMesh(const MonochromeMesh &mesh)
|
|
{
|
|
m_lineVertices = mesh.m_lineVertices;
|
|
}
|
|
|
|
MonochromeMesh::MonochromeMesh(MonochromeMesh &&mesh)
|
|
{
|
|
m_lineVertices = std::move(mesh.m_lineVertices);
|
|
}
|
|
|
|
MonochromeMesh::MonochromeMesh(const dust3d::Object &object)
|
|
{
|
|
/*
|
|
auto buildSection = [](const dust3d::Vector3 &origin,
|
|
const dust3d::Vector3 &faceNormal,
|
|
const dust3d::Vector3 &tagent,
|
|
double radius)
|
|
{
|
|
auto upDirection = dust3d::Vector3::crossProduct(tagent, faceNormal);
|
|
return std::vector<dust3d::Vector3> {
|
|
origin + tagent * radius,
|
|
origin - upDirection * radius,
|
|
origin - tagent * radius,
|
|
origin + upDirection * radius
|
|
};
|
|
};
|
|
|
|
auto calculateTagent = [](const dust3d::Vector3 &direction) {
|
|
const std::vector<dust3d::Vector3> axisList = {
|
|
dust3d::Vector3 {1, 0, 0},
|
|
dust3d::Vector3 {0, 1, 0},
|
|
dust3d::Vector3 {0, 0, 1},
|
|
};
|
|
float maxDot = -1;
|
|
size_t nearAxisIndex = 0;
|
|
bool reversed = false;
|
|
for (size_t i = 0; i < axisList.size(); ++i) {
|
|
const auto axis = axisList[i];
|
|
auto dot = dust3d::Vector3::dotProduct(axis, direction);
|
|
auto positiveDot = std::abs(dot);
|
|
if (positiveDot >= maxDot) {
|
|
reversed = dot < 0;
|
|
maxDot = positiveDot;
|
|
nearAxisIndex = i;
|
|
}
|
|
}
|
|
const auto& choosenAxis = axisList[(nearAxisIndex + 1) % 3];
|
|
auto startDirection = dust3d::Vector3::crossProduct(direction, choosenAxis).normalized();
|
|
return reversed ? -startDirection : startDirection;
|
|
};
|
|
*/
|
|
std::set<std::pair<size_t, size_t>> halfEdges;
|
|
for (const auto &face: object.triangleAndQuads) {
|
|
if (3 == face.size()) {
|
|
halfEdges.insert({face[0], face[1]});
|
|
halfEdges.insert({face[1], face[0]});
|
|
halfEdges.insert({face[1], face[2]});
|
|
halfEdges.insert({face[2], face[1]});
|
|
halfEdges.insert({face[2], face[0]});
|
|
halfEdges.insert({face[0], face[2]});
|
|
continue;
|
|
}
|
|
halfEdges.insert({face[0], face[1]});
|
|
halfEdges.insert({face[1], face[0]});
|
|
halfEdges.insert({face[1], face[2]});
|
|
halfEdges.insert({face[2], face[1]});
|
|
halfEdges.insert({face[2], face[3]});
|
|
halfEdges.insert({face[3], face[2]});
|
|
halfEdges.insert({face[3], face[0]});
|
|
halfEdges.insert({face[0], face[3]});
|
|
}
|
|
//m_triangleVertices.reserve(halfEdges.size() * 24);
|
|
m_lineVertices.reserve(halfEdges.size() * 2);
|
|
for (const auto &halfEdge: halfEdges) {
|
|
// For two halfedges shared one edge, only output one line
|
|
if (halfEdge.first > halfEdge.second)
|
|
continue;
|
|
const auto &from = object.vertices[halfEdge.first];
|
|
const auto &to = object.vertices[halfEdge.second];
|
|
m_lineVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)from.x(),
|
|
(GLfloat)from.y(),
|
|
(GLfloat)from.z()
|
|
});
|
|
m_lineVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)to.x(),
|
|
(GLfloat)to.y(),
|
|
(GLfloat)to.z()
|
|
});
|
|
/*
|
|
auto direction = to - from;
|
|
auto sectionNormal = direction.normalized();
|
|
auto sectionTagent = calculateTagent(sectionNormal);
|
|
auto sectionTo = buildSection(to, sectionNormal, sectionTagent, 0.002);
|
|
auto sectionFrom = sectionTo;
|
|
for (auto &it: sectionFrom)
|
|
it = it - direction;
|
|
|
|
for (size_t i = 0; i < sectionTo.size(); ++i) {
|
|
size_t j = (i + 1) % sectionTo.size();
|
|
m_triangleVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)sectionTo[i].x(),
|
|
(GLfloat)sectionTo[i].y(),
|
|
(GLfloat)sectionTo[i].z()
|
|
});
|
|
m_triangleVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)sectionFrom[i].x(),
|
|
(GLfloat)sectionFrom[i].y(),
|
|
(GLfloat)sectionFrom[i].z()
|
|
});
|
|
m_triangleVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)sectionTo[j].x(),
|
|
(GLfloat)sectionTo[j].y(),
|
|
(GLfloat)sectionTo[j].z()
|
|
});
|
|
|
|
m_triangleVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)sectionFrom[i].x(),
|
|
(GLfloat)sectionFrom[i].y(),
|
|
(GLfloat)sectionFrom[i].z()
|
|
});
|
|
m_triangleVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)sectionFrom[j].x(),
|
|
(GLfloat)sectionFrom[j].y(),
|
|
(GLfloat)sectionFrom[j].z()
|
|
});
|
|
m_triangleVertices.emplace_back(MonochromeOpenGLVertex {
|
|
(GLfloat)sectionTo[j].x(),
|
|
(GLfloat)sectionTo[j].y(),
|
|
(GLfloat)sectionTo[j].z()
|
|
});
|
|
}
|
|
*/
|
|
}
|
|
}
|
|
|
|
const MonochromeOpenGLVertex *MonochromeMesh::lineVertices()
|
|
{
|
|
if (m_lineVertices.empty())
|
|
return nullptr;
|
|
return &m_lineVertices[0];
|
|
}
|
|
|
|
int MonochromeMesh::lineVertexCount()
|
|
{
|
|
return (int)m_lineVertices.size();
|
|
}
|