14#include <lagrange/Logger.h>
15#include <lagrange/internal/attribute_string_utils.h>
16#include <lagrange/internal/visit_attribute.h>
17#include <lagrange/utils/assert.h>
20namespace OPENSUBDIV_VERSION {
26bool TopologyRefinerFactory<ConverterType>::resizeComponentTopology(
27 TopologyRefiner& refiner,
28 const ConverterType& conv)
30 const auto& mesh = conv.mesh;
34 setNumBaseVertices(refiner, num_vertices);
38 setNumBaseFaces(refiner, num_facets);
39 for (
int facet = 0; facet < num_facets; ++facet) {
41 setNumBaseFaceVertices(refiner, facet, nv);
50bool TopologyRefinerFactory<ConverterType>::assignComponentTopology(
51 TopologyRefiner& refiner,
52 const ConverterType& conv)
54 const auto& mesh = conv.mesh;
55 using Far::IndexArray;
59 for (
int facet = 0; facet < num_facets; ++facet) {
60 IndexArray dst_facet_vertices = getBaseFaceVertices(refiner, facet);
63 for (
size_t lv = 0; lv < fv.size(); ++lv) {
64 dst_facet_vertices[lv] =
static_cast<int>(fv[lv]);
73bool TopologyRefinerFactory<ConverterType>::assignComponentTags(
74 TopologyRefiner& refiner,
75 const ConverterType& conv)
77 const auto& mesh = conv.mesh;
78 const auto& options = conv.options;
80 if (options.edge_sharpness_attr.has_value()) {
83 options.edge_sharpness_attr.value(),
85 using AttributeType = std::decay_t<decltype(attr)>;
86 using ValueType = typename AttributeType::ValueType;
87 la_runtime_assert(attr.get_num_channels() == 1);
89 std::is_floating_point_v<ValueType>,
91 "Edge sharpness attribute must use a floating point type. Received: {}",
92 lagrange::internal::value_type_name<ValueType>()));
93 la_runtime_assert(attr.get_element_type() == lagrange::AttributeElement::Edge);
94 if constexpr (AttributeType::IsIndexed) {
95 la_runtime_assert(
"Edge sharpness cannot be an indexed attribute");
97 lagrange::logger().debug(
"Using edge sharpness attribute");
98 auto values = attr.get_all();
99 for (int e = 0; e < static_cast<int>(values.size()); ++e) {
100 auto v = mesh.get_edge_vertices(e);
101 Index idx = findBaseEdge(refiner, v[0], v[1]);
103 if (idx != INDEX_INVALID) {
104 float s = static_cast<float>(ValueType(10.0) * values[e]);
105 setBaseEdgeSharpness(refiner, idx, s);
111 "Edge %d specified to be sharp does not exist (%d, %d)",
113 static_cast<int>(v[0]),
114 static_cast<int>(v[1]));
115 reportInvalidTopology(
116 Vtr::internal::Level::TOPOLOGY_INVALID_CREASE_EDGE,
125 if (options.vertex_sharpness_attr.has_value()) {
128 options.vertex_sharpness_attr.value(),
130 using AttributeType = std::decay_t<decltype(attr)>;
131 using ValueType = typename AttributeType::ValueType;
132 la_runtime_assert(attr.get_num_channels() == 1);
133 la_runtime_assert(attr.get_element_type() == lagrange::AttributeElement::Vertex);
135 std::is_floating_point_v<ValueType>,
137 "Vertex sharpness attribute must use a floating point type. Received: {}",
138 lagrange::internal::value_type_name<ValueType>()));
139 if constexpr (AttributeType::IsIndexed) {
140 la_runtime_assert(
"Vertex sharpness cannot be an indexed attribute");
142 lagrange::logger().debug(
"Using vertex sharpness attribute");
143 auto values = attr.get_all();
144 for (int v = 0; v < static_cast<int>(values.size()); ++v) {
145 float s = static_cast<float>(ValueType(10.0) * values[v]);
146 setBaseVertexSharpness(refiner, v, s);
152 if (options.face_hole_attr.has_value()) {
155 options.face_hole_attr.value(),
157 using AttributeType = std::decay_t<decltype(attr)>;
158 using ValueType = typename AttributeType::ValueType;
159 la_runtime_assert(attr.get_num_channels() == 1);
161 std::is_integral_v<ValueType>,
163 "Face holes attribute must use an integral type. Received: {}",
164 lagrange::internal::value_type_name<ValueType>()));
165 if constexpr (AttributeType::IsIndexed) {
166 la_runtime_assert(
"Face holes cannot be an indexed attribute");
168 lagrange::logger().debug(
"Using facet hole attribute");
169 auto values = attr.get_all();
170 for (int f = 0; f < static_cast<int>(values.size()); ++f) {
171 if (values[f] != ValueType(0)) {
172 lagrange::logger().warn(
"Setting facet f{} as a hole", f);
173 setBaseFaceHole(refiner, f, true);
186bool TopologyRefinerFactory<ConverterType>::assignFaceVaryingTopology(
187 TopologyRefiner& refiner,
188 const ConverterType& conv)
190 const auto& mesh = conv.mesh;
196 using AttributeType = std::decay_t<
decltype(attr)>;
197 if constexpr (!AttributeType::IsIndexed) {
201 "Face varying attributes must indexed attributes. Received: {}",
204 int num_values =
static_cast<int>(attr.values().get_num_elements());
205 auto src_indices = attr.indices().get_all();
207 int channel = createBaseFVarChannel(refiner, num_values);
209 for (
int f = 0, src_next = 0; f < static_cast<int>(mesh.get_num_facets()); ++f) {
210 IndexArray dst_indices = getBaseFaceFVarValues(refiner, f, channel);
212 for (
int lv = 0; lv < dst_indices.size(); ++lv) {
213 dst_indices[lv] = src_indices[src_next++];
224void TopologyRefinerFactory<ConverterType>::reportInvalidTopology(
227 const ConverterType& )
Index get_num_vertices() const
Retrieves the number of vertices.
Definition SurfaceMesh.h:671
span< const Index > get_facet_vertices(Index f) const
Retrieves a read-only pointer to a facet indices.
Definition SurfaceMesh.cpp:2188
Index get_num_facets() const
Retrieves the number of facets.
Definition SurfaceMesh.h:678
Index get_facet_size(Index f) const
Number of vertices in the facet.
Definition SurfaceMesh.h:719
LA_CORE_API spdlog::logger & logger()
Retrieves the current logger.
Definition Logger.cpp:40
uint32_t AttributeId
Identified to be used to access an attribute.
Definition AttributeFwd.h:73
#define la_runtime_assert(...)
Runtime assertion check.
Definition assert.h:174
LA_CORE_API std::string_view to_string(AttributeElement element)
Returns a string representation of an attribute element type.
Definition attribute_string_utils.cpp:22
void visit_attribute_read(const SurfaceMesh< Scalar, Index > &mesh, AttributeId id, Func &&func)
Definition visit_attribute.h:39