You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
126 lines
5.4 KiB
126 lines
5.4 KiB
7 months ago
|
#include "internal_primitive_desc.hpp"
|
||
|
|
||
|
// ===========================================================================
|
||
|
|
||
|
template <typename T>
|
||
|
struct primitive_descriptor_meta;
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<constant_descriptor_t> {
|
||
|
using internal_type = internal::constant;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_CONSTANT;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<plane_descriptor_t> {
|
||
|
using internal_type = internal::plane;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_PLANE;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<sphere_descriptor_t> {
|
||
|
using internal_type = internal::sphere;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_SPHERE;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<cylinder_descriptor_t> {
|
||
|
using internal_type = internal::cylinder;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_CYLINDER;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<cone_descriptor_t> {
|
||
|
using internal_type = internal::cone;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_CONE;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<box_descriptor_t> {
|
||
|
using internal_type = internal::box;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_BOX;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<mesh_descriptor_t> {
|
||
|
using internal_type = internal::mesh;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_MESH;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<extrude_polyline_descriptor_t> {
|
||
|
using internal_type = internal::extrude_polyline;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_EXTRUDE_POLYLINE;
|
||
|
};
|
||
|
|
||
|
template <>
|
||
|
struct primitive_descriptor_meta<extrude_helixline_descriptor_t> {
|
||
|
using internal_type = internal::extrude_helixline;
|
||
|
static constexpr primitive_type type = PRIMITIVE_TYPE_EXTRUDE_HELIXLINE;
|
||
|
};
|
||
|
|
||
|
// ===========================================================================
|
||
|
|
||
|
primitive_node_t::primitive_node_t(const legal_primitive_descriptor_t &descriptor) noexcept
|
||
|
{
|
||
|
std::visit(
|
||
|
[this](auto &&desc) -> void {
|
||
|
using T = std::decay_t<decltype(desc)>;
|
||
|
using internal_type = typename primitive_descriptor_meta<T>::internal_type;
|
||
|
this->desc = ::malloc(sizeof(internal_type));
|
||
|
auto handle = new (this->desc) internal_type(desc, this->aabb);
|
||
|
this->type = primitive_descriptor_meta<T>::type;
|
||
|
},
|
||
|
descriptor);
|
||
|
}
|
||
|
|
||
|
primitive_node_t::primitive_node_t(legal_primitive_descriptor_t &&descriptor) noexcept
|
||
|
{
|
||
|
std::visit(
|
||
|
[this](auto &&desc) {
|
||
|
using T = std::decay_t<decltype(desc)>;
|
||
|
using internal_type = typename primitive_descriptor_meta<T>::internal_type;
|
||
|
this->desc = ::malloc(sizeof(internal_type));
|
||
|
auto handle = new (this->desc) internal_type(std::move(desc), this->aabb);
|
||
|
this->type = primitive_descriptor_meta<T>::type;
|
||
|
},
|
||
|
std::move(descriptor));
|
||
|
}
|
||
|
|
||
|
primitive_node_t::~primitive_node_t() noexcept
|
||
|
{
|
||
|
if (this->desc == nullptr) return;
|
||
|
|
||
|
if (this->type == PRIMITIVE_TYPE_MESH)
|
||
|
static_cast<internal::mesh *>(this->desc)->~mesh();
|
||
|
else if (this->type == PRIMITIVE_TYPE_EXTRUDE_POLYLINE)
|
||
|
static_cast<internal::extrude_polyline *>(this->desc)->~extrude_polyline();
|
||
|
else if (this->type == PRIMITIVE_TYPE_EXTRUDE_HELIXLINE)
|
||
|
static_cast<internal::extrude_helixline *>(this->desc)->~extrude_helixline();
|
||
|
::free(this->desc);
|
||
|
this->desc = nullptr;
|
||
|
}
|
||
|
|
||
|
template <typename Routine>
|
||
|
process_return_type_t<Routine> primitive_node_t::evaluate([[maybe_unused]] const Eigen::Ref<const Eigen::Vector3d> &point) const
|
||
|
{
|
||
|
switch (this->type) {
|
||
|
case PRIMITIVE_TYPE_CONSTANT: return static_cast<const internal::constant *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_PLANE: return static_cast<const internal::plane *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_SPHERE: return static_cast<const internal::sphere *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_CYLINDER: return static_cast<const internal::cylinder *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_CONE: return static_cast<const internal::cone *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_BOX: return static_cast<const internal::box *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_MESH: return static_cast<const internal::mesh *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_EXTRUDE_POLYLINE:
|
||
|
return static_cast<const internal::extrude_polyline *>(this->desc)->evaluate<Routine>(point);
|
||
|
case PRIMITIVE_TYPE_EXTRUDE_HELIXLINE:
|
||
|
return static_cast<const internal::extrude_helixline *>(this->desc)->evaluate<Routine>(point);
|
||
|
default: throw std::runtime_error("Invalid primitive type");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
template process_return_type_t<evaluation_routine_tag> primitive_node_t::evaluate<evaluation_routine_tag>(
|
||
|
[[maybe_unused]] const Eigen::Ref<const Eigen::Vector3d> &point) const;
|
||
|
template process_return_type_t<closest_point_routine_tag> primitive_node_t::evaluate<closest_point_routine_tag>(
|
||
|
[[maybe_unused]] const Eigen::Ref<const Eigen::Vector3d> &point) const;
|