19#include <pxr/usd/usdGeom/capsule.h>
20#include <pxr/usd/usdGeom/capsule_1.h>
21#include <pxr/usd/usdGeom/cone.h>
22#include <pxr/usd/usdGeom/cube.h>
23#include <pxr/usd/usdGeom/cylinder.h>
24#include <pxr/usd/usdGeom/cylinder_1.h>
25#include <pxr/usd/usdGeom/plane.h>
26#include <pxr/usd/usdGeom/sphere.h>
27#include <pxr/usdImaging/usdImaging/capsuleAdapter.h>
28#include <pxr/usdImaging/usdImaging/coneAdapter.h>
29#include <pxr/usdImaging/usdImaging/cubeAdapter.h>
30#include <pxr/usdImaging/usdImaging/cylinderAdapter.h>
31#include <pxr/usdImaging/usdImaging/planeAdapter.h>
32#include <pxr/usdImaging/usdImaging/sphereAdapter.h>
55 Mesh *read_mesh = this->read_mesh(mesh,
params,
nullptr);
57 if (read_mesh != mesh) {
67template<
typename Adapter>
68void USDShapeReader::read_values(
const pxr::UsdTimeCode time,
69 pxr::VtVec3fArray &positions,
70 pxr::VtIntArray &face_indices,
71 pxr::VtIntArray &face_counts)
const
74 pxr::VtValue points_val = adapter.GetPoints(
prim_, time);
76 if (points_val.IsHolding<pxr::VtVec3fArray>()) {
77 positions = points_val.UncheckedGet<pxr::VtVec3fArray>();
80 pxr::VtValue topology_val = adapter.GetTopology(
prim_, pxr::SdfPath(), time);
82 if (topology_val.IsHolding<pxr::HdMeshTopology>()) {
83 const pxr::HdMeshTopology &topology = topology_val.UncheckedGet<pxr::HdMeshTopology>();
84 face_counts = topology.GetFaceVertexCounts();
85 face_indices = topology.GetFaceVertexIndices();
89bool USDShapeReader::read_mesh_values(pxr::UsdTimeCode time,
90 pxr::VtVec3fArray &positions,
91 pxr::VtIntArray &face_indices,
92 pxr::VtIntArray &face_counts)
const
94 if (
prim_.IsA<pxr::UsdGeomCapsule>() ||
prim_.IsA<pxr::UsdGeomCapsule_1>()) {
95 read_values<pxr::UsdImagingCapsuleAdapter>(time, positions, face_indices, face_counts);
99 if (
prim_.IsA<pxr::UsdGeomCylinder>() ||
prim_.IsA<pxr::UsdGeomCylinder_1>()) {
100 read_values<pxr::UsdImagingCylinderAdapter>(time, positions, face_indices, face_counts);
104 if (
prim_.IsA<pxr::UsdGeomCone>()) {
105 read_values<pxr::UsdImagingConeAdapter>(time, positions, face_indices, face_counts);
109 if (
prim_.IsA<pxr::UsdGeomCube>()) {
110 read_values<pxr::UsdImagingCubeAdapter>(time, positions, face_indices, face_counts);
114 if (
prim_.IsA<pxr::UsdGeomSphere>()) {
115 read_values<pxr::UsdImagingSphereAdapter>(time, positions, face_indices, face_counts);
119 if (
prim_.IsA<pxr::UsdGeomPlane>()) {
120 read_values<pxr::UsdImagingPlaneAdapter>(time, positions, face_indices, face_counts);
126 "Unhandled Gprim type: %s (%s)",
127 prim_.GetTypeName().GetText(),
128 prim_.GetPath().GetText());
132Mesh *USDShapeReader::read_mesh(
Mesh *existing_mesh,
137 return existing_mesh;
140 pxr::VtIntArray usd_face_indices;
141 pxr::VtIntArray usd_face_counts;
144 Mesh *active_mesh = mesh_from_prim(existing_mesh,
params, usd_face_indices, usd_face_counts);
146 if (active_mesh == existing_mesh) {
147 return existing_mesh;
150 Span<int> face_indices =
Span(usd_face_indices.cdata(), usd_face_indices.size());
151 Span<int> face_counts =
Span(usd_face_counts.cdata(), usd_face_counts.size());
153 MutableSpan<int> face_offsets = active_mesh->face_offsets_for_write();
154 for (
const int i : IndexRange(active_mesh->
faces_num)) {
155 face_offsets[
i] = face_counts[
i];
162 MutableSpan<int> corner_verts = active_mesh->corner_verts_for_write();
164 corner_verts[
i] = face_indices[
i];
173 const char **r_err_str)
176 Mesh *new_mesh = read_mesh(existing_mesh,
params, r_err_str);
178 if (new_mesh != existing_mesh) {
183void USDShapeReader::apply_primvars_to_mesh(
Mesh *mesh,
const pxr::UsdTimeCode time)
const
186 if (!mesh || !
prim_) {
190 pxr::UsdGeomPrimvarsAPI pv_api = pxr::UsdGeomPrimvarsAPI(
prim_);
191 std::vector<pxr::UsdGeomPrimvar> primvars = pv_api.GetPrimvarsWithValues();
193 pxr::TfToken active_color_name;
195 for (
const pxr::UsdGeomPrimvar &pv : primvars) {
196 const pxr::SdfValueTypeName pv_type = pv.GetTypeName();
197 if (!pv_type.IsArray()) {
201 const pxr::TfToken
name = pxr::UsdGeomPrimvar::StripPrimvarsName(pv.GetPrimvarName());
214 active_color_name =
name;
221 if (!primvar_time_varying_map_.contains(
name)) {
222 primvar_time_varying_map_.add(
name, pv.ValueMightBeTimeVarying());
226 if (!active_color_name.IsEmpty()) {
232Mesh *USDShapeReader::mesh_from_prim(
Mesh *existing_mesh,
234 pxr::VtIntArray &face_indices,
235 pxr::VtIntArray &face_counts)
const
237 pxr::VtVec3fArray positions;
239 if (!read_mesh_values(
params.motion_sample_time, positions, face_indices, face_counts)) {
240 return existing_mesh;
243 const bool poly_counts_match = existing_mesh ? face_counts.size() == existing_mesh->
faces_num :
245 const bool position_counts_match = existing_mesh ? positions.size() == existing_mesh->
verts_num :
248 Mesh *active_mesh =
nullptr;
249 if (!position_counts_match || !poly_counts_match) {
251 existing_mesh, positions.size(), 0, face_counts.size(), face_indices.size());
254 active_mesh = existing_mesh;
257 MutableSpan<float3> vert_positions = active_mesh->vert_positions_for_write();
261 if (active_mesh != existing_mesh) {
263 this->primvar_time_varying_map_.clear();
265 apply_primvars_to_mesh(active_mesh,
params.motion_sample_time);
273 for (
const bool animating_flag : primvar_time_varying_map_.values()) {
274 if (animating_flag) {
279 if (
prim_.IsA<pxr::UsdGeomCapsule>()) {
280 pxr::UsdGeomCapsule geom(
prim_);
281 return (geom.GetAxisAttr().ValueMightBeTimeVarying() ||
282 geom.GetHeightAttr().ValueMightBeTimeVarying() ||
283 geom.GetRadiusAttr().ValueMightBeTimeVarying());
286 if (
prim_.IsA<pxr::UsdGeomCapsule_1>()) {
287 pxr::UsdGeomCapsule_1 geom(
prim_);
288 return (geom.GetAxisAttr().ValueMightBeTimeVarying() ||
289 geom.GetHeightAttr().ValueMightBeTimeVarying() ||
290 geom.GetRadiusTopAttr().ValueMightBeTimeVarying() ||
291 geom.GetRadiusBottomAttr().ValueMightBeTimeVarying());
294 if (
prim_.IsA<pxr::UsdGeomCylinder>()) {
295 pxr::UsdGeomCylinder geom(
prim_);
296 return (geom.GetAxisAttr().ValueMightBeTimeVarying() ||
297 geom.GetHeightAttr().ValueMightBeTimeVarying() ||
298 geom.GetRadiusAttr().ValueMightBeTimeVarying());
301 if (
prim_.IsA<pxr::UsdGeomCylinder_1>()) {
302 pxr::UsdGeomCylinder_1 geom(
prim_);
303 return (geom.GetAxisAttr().ValueMightBeTimeVarying() ||
304 geom.GetHeightAttr().ValueMightBeTimeVarying() ||
305 geom.GetRadiusTopAttr().ValueMightBeTimeVarying() ||
306 geom.GetRadiusBottomAttr().ValueMightBeTimeVarying());
309 if (
prim_.IsA<pxr::UsdGeomCone>()) {
310 pxr::UsdGeomCone geom(
prim_);
311 return (geom.GetAxisAttr().ValueMightBeTimeVarying() ||
312 geom.GetHeightAttr().ValueMightBeTimeVarying() ||
313 geom.GetRadiusAttr().ValueMightBeTimeVarying());
316 if (
prim_.IsA<pxr::UsdGeomCube>()) {
317 pxr::UsdGeomCube geom(
prim_);
318 return geom.GetSizeAttr().ValueMightBeTimeVarying();
321 if (
prim_.IsA<pxr::UsdGeomSphere>()) {
322 pxr::UsdGeomSphere geom(
prim_);
323 return geom.GetRadiusAttr().ValueMightBeTimeVarying();
326 if (
prim_.IsA<pxr::UsdGeomPlane>()) {
327 pxr::UsdGeomPlane geom(
prim_);
328 return (geom.GetWidthAttr().ValueMightBeTimeVarying() ||
329 geom.GetLengthAttr().ValueMightBeTimeVarying() ||
330 geom.GetAxisAttr().ValueMightBeTimeVarying());
335 "Unhandled Gprim type: %s (%s)",
336 prim_.GetTypeName().GetText(),
337 prim_.GetPath().GetText());
void BKE_id_attributes_default_color_set(struct ID *id, std::optional< blender::StringRef > name)
void BKE_id_attributes_active_color_set(struct ID *id, std::optional< blender::StringRef > name)
Mesh * BKE_mesh_new_nomain_from_template(const Mesh *me_src, int verts_num, int edges_num, int faces_num, int corners_num)
Mesh * BKE_mesh_add(Main *bmain, const char *name)
void BKE_mesh_nomain_to_mesh(Mesh *mesh_src, Mesh *mesh_dst, Object *ob, bool process_shape_keys=true)
General operations, lookup, etc. for blender objects.
Object * BKE_object_add_only_object(Main *bmain, int type, const char *name) ATTR_RETURNS_NONNULL
void BKE_reportf(ReportList *reports, eReportType type, const char *format,...) ATTR_PRINTF_FORMAT(3
Object is a sort of wrapper for general info.
const Value & lookup(const Key &key) const
bool contains(const Key &key) const
constexpr IndexRange index_range() const
constexpr void copy_from(Span< T > values) const
void add_cache_modifier()
USDGeomReader(const pxr::UsdPrim &prim, const USDImportParams &import_params, const ImportSettings &settings)
const pxr::UsdPrim & prim() const
StringRefNull name() const
const USDImportParams & import_params_
ReportList * reports() const
void create_object(Main *bmain) override
USDShapeReader(const pxr::UsdPrim &prim, const USDImportParams &import_params, const ImportSettings &settings)
void read_geometry(bke::GeometrySet &, USDMeshReadParams, const char **) override
void read_object_data(Main *bmain, pxr::UsdTimeCode time) override
void mesh_smooth_set(Mesh &mesh, bool use_smooth, bool keep_sharp_edges=false)
void mesh_calc_edges(Mesh &mesh, bool keep_existing_edges, bool select_new_edges)
USDMeshReadParams create_mesh_read_params(const double motion_sample_time, const int read_flags)
std::optional< bke::AttrType > convert_usd_type_to_blender(const pxr::SdfValueTypeName usd_type)
void read_generic_mesh_primvar(Mesh *mesh, const pxr::UsdGeomPrimvar &primvar, const pxr::UsdTimeCode time, const bool is_left_handed)
OffsetIndices< int > accumulate_counts_to_offsets(MutableSpan< int > counts_to_offsets, int start_offset=0)
VecBase< float, 3 > float3
const pxr::TfToken displayColor("displayColor", pxr::TfToken::Immortal)
void replace_mesh(Mesh *mesh, GeometryOwnershipType ownership=GeometryOwnershipType::Owned)
Mesh * get_mesh_for_write()