2
// Copyright 2016 Pixar
4
// Licensed under the Apache License, Version 2.0 (the "Apache License")
5
// with the following modification; you may not use this file except in
6
// compliance with the Apache License and the following modification to it:
7
// Section 6. Trademarks. is deleted and replaced with:
9
// 6. Trademarks. This License does not grant permission to use the trade
10
// names, trademarks, service marks, or product names of the Licensor
11
// and its affiliates, except as required to comply with Section 4(c) of
12
// the License and to reproduce the content of the NOTICE file.
14
// You may obtain a copy of the Apache License at
16
// http://www.apache.org/licenses/LICENSE-2.0
18
// Unless required by applicable law or agreed to in writing, software
19
// distributed under the Apache License with the above modification is
20
// distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
21
// KIND, either express or implied. See the Apache License for the specific
22
// language governing permissions and limitations under the Apache License.
24
#ifndef USDGEOM_GENERATED_IMAGEABLE_H
25
#define USDGEOM_GENERATED_IMAGEABLE_H
27
#include "pxr/usd/usd/typed.h"
28
#include "pxr/usd/usd/prim.h"
29
#include "pxr/usd/usd/stage.h"
30
#include "pxr/usd/usdGeom/tokens.h"
32
#include "pxr/base/gf/bbox3d.h"
33
#include "pxr/usd/usdGeom/primvar.h"
35
#include "pxr/base/vt/value.h"
37
#include "pxr/base/gf/vec3d.h"
38
#include "pxr/base/gf/vec3f.h"
39
#include "pxr/base/gf/matrix4d.h"
41
#include "pxr/base/tf/token.h"
42
#include "pxr/base/tf/type.h"
46
// -------------------------------------------------------------------------- //
48
// -------------------------------------------------------------------------- //
50
/// \brief Base class for all prims that may require rendering or
51
/// visualization of some sort. The primary attributes of Imageable
52
/// are \em visibility and \em purpose, which each provide instructions for
53
/// what geometry should be included for processing by rendering and other
56
/// Imageable also introduces the concept (and API) of geometric
57
/// "primitive variables", as UsdGeomPrimvar, which interpolate across a
58
/// primitive and can override shader inputs.
60
/// For any described attribute \em Fallback \em Value or \em Allowed \em Values below
61
/// that are text/tokens, the actual token is published and defined in \ref UsdGeomTokens.
62
/// So to set an attribute to the value "rightHanded", use UsdGeomTokens->rightHanded
65
class UsdGeomImageable : public UsdTyped
68
/// Compile-time constant indicating whether or not this class corresponds
69
/// to a concrete instantiable prim type in scene description. If this is
70
/// true, GetStaticPrimDefinition() will return a valid prim definition with
71
/// a non-empty typeName.
72
static const bool IsConcrete = false;
74
/// Construct a UsdGeomImageable on UsdPrim \p prim .
75
/// Equivalent to UsdGeomImageable::Get(prim.GetStage(), prim.GetPath())
76
/// for a \em valid \p prim, but will not immediately throw an error for
77
/// an invalid \p prim
78
explicit UsdGeomImageable(const UsdPrim& prim=UsdPrim())
83
/// Construct a UsdGeomImageable on the prim held by \p schemaObj .
84
/// Should be preferred over UsdGeomImageable(schemaObj.GetPrim()),
85
/// as it preserves SchemaBase state.
86
explicit UsdGeomImageable(const UsdSchemaBase& schemaObj)
92
virtual ~UsdGeomImageable();
94
/// Return a vector of names of all pre-declared attributes for this schema
95
/// class and all its ancestor classes. Does not include attributes that
96
/// may be authored by custom/extended methods of the schemas involved.
97
static const TfTokenVector &
98
GetSchemaAttributeNames(bool includeInherited=true);
100
/// \brief Return a UsdGeomImageable holding the prim adhering to this
101
/// schema at \p path on \p stage. If no prim exists at \p path on
102
/// \p stage, or if the prim at that path does not adhere to this schema,
103
/// return an invalid schema object. This is shorthand for the following:
106
/// UsdGeomImageable(stage->GetPrimAtPath(path));
109
static UsdGeomImageable
110
Get(const UsdStagePtr &stage, const SdfPath &path);
114
// needs to invoke _GetStaticTfType.
115
friend class UsdSchemaRegistry;
116
static const TfType &_GetStaticTfType();
118
static bool _IsTypedSchema();
120
// override SchemaBase virtuals.
121
virtual const TfType &_GetTfType() const;
124
// --------------------------------------------------------------------- //
126
// --------------------------------------------------------------------- //
127
/// Visibility is meant to be the simplest form of "pruning"
128
/// visibility that is supported by most DCC apps. Visibility is
129
/// animatable, allowing a sub-tree of geometry to be present for some
130
/// segment of a shot, and absent from others; unlike the action of
131
/// deactivating geometry prims, invisible geometry is still
132
/// available for inspection, for positioning, for defining volumes, etc.
134
/// \n C++ Type: TfToken
135
/// \n Usd Type: SdfValueTypeNames->Token
136
/// \n Variability: SdfVariabilityVarying
137
/// \n Fallback Value: inherited
138
/// \n \ref UsdGeomTokens "Allowed Values": [inherited, invisible]
139
UsdAttribute GetVisibilityAttr() const;
141
/// See GetVisibilityAttr(), and also
142
/// \ref Usd_Create_Or_Get_Property for when to use Get vs Create.
143
/// If specified, author \p defaultValue as the attribute's default,
144
/// sparsely (when it makes sense to do so) if \p writeSparsely is \c true -
145
/// the default for \p writeSparsely is \c false.
146
UsdAttribute CreateVisibilityAttr(VtValue const &defaultValue = VtValue(), bool writeSparsely=false) const;
149
// --------------------------------------------------------------------- //
151
// --------------------------------------------------------------------- //
152
/// Purpose is a concept we have found useful in our pipeline for
153
/// classifying geometry into categories that can each be independently
154
/// included or excluded from traversals of prims on a stage, such as
155
/// rendering or bounding-box computation traversals. The fallback
156
/// purpose, \em default indicates that a prim has "no special purpose"
157
/// and should generally be included in all traversals. Subtrees rooted
158
/// at a prim with purpose \em render should generally only be included
159
/// when performing a "final quality" render. Subtrees rooted at a prim
160
/// with purpose \em proxy should generally only be included when
161
/// performing a lightweight proxy render (such as openGL). Finally,
162
/// subtrees rooted at a prim with purpose \em guide should generally
163
/// only be included when an interactive application has been explicitly
164
/// asked to "show guides".
166
/// In the previous paragraph, when we say "subtrees rooted at a prim",
167
/// we mean the most ancestral or tallest subtree that has an authored,
168
/// non-default opinion. If the purpose of </RootPrim> is set to
169
/// "render", then the effective purpose of </RootPrim/ChildPrim> will
170
/// be "render" even if that prim has a different authored value for
171
/// purpose. <b>See ComputePurpose() for details of how purpose
172
/// inherits down namespace</b>.
174
/// As demonstrated in UsdGeomBBoxCache, a traverser should be ready to
175
/// accept combinations of included purposes as an input.
177
/// Purpose \em render can be useful in creating "light blocker"
178
/// geometry for raytracing interior scenes. Purposes \em render and
179
/// \em proxy can be used together to partition a complicated model
180
/// into a lightweight proxy representation for interactive use, and a
181
/// fully realized, potentially quite heavy, representation for rendering.
182
/// One can also use UsdVariantSets to create proxy representations, but
183
/// this can potentially lead to an explosion in variants for models that
184
/// already have several axes of variation. Purpose provides us with
185
/// another tool for interactive complexity management.
187
/// \n C++ Type: TfToken
188
/// \n Usd Type: SdfValueTypeNames->Token
189
/// \n Variability: SdfVariabilityUniform
190
/// \n Fallback Value: default
191
/// \n \ref UsdGeomTokens "Allowed Values": [default, render, proxy, guide]
192
UsdAttribute GetPurposeAttr() const;
194
/// See GetPurposeAttr(), and also
195
/// \ref Usd_Create_Or_Get_Property for when to use Get vs Create.
196
/// If specified, author \p defaultValue as the attribute's default,
197
/// sparsely (when it makes sense to do so) if \p writeSparsely is \c true -
198
/// the default for \p writeSparsely is \c false.
199
UsdAttribute CreatePurposeAttr(VtValue const &defaultValue = VtValue(), bool writeSparsely=false) const;
202
// ===================================================================== //
203
// Feel free to add custom code below this line, it will be preserved by
204
// the code generator.
206
// Just remember to close the class delcaration with }; and complete the
207
// include guard with #endif
208
// ===================================================================== //
209
// --(BEGIN CUSTOM CODE)--
212
// --------------------------------------------------------------------- //
213
/// \name Primvar Creation and Introspection
215
// --------------------------------------------------------------------- //
217
/// Author scene description to create an attribute on this prim that
218
/// will be recognized as Primvar (i.e. will present as a valid
221
/// The name of the created attribute may or may not be the specified
222
/// \p attrName, due to the possible need to apply property namespacing
223
/// for primvars. See \ref Usd_Creating_and_Accessing_Primvars
224
/// for more information. Creation may fail and return an invalid
225
/// Primvar if \p attrName contains any other namespaces than the
226
/// canonical primvars namespace, as described in the above reference.
228
/// The behavior with respect to the provided \p typeName,
229
/// and \p custom is the same as for UsdAttributes::Create(), and
230
/// \p interpolation and \p elementSize are as described in
231
/// UsdGeomPrimvar::GetInterpolation() and UsdGeomPrimvar::GetElementSize().
233
/// If \p interpolation and/or \p elementSize are left unspecified, we
234
/// will author no opinions for them, which means any (strongest) opinion
235
/// already authored in any contributing layer for these fields will
236
/// become the Primvar's values, or the fallbacks if no opinions
237
/// have been authored.
239
/// \return an invalid UsdGeomPrimvar if we failed to create a valid
240
/// attribute, a valid UsdGeomPrimvar otherwise. It is not an
241
/// error to create over an existing, compatible attribute.
243
/// \sa UsdPrim::CreateAttribute(), UsdGeomPrimvar::IsPrimvar()
244
UsdGeomPrimvar CreatePrimvar(const TfToken& attrName,
245
const SdfValueTypeName &typeName,
246
const TfToken& interpolation = TfToken(),
247
int elementSize = -1,
248
bool custom = false);
250
/// Return the Primvar attribute named by \p name, which will
251
/// be valid if a Primvar attribute definition already exists.
253
/// Name lookup will account for Primvar namespacing, which means
254
/// that this method will succeed in some cases where
256
/// UsdGeomPrimvar(prim->GetAttribute(name))
258
/// will not, unless \p name is properly namespace prefixed.
261
UsdGeomPrimvar GetPrimvar(const TfToken &name) const;
263
/// Return valid UsdGeomPrimvar objects for all defined Primvars on
266
/// Although we hope eventually to make this faster, this is currently
267
/// a fairly expensive operation. If you know you'll need to process
268
/// other attributes as well, you might do better by fetching all
269
/// the attributes at once, and using the pattern described in
270
/// \ref UsdGeomPrimvar_Using_Primvar "Using Primvars" to test individual
272
std::vector<UsdGeomPrimvar> GetPrimvars() const;
274
/// Like GetPrimvars(), but exclude primvars that have no authored scene
276
std::vector<UsdGeomPrimvar> GetAuthoredPrimvars() const;
278
/// Is there defined Primvar \p name on this prim?
280
/// Name lookup will account for Primvar namespacing.
283
bool HasPrimvar(const TfToken &name) const;
287
/// Returns an ordered list of allowed values of the purpose attribute.
289
/// The ordering is important because it defines the protocol between
290
/// UsdGeomModelAPI and UsdGeomBBoxCache for caching and retrieving extents
291
/// hints by purpose.
293
/// The order is: [default, render, proxy, guide]
295
/// See \sa UsdGeomModelAPI::GetExtentsHint().
297
/// \sa GetOrderedPurposeTokens()
298
static const TfTokenVector &GetOrderedPurposeTokens();
300
// --------------------------------------------------------------------- //
301
/// \name Visibility Authoring Helpers
302
/// \anchor usdGeom_Visibility_Authoring_Helpers
303
/// Convenience API for making an imageable visible or invisible.
305
// --------------------------------------------------------------------- //
307
/// \brief Make the imageable visible if it is invisible at the given time.
309
/// Since visibility is pruning, this may need to override some
310
/// ancestor's visibility and all-but-one of the ancestor's children's
311
/// visibility, for all the ancestors of this prim up to the highest
312
/// ancestor that is explicitly invisible, to preserve the visibility state.
314
/// If MakeVisible() (or MakeInvisible()) is going to be applied to all
315
/// the prims on a stage, ancestors must be processed prior to descendants
316
/// to get the correct behavior.
318
/// \note When visibility is animated, this only works when it is
319
/// invoked sequentially at increasing time samples. If visibility is
320
/// already authored and animated in the scene, calling MakeVisible() at
321
/// an arbitrary (in-between) frame isn't guaranteed to work.
323
/// \note This will only work properly if all ancestor prims of the
324
/// imageable are <b>defined</b>, as the imageable schema is only valid on
327
/// \note Be sure to set the edit target to the layer containing the
328
/// strongest visibility opinion or to a stronger layer.
330
/// \sa MakeInvisible()
331
/// \sa ComputeVisibility()
333
void MakeVisible(const UsdTimeCode &time=UsdTimeCode::Default()) const;
335
/// \brief Makes the imageable invisible if it is visible at the given time.
337
/// \note When visibility is animated, this only works when it is
338
/// invoked sequentially at increasing time samples. If visibility is
339
/// already authored and animated in the scene, calling MakeVisible() at
340
/// an arbitrary (in-between) frame isn't guaranteed to work.
342
/// \note Be sure to set the edit target to the layer containing the
343
/// strongest visibility opinion or to a stronger layer.
345
/// \sa MakeVisible()
346
/// \sa ComputeVisibility()
348
void MakeInvisible(const UsdTimeCode &time=UsdTimeCode::Default()) const;
352
// --------------------------------------------------------------------- //
353
/// \name Computed Attribute Helpers
354
/// \anchor usdGeom_Computed_Attribute_Helpers
355
/// Visbility, Purpose, Bounds (World, Local, and Untransformed), and
356
/// Transform (LocalToWorld and ParentToWorld) are all qualities of a
357
/// prim's location in namespace that require non-local data and
358
/// computation. Computing these efficiently requires a stage-level
359
/// cache, but when performance is not a concern, it is convenient to
360
/// query these quantities directly on a prim, so we provide convenience
361
/// API here for doing so.
363
// --------------------------------------------------------------------- //
365
/// Calculate the effective visibility of this prim, as defined by its
366
/// most ancestral authored "invisible" opinion, if any.
368
/// A prim is considered visible at the current \p time if none of its
369
/// Imageable ancestors express an authored "invisible" opinion, which is
370
/// what leads to the "simple pruning" behavior described in
371
/// GetVisibilityAttr().
373
/// This function should be considered a reference implementation for
374
/// correctness. <b>If called on each prim in the context of a traversal
375
/// we will perform massive overcomputation, because sibling prims share
376
/// sub-problems in the query that can be efficiently cached, but are not
377
/// (cannot be) by this simple implementation.</b> If you have control of
378
/// your traversal, it will be far more efficient to manage visibility
379
/// on a stack as you traverse.
381
/// \sa GetVisibilityAttr()
382
TfToken ComputeVisibility(UsdTimeCode const &time = UsdTimeCode::Default()) const;
384
/// Calculate the effective purpose of this prim, as defined by its
385
/// most ancestral authored non-"default" opinion, if any.
387
/// If no opinion for purpose is authored on prim or any of its
388
/// ancestors, its computed purpose is UsdGeomTokens->default_ .
389
/// Otherwise, its computed purpose is that of its highest ancestor
390
/// with an authored purpose of something other than UsdGeomTokens->default_
392
/// In other words, all of a stage's root prims inherit the *purpose*
393
/// UsdGeomTokens->default_ from the pseudoroot, and that value will be
394
/// **inherited** by all of their descendants, until a descendant
395
/// </Some/path/to/nonDefault> contains some other, authored value of
396
/// *purpose* . The computed purpose of that prim **and all of its
397
/// descendants** will be that prim's authored value, regardless of what
398
/// *putpose* opinions its own descendant prims may express.
400
/// This function should be considered a reference implementation for
401
/// correctness. <b>If called on each prim in the context of a traversal
402
/// we will perform massive overcomputation, because sibling prims share
403
/// sub-problems in the query that can be efficiently cached, but are not
404
/// (cannot be) by this simple implementation.</b> If you have control of
405
/// your traversal, it will be far more efficient to manage purpose, along
406
/// with visibility, on a stack as you traverse.
408
/// \sa GetPurposeAttr()
409
TfToken ComputePurpose() const;
411
/// Compute the bound of this prim in world space, at the specified
412
/// \p time, and for the specified purposes.
414
/// The bound of the prim is computed, including the transform (if any)
415
/// authored on the node itself, and then transformed to world space.
417
/// It is an error to not specify any purposes, which will result in the
418
/// return of an empty box.
420
/// <b>If you need to compute bounds for multiple prims on a stage, it
421
/// will be much, much more efficient to instantiate a UsdGeomBBoxCache
422
/// and query it directly; doing so will reuse sub-computations shared
423
/// by the prims.</b>
424
GfBBox3d ComputeWorldBound(UsdTimeCode const& time,
425
TfToken const &purpose1=TfToken(),
426
TfToken const &purpose2=TfToken(),
427
TfToken const &purpose3=TfToken(),
428
TfToken const &purpose4=TfToken()) const;
431
/// Compute the bound of this prim in local space, at the specified
432
/// \p time, and for the specified purposes.
434
/// The bound of the prim is computed, including the transform (if any)
435
/// authored on the node itself.
437
/// It is an error to not specify any purposes, which will result in the
438
/// return of an empty box.
440
/// <b>If you need to compute bounds for multiple prims on a stage, it
441
/// will be much, much more efficient to instantiate a UsdGeomBBoxCache
442
/// and query it directly; doing so will reuse sub-computations shared
443
/// by the prims.</b>
444
GfBBox3d ComputeLocalBound(UsdTimeCode const& time,
445
TfToken const &purpose1=TfToken(),
446
TfToken const &purpose2=TfToken(),
447
TfToken const &purpose3=TfToken(),
448
TfToken const &purpose4=TfToken()) const;
450
/// Compute the untransformed bound of this prim, at the specified
451
/// \p time, and for the specified purposes.
453
/// The bound of the prim is computed in its object space, ignoring
454
/// any transforms authored on or above the prim.
456
/// It is an error to not specify any purposes, which will result in the
457
/// return of an empty box.
459
/// <b>If you need to compute bounds for multiple prims on a stage, it
460
/// will be much, much more efficient to instantiate a UsdGeomBBoxCache
461
/// and query it directly; doing so will reuse sub-computations shared
462
/// by the prims.</b>
463
GfBBox3d ComputeUntransformedBound(UsdTimeCode const& time,
464
TfToken const &purpose1=TfToken(),
465
TfToken const &purpose2=TfToken(),
466
TfToken const &purpose3=TfToken(),
467
TfToken const &purpose4=TfToken()) const;
469
/// Compute the transformation matrix for this prim at the given time,
470
/// including the transform authored on the Prim itself, if present.
472
/// <b>If you need to compute the transform for multiple prims on a
473
/// stage, it will be much, much more efficient to instantiate a
474
/// UsdGeomXformCache and query it directly; doing so will reuse
475
/// sub-computations shared by the prims.</b>
476
GfMatrix4d ComputeLocalToWorldTransform(UsdTimeCode const &time) const;
478
/// Compute the transformation matrix for this prim at the given time,
479
/// \em NOT including the transform authored on the prim itself.
481
/// <b>If you need to compute the transform for multiple prims on a
482
/// stage, it will be much, much more efficient to instantiate a
483
/// UsdGeomXformCache and query it directly; doing so will reuse
484
/// sub-computations shared by the prims.</b>
485
GfMatrix4d ComputeParentToWorldTransform(UsdTimeCode const &time) const;
490
// Helper for Get(Authored)Primvars().
491
std::vector<UsdGeomPrimvar>
492
_MakePrimvars(std::vector<UsdProperty> const &props) const;