133 lines
5.8 KiB
C++
Executable File
133 lines
5.8 KiB
C++
Executable File
#ifndef FLATPATTERNGEOMETRY_HPP
|
|
#define FLATPATTERNGEOMETRY_HPP
|
|
#include "edgemesh.hpp"
|
|
#include <string>
|
|
#include <unordered_map>
|
|
#include <unordered_set>
|
|
#include "vcgtrimesh.hpp"
|
|
#include "polymesh.hpp"
|
|
|
|
class PatternGeometry;
|
|
using ConstPatternGeometry = PatternGeometry;
|
|
|
|
class PatternGeometry : public VCGEdgeMesh
|
|
{
|
|
private:
|
|
size_t
|
|
computeTiledValence(const size_t &nodeIndex,
|
|
const std::vector<size_t> &numberOfNodesPerSlot) const;
|
|
size_t getNodeValence(const size_t &nodeIndex) const;
|
|
size_t getNodeSlot(const size_t &nodeIndex) const;
|
|
|
|
void addNormals();
|
|
double baseTriangleHeight;
|
|
double computeBaseTriangleHeight() const;
|
|
|
|
inline static size_t fanSize{6};
|
|
std::vector<VCGEdgeMesh::CoordType> vertices;
|
|
const double triangleEdgeSize{1}; // radius edge
|
|
std::unordered_map<size_t, size_t> nodeToSlotMap;
|
|
std::unordered_map<size_t, size_t> correspondingNode;
|
|
std::unordered_map<size_t, size_t> nodeTiledValence;
|
|
vcg::Triangle3<double> baseTriangle;
|
|
|
|
void
|
|
constructCorrespondingNodeMap(const std::vector<size_t> &numberOfNodesPerSlot);
|
|
|
|
void constructNodeToTiledValenceMap(const std::vector<size_t> &numberOfNodesPerSlot);
|
|
|
|
std::vector<VectorType> getEdgeVectorsWithVertexAsOrigin(std::vector<EdgePointer> &edgePointers,
|
|
const int &vi);
|
|
|
|
public:
|
|
PatternGeometry();
|
|
/*The following function should be a copy constructor with
|
|
* a const argument but this is impossible due to the
|
|
* vcglib interface.
|
|
* */
|
|
PatternGeometry(PatternGeometry &other);
|
|
bool load(const std::filesystem::path &meshFilePath) override;
|
|
void add(const std::vector<vcg::Point3d> &vertices);
|
|
void add(const std::vector<vcg::Point2i> &edges);
|
|
void add(const std::vector<vcg::Point3d> &vertices, const std::vector<vcg::Point2i> &edges);
|
|
void add(const std::vector<size_t> &numberOfNodesPerSlot,
|
|
const std::vector<vcg::Point2i> &edges);
|
|
static std::vector<vcg::Point3d>
|
|
constructVertexVector(const std::vector<size_t> &numberOfNodesPerSlot,
|
|
const size_t &fanSize, const double &triangleEdgeSize);
|
|
bool hasDanglingEdges(const std::vector<size_t> &numberOfNodesPerSlot);
|
|
bool hasValenceGreaterThan(const std::vector<size_t> &numberOfNodesPerSlot,
|
|
const size_t &valenceThreshold);
|
|
std::vector<vcg::Point3d> getVertices() const;
|
|
static PatternGeometry createFan(PatternGeometry &pattern);
|
|
static PatternGeometry createTile(PatternGeometry &pattern);
|
|
double getTriangleEdgeSize() const;
|
|
bool hasUntiledDanglingEdges();
|
|
std::unordered_map<size_t, std::unordered_set<size_t>>
|
|
getIntersectingEdges(size_t &numberOfIntersectingEdgePairs) const;
|
|
|
|
static size_t binomialCoefficient(size_t n, size_t m) {
|
|
assert(n >= m);
|
|
return tgamma(n + 1) / (tgamma(m + 1) * tgamma(n - m + 1));
|
|
}
|
|
bool isFullyConnectedWhenFanned();
|
|
|
|
bool hasIntersectingEdges(
|
|
const std::string &patternBinaryRepresentation,
|
|
const std::unordered_map<size_t, std::unordered_set<size_t>>
|
|
&intersectingEdges);
|
|
bool isPatternValid();
|
|
size_t getFanSize() const;
|
|
void add(const std::vector<vcg::Point2d> &vertices,
|
|
const std::vector<vcg::Point2i> &edges);
|
|
|
|
PatternGeometry(const std::vector<size_t> &numberOfNodesPerSlot,
|
|
const std::vector<vcg::Point2i> &edges);
|
|
PatternGeometry(const std::string &filename, bool addNormalsIfAbsent = true);
|
|
|
|
bool createHoneycombAtom();
|
|
void copy(PatternGeometry ©From);
|
|
|
|
void tilePattern(VCGEdgeMesh &pattern,
|
|
VCGPolyMesh &tileInto,
|
|
const int &interfaceNodeIndex,
|
|
const bool &shouldDeleteDanglingEdges);
|
|
|
|
void scale(const double &desiredBaseTriangleCentralEdgeSize, const int &interfaceNodeIndex);
|
|
|
|
double getBaseTriangleHeight() const;
|
|
vcg::Triangle3<double> computeBaseTriangle() const;
|
|
|
|
PatternGeometry(const std::vector<vcg::Point2d> &vertices, const std::vector<vcg::Point2i> &edges);
|
|
// static std::shared_ptr<PatternGeometry> tilePattern(
|
|
// std::vector<PatternGeometry> &pattern,
|
|
// const std::vector<int> &connectToNeighborsVi,
|
|
// const VCGPolyMesh &tileInto,
|
|
// std::vector<int> &tileIntoEdgesToTiledVi,
|
|
// std::vector<std::vector<size_t>> &perPatternEdges);
|
|
void createFan(const std::vector<int> &connectToNeighborsVi = std::vector<int>(),
|
|
const size_t &fanSize = 6);
|
|
int interfaceNodeIndex{3}; //TODO: Fix this. This should be automatically computed
|
|
bool hasAngleSmallerThanThreshold(const std::vector<size_t> &numberOfNodesPerSlot,
|
|
const double &angleThreshold_degrees);
|
|
vcg::Triangle3<double> getBaseTriangle() const;
|
|
static std::shared_ptr<PatternGeometry> tilePattern(PatternGeometry &pattern,
|
|
const std::vector<int> &connectToNeighborsVi,
|
|
const VCGPolyMesh &tileInto,
|
|
std::vector<int> &tileIntoEdgesToTiledVi);
|
|
static std::shared_ptr<PatternGeometry> tilePattern(
|
|
std::vector<ConstPatternGeometry> &patterns,
|
|
const std::vector<int> &connectToNeighborsVi,
|
|
const VCGPolyMesh &tileInto,
|
|
const std::vector<int> &perSurfaceFacePatternIndices,
|
|
std::vector<size_t> &tileIntoEdgesToTiledVi,
|
|
std::vector<std::vector<size_t>> &perPatternIndexTiledPatternEdgeIndex);
|
|
std::unordered_set<VertexIndex> getInterfaceNodes(const std::vector<size_t> &numberOfNodesPerSlot);
|
|
bool isInterfaceConnected(const std::unordered_set<VertexIndex> &interfaceNodes);
|
|
void deleteDanglingVertices() override;
|
|
void deleteDanglingVertices(
|
|
vcg::tri::Allocator<VCGEdgeMesh>::PointerUpdater<VertexPointer> &pu) override;
|
|
};
|
|
|
|
#endif // FLATPATTERNGEOMETRY_HPP
|