1 // 2 // Copyright 2016 Pixar 3 // 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: 8 // 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. 13 // 14 // You may obtain a copy of the Apache License at 15 // 16 // http://www.apache.org/licenses/LICENSE-2.0 17 // 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. 23 // 24 #ifndef USDGEOM_GENERATED_PRIMVARSAPI_H 25 #define USDGEOM_GENERATED_PRIMVARSAPI_H 26 27 /// \file usdGeom/primvarsAPI.h 28 29 #include "pxr/pxr.h" 30 #include "pxr/usd/usdGeom/api.h" 31 #include "pxr/usd/usd/apiSchemaBase.h" 32 #include "pxr/usd/usd/prim.h" 33 #include "pxr/usd/usd/stage.h" 34 35 #include "pxr/usd/usdGeom/primvar.h" 36 37 #include "pxr/base/vt/value.h" 38 39 #include "pxr/base/gf/vec3d.h" 40 #include "pxr/base/gf/vec3f.h" 41 #include "pxr/base/gf/matrix4d.h" 42 43 #include "pxr/base/tf/token.h" 44 #include "pxr/base/tf/type.h" 45 46 PXR_NAMESPACE_OPEN_SCOPE 47 48 class SdfAssetPath; 49 50 // -------------------------------------------------------------------------- // 51 // PRIMVARSAPI // 52 // -------------------------------------------------------------------------- // 53 54 /// \class UsdGeomPrimvarsAPI 55 /// 56 /// UsdGeomPrimvarsAPI encodes geometric "primitive variables", 57 /// as UsdGeomPrimvar, which interpolate across a primitive's topology, 58 /// can override shader inputs, and inherit down namespace. 59 /// 60 /// \section usdGeom_PrimvarFetchingAPI Which Method to Use to Retrieve Primvars 61 /// 62 /// While creating primvars is unambiguous (CreatePrimvar()), there are quite 63 /// a few methods available for retrieving primvars, making it potentially 64 /// confusing knowing which one to use. Here are some guidelines: 65 /// 66 /// \li If you are populating a GUI with the primvars already available for 67 /// authoring values on a prim, use GetPrimvars(). 68 /// \li If you want all of the "useful" (e.g. to a renderer) primvars 69 /// available at a prim, including those inherited from ancestor prims, use 70 /// FindPrimvarsWithInheritance(). Note that doing so individually for many 71 /// prims will be inefficient. 72 /// \li To find a particular primvar defined directly on a prim, which may 73 /// or may not provide a value, use GetPrimvar(). 74 /// \li To find a particular primvar defined on a prim or inherited from 75 /// ancestors, which may or may not provide a value, use 76 /// FindPrimvarWithInheritance(). 77 /// \li To *efficiently* query for primvars using the overloads of 78 /// FindPrimvarWithInheritance() and FindPrimvarsWithInheritance(), one 79 /// must first cache the results of FindIncrementallyInheritablePrimvars() for 80 /// each non-leaf prim on the stage. 81 /// 82 class UsdGeomPrimvarsAPI : public UsdAPISchemaBase 83 { 84 public: 85 /// Compile time constant representing what kind of schema this class is. 86 /// 87 /// \sa UsdSchemaKind 88 static const UsdSchemaKind schemaKind = UsdSchemaKind::NonAppliedAPI; 89 90 /// Construct a UsdGeomPrimvarsAPI on UsdPrim \p prim . 91 /// Equivalent to UsdGeomPrimvarsAPI::Get(prim.GetStage(), prim.GetPath()) 92 /// for a \em valid \p prim, but will not immediately throw an error for 93 /// an invalid \p prim 94 explicit UsdGeomPrimvarsAPI(const UsdPrim& prim=UsdPrim()) UsdAPISchemaBase(prim)95 : UsdAPISchemaBase(prim) 96 { 97 } 98 99 /// Construct a UsdGeomPrimvarsAPI on the prim held by \p schemaObj . 100 /// Should be preferred over UsdGeomPrimvarsAPI(schemaObj.GetPrim()), 101 /// as it preserves SchemaBase state. UsdGeomPrimvarsAPI(const UsdSchemaBase & schemaObj)102 explicit UsdGeomPrimvarsAPI(const UsdSchemaBase& schemaObj) 103 : UsdAPISchemaBase(schemaObj) 104 { 105 } 106 107 /// Destructor. 108 USDGEOM_API 109 virtual ~UsdGeomPrimvarsAPI(); 110 111 /// Return a vector of names of all pre-declared attributes for this schema 112 /// class and all its ancestor classes. Does not include attributes that 113 /// may be authored by custom/extended methods of the schemas involved. 114 USDGEOM_API 115 static const TfTokenVector & 116 GetSchemaAttributeNames(bool includeInherited=true); 117 118 /// Return a UsdGeomPrimvarsAPI holding the prim adhering to this 119 /// schema at \p path on \p stage. If no prim exists at \p path on 120 /// \p stage, or if the prim at that path does not adhere to this schema, 121 /// return an invalid schema object. This is shorthand for the following: 122 /// 123 /// \code 124 /// UsdGeomPrimvarsAPI(stage->GetPrimAtPath(path)); 125 /// \endcode 126 /// 127 USDGEOM_API 128 static UsdGeomPrimvarsAPI 129 Get(const UsdStagePtr &stage, const SdfPath &path); 130 131 132 protected: 133 /// Returns the kind of schema this class belongs to. 134 /// 135 /// \sa UsdSchemaKind 136 USDGEOM_API 137 UsdSchemaKind _GetSchemaKind() const override; 138 139 private: 140 // needs to invoke _GetStaticTfType. 141 friend class UsdSchemaRegistry; 142 USDGEOM_API 143 static const TfType &_GetStaticTfType(); 144 145 static bool _IsTypedSchema(); 146 147 // override SchemaBase virtuals. 148 USDGEOM_API 149 const TfType &_GetTfType() const override; 150 151 public: 152 // ===================================================================== // 153 // Feel free to add custom code below this line, it will be preserved by 154 // the code generator. 155 // 156 // Just remember to: 157 // - Close the class declaration with }; 158 // - Close the namespace with PXR_NAMESPACE_CLOSE_SCOPE 159 // - Close the include guard with #endif 160 // ===================================================================== // 161 // --(BEGIN CUSTOM CODE)-- 162 163 /// Author scene description to create an attribute on this prim that 164 /// will be recognized as Primvar (i.e. will present as a valid 165 /// UsdGeomPrimvar). 166 /// 167 /// The name of the created attribute may or may not be the specified 168 /// \p name, due to the possible need to apply property namespacing 169 /// for primvars. See \ref Usd_Creating_and_Accessing_Primvars 170 /// for more information. Creation may fail and return an invalid 171 /// Primvar if \p name contains a reserved keyword, such as the 172 /// "indices" suffix we use for indexed primvars. 173 /// 174 /// The behavior with respect to the provided \p typeName 175 /// is the same as for UsdAttributes::Create(), and 176 /// \p interpolation and \p elementSize are as described in 177 /// UsdGeomPrimvar::GetInterpolation() and UsdGeomPrimvar::GetElementSize(). 178 /// 179 /// If \p interpolation and/or \p elementSize are left unspecified, we 180 /// will author no opinions for them, which means any (strongest) opinion 181 /// already authored in any contributing layer for these fields will 182 /// become the Primvar's values, or the fallbacks if no opinions 183 /// have been authored. 184 /// 185 /// \return an invalid UsdGeomPrimvar if we failed to create a valid 186 /// attribute, a valid UsdGeomPrimvar otherwise. It is not an 187 /// error to create over an existing, compatible attribute. 188 /// 189 /// \sa UsdPrim::CreateAttribute(), UsdGeomPrimvar::IsPrimvar() 190 USDGEOM_API 191 UsdGeomPrimvar CreatePrimvar(const TfToken& name, 192 const SdfValueTypeName &typeName, 193 const TfToken& interpolation = TfToken(), 194 int elementSize = -1) const; 195 196 /// Author scene description to create an attribute and authoring a \p value 197 /// on this prim that will be recognized as a Primvar (i.e. will present as 198 /// a valid UsdGeomPrimvar). Note that unlike CreatePrimvar using this API 199 /// explicitly authors a block for the indices attr associated with the 200 /// primvar, thereby blocking any indices set in any weaker layers. 201 /// 202 /// \return an invalid UsdGeomPrimvar on error, a valid UsdGeomPrimvar 203 /// otherwise. It is fine to call this method multiple times, and in 204 /// different UsdEditTargets, even if there is an existing primvar of the 205 /// same name, indexed or not. 206 /// 207 /// \sa CreatePrimvar(), CreateIndexedPrimvar(), UsdPrim::CreateAttribute(), 208 /// UsdGeomPrimvar::IsPrimvar() 209 template <typename T> 210 UsdGeomPrimvar CreateNonIndexedPrimvar( 211 const TfToken& name, 212 const SdfValueTypeName &typeName, 213 const T &value, 214 const TfToken &interpolation = TfToken(), 215 int elementSize = -1, 216 UsdTimeCode time = UsdTimeCode::Default()) const 217 { 218 UsdGeomPrimvar primvar = 219 CreatePrimvar(name, typeName, interpolation, elementSize); 220 221 primvar.GetAttr().Set(value, time); 222 primvar.BlockIndices(); 223 return primvar; 224 } 225 226 /// Author scene description to create an attribute and authoring a \p value 227 /// on this prim that will be recognized as an indexed Primvar with \p 228 /// indices appropriately set (i.e. will present as a valid UsdGeomPrimvar). 229 /// 230 /// \return an invalid UsdGeomPrimvar on error, a valid UsdGeomPrimvar 231 /// otherwise. It is fine to call this method multiple times, and in 232 /// different UsdEditTargets, even if there is an existing primvar of the 233 /// same name, indexed or not. 234 /// 235 /// \sa CreatePrimvar(), CreateNonIndexedPrimvar(), 236 /// UsdPrim::CreateAttribute(), UsdGeomPrimvar::IsPrimvar() 237 template <typename T> 238 UsdGeomPrimvar CreateIndexedPrimvar( 239 const TfToken& name, 240 const SdfValueTypeName &typeName, 241 const T &value, 242 const VtIntArray &indices, 243 const TfToken &interpolation = TfToken(), 244 int elementSize = -1, 245 UsdTimeCode time = UsdTimeCode::Default()) const 246 { 247 UsdGeomPrimvar primvar = 248 CreatePrimvar(name, typeName, interpolation, elementSize); 249 250 primvar.GetAttr().Set(value, time); 251 primvar.SetIndices(indices, time); 252 return primvar; 253 } 254 255 /// Author scene description to delete an attribute on this prim that 256 /// was recognized as Primvar (i.e. will present as a valid UsdGeomPrimvar), 257 /// <em>in the current UsdEditTarget</em>. 258 /// 259 /// Because this method can only remove opinions about the primvar 260 /// from the current EditTarget, you may generally find it more useful to 261 /// use BlockPrimvar() which will ensure that all values from the EditTarget 262 /// and weaker layers for the primvar and its indices will be ignored. 263 /// 264 /// Removal may fail and return false if \p name contains a reserved 265 /// keyword, such as the "indices" suffix we use for indexed primvars. 266 /// 267 /// Note this will also remove the indices attribute associated with an 268 /// indiced primvar. 269 /// 270 /// \return true if UsdGeomPrimvar and indices attribute was successfully 271 /// removed, false otherwise. 272 /// 273 /// \sa UsdPrim::RemoveProperty()) 274 USDGEOM_API 275 bool RemovePrimvar(const TfToken& name); 276 277 /// Remove all time samples on the primvar and its associated indices attr, 278 /// and author a *block* \c default value. This will cause authored opinions 279 /// in weaker layers to be ignored. 280 /// 281 /// \sa UsdAttribute::Block(), UsdGeomPrimvar::BlockIndices 282 USDGEOM_API 283 void BlockPrimvar(const TfToken& name); 284 285 /// Return the Primvar object named by \p name, which will 286 /// be valid if a Primvar attribute definition already exists. 287 /// 288 /// Name lookup will account for Primvar namespacing, which means 289 /// that this method will succeed in some cases where 290 /// \code 291 /// UsdGeomPrimvar(prim->GetAttribute(name)) 292 /// \endcode 293 /// will not, unless \p name is properly namespace prefixed. 294 /// 295 /// \note Just because a Primvar is valid and defined, and *even if* its 296 /// underlying UsdAttribute (GetAttr()) answers HasValue() affirmatively, 297 /// one must still check the return value of Get(), due to the potential 298 /// of time-varying value blocks (see \ref Usd_AttributeBlocking). 299 /// 300 /// \sa HasPrimvar(), \ref usdGeom_PrimvarFetchingAPI 301 USDGEOM_API 302 UsdGeomPrimvar GetPrimvar(const TfToken &name) const; 303 304 /// Return valid UsdGeomPrimvar objects for all defined Primvars on 305 /// this prim, similarly to UsdPrim::GetAttributes(). 306 /// 307 /// The returned primvars may not possess any values, and therefore not 308 /// be useful to some clients. For the primvars useful for inheritance 309 /// computations, see GetPrimvarsWithAuthoredValues(), and for primvars 310 /// useful for direct consumption, see GetPrimvarsWithValues(). 311 /// 312 /// \sa \ref usdGeom_PrimvarFetchingAPI 313 USDGEOM_API 314 std::vector<UsdGeomPrimvar> GetPrimvars() const; 315 316 /// Like GetPrimvars(), but include only primvars that have some 317 /// authored scene description (though not necessarily a value). 318 /// 319 /// \sa \ref usdGeom_PrimvarFetchingAPI 320 USDGEOM_API 321 std::vector<UsdGeomPrimvar> GetAuthoredPrimvars() const; 322 323 /// Like GetPrimvars(), but include only primvars that have some 324 /// value, whether it comes from authored scene description or a schema 325 /// fallback. 326 /// 327 /// For most purposes, this method is more useful than GetPrimvars(). 328 /// 329 /// \sa \ref usdGeom_PrimvarFetchingAPI 330 USDGEOM_API 331 std::vector<UsdGeomPrimvar> GetPrimvarsWithValues() const; 332 333 /// Like GetPrimvars(), but include only primvars that have an **authored** 334 /// value. 335 /// 336 /// This is the query used when computing inheritable primvars, and is 337 /// generally more useful than GetAuthoredPrimvars(). 338 /// 339 /// \sa \ref usdGeom_PrimvarFetchingAPI 340 USDGEOM_API 341 std::vector<UsdGeomPrimvar> GetPrimvarsWithAuthoredValues() const; 342 343 /// Compute the primvars that can be inherited from this prim by its 344 /// child prims, including the primvars that **this** prim inherits from 345 /// ancestor prims. Inherited primvars will be bound to attributes on 346 /// the corresponding ancestor prims. 347 /// 348 /// Only primvars with **authored**, **non-blocked**, 349 /// **constant interpolation** values are inheritable; 350 /// fallback values are not inherited. The order of the returned 351 /// primvars is undefined. 352 /// 353 /// It is not generally useful to call this method on UsdGeomGprim leaf 354 /// prims, and furthermore likely to be expensive since *most* primvars 355 /// are defined on Gprims. 356 /// 357 /// \sa \ref usdGeom_PrimvarFetchingAPI 358 USDGEOM_API 359 std::vector<UsdGeomPrimvar> FindInheritablePrimvars() const; 360 361 /// Compute the primvars that can be inherited from this prim by its 362 /// child prims, starting from the set of primvars inherited from 363 /// this prim's ancestors. If this method returns an empty vector, then 364 /// this prim's children should inherit the same set of primvars available 365 /// to this prim, i.e. the input `inheritedFromAncestors` . 366 /// 367 /// As opposed to FindInheritablePrimvars(), which always recurses up 368 /// through all of the prim's ancestors, this method allows more 369 /// efficient computation of inheritable primvars by starting with the 370 /// list of primvars inherited from this prim's ancestors, and returning 371 /// a newly allocated vector only when this prim makes a change to the 372 /// set of inherited primvars. This enables O(n) inherited primvar 373 /// computation for all prims on a Stage, with potential to share 374 /// computed results that are identical (i.e. when this method returns an 375 /// empty vector, its parent's result can (and must!) be reused for all 376 /// of the prim's children. 377 /// 378 /// \sa \ref usdGeom_PrimvarFetchingAPI 379 USDGEOM_API 380 std::vector<UsdGeomPrimvar> FindIncrementallyInheritablePrimvars( 381 const std::vector<UsdGeomPrimvar> &inheritedFromAncestors) const; 382 383 /// Like GetPrimvar(), but if the named primvar does not exist or has no 384 /// authored value on this prim, search for the named, value-producing 385 /// primvar on ancestor prims. 386 /// 387 /// The returned primvar will be bound to the attribute on the 388 /// corresponding ancestor prim on which it was found (if any). If neither 389 /// this prim nor any ancestor contains a value-producing primvar, then 390 /// the returned primvar will be the same as that returned by GetPrimvar(). 391 /// 392 /// This is probably the method you want to call when needing to consume 393 /// a primvar of a particular name. 394 /// 395 /// \sa \ref usdGeom_PrimvarFetchingAPI 396 USDGEOM_API 397 UsdGeomPrimvar FindPrimvarWithInheritance(const TfToken &name) const; 398 399 /// \overload 400 /// 401 /// This version of FindPrimvarWithInheritance() takes the pre-computed 402 /// set of primvars inherited from this prim's ancestors, as computed 403 /// by FindInheritablePrimvars() or FindIncrementallyInheritablePrimvars() 404 /// on the prim's parent. 405 /// 406 /// \sa \ref usdGeom_PrimvarFetchingAPI 407 USDGEOM_API 408 UsdGeomPrimvar FindPrimvarWithInheritance(const TfToken &name, 409 const std::vector<UsdGeomPrimvar> &inheritedFromAncestors) const; 410 411 /// Find all of the value-producing primvars either defined on this prim, 412 /// or inherited from ancestor prims. 413 /// 414 /// \sa \ref usdGeom_PrimvarFetchingAPI 415 USDGEOM_API 416 std::vector<UsdGeomPrimvar> FindPrimvarsWithInheritance() const; 417 418 /// \overload 419 /// 420 /// This version of FindPrimvarsWithInheritance() takes the pre-computed 421 /// set of primvars inherited from this prim's ancestors, as computed 422 /// by FindInheritablePrimvars() or FindIncrementallyInheritablePrimvars() 423 /// on the prim's parent. 424 /// 425 /// \sa \ref usdGeom_PrimvarFetchingAPI 426 USDGEOM_API 427 std::vector<UsdGeomPrimvar> FindPrimvarsWithInheritance( 428 const std::vector<UsdGeomPrimvar> &inheritedFromAncestors) const; 429 430 /// Is there a defined Primvar \p name on this prim? 431 /// 432 /// Name lookup will account for Primvar namespacing. 433 /// 434 /// Like GetPrimvar(), a return value of `true` for HasPrimvar() does not 435 /// guarantee the primvar will produce a value. 436 USDGEOM_API 437 bool HasPrimvar(const TfToken &name) const; 438 439 /// Is there a Primvar named \p name with an authored value on this 440 /// prim or any of its ancestors? 441 /// 442 /// This is probably the method you want to call when wanting to know 443 /// whether or not the prim "has" a primvar of a particular name. 444 /// 445 /// \sa FindPrimvarWithInheritance() 446 USDGEOM_API 447 bool HasPossiblyInheritedPrimvar(const TfToken &name) const; 448 449 /// Test whether a given \p name contains the "primvars:" prefix 450 /// 451 USDGEOM_API 452 static bool CanContainPropertyName(const TfToken& name); 453 }; 454 455 PXR_NAMESPACE_CLOSE_SCOPE 456 457 #endif 458