HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
rprim.h
Go to the documentation of this file.
1 //
2 // Copyright 2016 Pixar
3 //
4 // Licensed under the terms set forth in the LICENSE.txt file available at
5 // https://openusd.org/license.
6 //
7 #ifndef PXR_IMAGING_HD_RPRIM_H
8 #define PXR_IMAGING_HD_RPRIM_H
9 
10 #include "pxr/pxr.h"
11 #include "pxr/imaging/hd/api.h"
12 #include "pxr/imaging/hd/version.h"
14 #include "pxr/imaging/hd/repr.h"
16 #include "pxr/imaging/hd/types.h"
17 #include "pxr/usd/sdf/path.h"
18 #include "pxr/base/gf/range3d.h"
19 #include "pxr/base/arch/inttypes.h"
20 
21 #include <memory>
22 #include <vector>
23 
25 
26 class HdChangeTracker;
27 class HdRenderIndex;
28 class HdRenderParam;
29 
30 using HdReprSharedPtr = std::shared_ptr<HdRepr>;
31 
32 /// \class HdRprim
33 ///
34 /// The render engine state for a given rprim from the scene graph. All data
35 /// access (aside from local caches) is delegated to the HdSceneDelegate.
36 ///
37 class HdRprim
38 {
39 public:
40  HD_API
41  HdRprim(SdfPath const& id);
42 
43  HD_API
44  virtual ~HdRprim();
45 
46  // ---------------------------------------------------------------------- //
47  /// \name Rprim Hydra Engine API : Pre-Sync & Sync-Phase
48  // ---------------------------------------------------------------------- //
49 
50  /// Returns the set of dirty bits that should be
51  /// added to the change tracker for this prim, when this prim is inserted.
52  virtual HdDirtyBits GetInitialDirtyBitsMask() const = 0;
53 
54  /// This function gives an Rprim the chance to "early exit" from dirty
55  /// bit propagation, delegate sync and rprim sync altogether. It is
56  /// a temporary measure to prevent unnecessary work, like in the case of
57  /// invisible prims. The dirty bits in the change tracker remain the same.
58  /// See the implementation for the finer details.
59  HD_API
61 
62  /// This function gives an Rprim the chance to set additional dirty bits
63  /// based on those set in the change tracker, before passing the dirty bits
64  /// to the scene delegate.
65  /// It calls into _PropagateDirtyBits, which gives the Rprim an opportunity
66  /// to specify the additional data needed to process the requested changes.
67  ///
68  /// The return value is the new set of dirty bits.
69  HD_API
71 
72  /// Initialize the representation of this Rprim by calling _InitRepr.
73  /// This is called prior to dirty bit propagation & sync, the first time the
74  /// repr is used, or when the authored representation is dirty.
75  ///
76  /// dirtyBits is an in/out value. It is initialized to the dirty bits
77  /// from the change tracker. InitRepr can then set additional dirty bits
78  /// if additional data is required from the scene delegate when this
79  /// repr is synced.
80  HD_API
81  void InitRepr(HdSceneDelegate* delegate,
82  TfToken const &reprToken,
83  HdDirtyBits *dirtyBits);
84 
85  /// Pull invalidated scene data and prepare/update the renderable
86  /// representation.
87  ///
88  /// This function is told which scene data to pull through the
89  /// dirtyBits parameter. The first time it's called, dirtyBits comes
90  /// from _GetInitialDirtyBits(), which provides initial dirty state,
91  /// but after that it's driven by invalidation tracking in the scene
92  /// delegate.
93  ///
94  /// The contract for this function is that the prim can only pull on scene
95  /// delegate buffers that are marked dirty. Scene delegates can and do
96  /// implement just-in-time data schemes that mean that pulling on clean
97  /// data will be at best incorrect, and at worst a crash.
98  ///
99  /// This function is called in parallel from worker threads, so it needs
100  /// to be threadsafe; calls into HdSceneDelegate are ok.
101  ///
102  /// \param sceneDelegate The data source for this geometry item.
103  /// \param renderParam A render delegate object that holds rendering
104  /// parameters that scene geometry may use.
105  /// \param dirtyBits A specifier for which scene data has changed.
106  /// \param reprToken The representation that needs to be updated. This is
107  /// useful for backends that support multiple display
108  /// representations for an rprim. A given representation
109  /// may choose to pull on a subset of the dirty state.
110  /// \param dirtyBits On input specifies which state is dirty and can be
111  /// pulled from the scene delegate.
112  /// On output specifies which bits are still dirty and
113  /// were not cleaned by the sync.
114  virtual void Sync(HdSceneDelegate *delegate,
115  HdRenderParam *renderParam,
116  HdDirtyBits *dirtyBits,
117  TfToken const &reprToken) = 0;
118  // ---------------------------------------------------------------------- //
119  /// \name Rprim Hydra Engine API : Execute Phase
120  // ---------------------------------------------------------------------- //
121 
122  /// Returns the draw items for the requested repr token, if any.
123  /// These draw items should be constructed and cached beforehand by Sync().
124  /// If no draw items exist, or reprToken cannot be found, nullptr will be
125  /// returned.
126  HD_API
128  GetDrawItems(TfToken const& reprToken) const;
129 
130  // ---------------------------------------------------------------------- //
131  /// \name Rprim Hydra Engine API : Cleanup
132  // ---------------------------------------------------------------------- //
133  /// Finalizes object resources. This function might not delete resources,
134  /// but it should deal with resource ownership so that the rprim is
135  /// deletable.
136  HD_API
137  virtual void Finalize(HdRenderParam *renderParam);
138 
139  // ---------------------------------------------------------------------- //
140  /// \name Rprim Data API
141  // ---------------------------------------------------------------------- //
142 
143  /// Returns the identifier of this Rprim. This is both used in the
144  /// RenderIndex and the SceneDelegate and acts as the associative key for
145  /// the Rprim in both contexts.
146  SdfPath const& GetId() const { return _sharedData.rprimID; }
147 
148  /// Return the unique instance id
149  int32_t GetPrimId() const { return _primId; };
150 
151  /// Set the unique instance id
152  HD_API
153  void SetPrimId(int32_t primId);
154 
155  /// Returns the identifier of the instancer (if any) for this Rprim. If this
156  /// Rprim is not instanced, an empty SdfPath will be returned.
157  SdfPath const& GetInstancerId() const { return _instancerId; }
158 
159  /// Returns the path of the material to which this Rprim is bound. The
160  /// material object itself can be fetched from the RenderIndex using
161  /// this identifier.
162  SdfPath const& GetMaterialId() const { return _materialId; }
163 
164  /// Sets a new material binding to be used by this rprim
165  HD_API
166  void SetMaterialId(SdfPath const& materialId);
167 
169  return _authoredReprSelector;
170  }
171 
172  TfToken const& GetRenderTag() const {
173  return _renderTag;
174  }
175 
176  /// Returns the render tag associated to this rprim
177  inline TfToken GetRenderTag(HdSceneDelegate* delegate) const;
178 
179  /// Returns the bounds of the rprim in local, untransformed space.
180  inline GfRange3d GetExtent(HdSceneDelegate* delegate) const;
181 
182  /// Primvar Query
185  HdInterpolation interpolation) const;
186 
187  /// Returns the names of built-in primvars, i.e. primvars that
188  /// are part of the core geometric schema for this prim.
189  HD_API
190  virtual TfTokenVector const & GetBuiltinPrimvarNames() const = 0;
191 
192  inline VtValue
193  GetPrimvar(HdSceneDelegate* delegate, const TfToken &name) const;
194 
195  inline VtValue
196  GetIndexedPrimvar(HdSceneDelegate* delegate, const TfToken &name,
197  VtIntArray *indices) const;
198 
199  HD_API
200  VtMatrix4dArray GetInstancerTransforms(HdSceneDelegate* delegate);
201 
202  /// Returns true if any dirty flags are set for this rprim.
203  HD_API
204  bool IsDirty(HdChangeTracker &changeTracker) const;
205 
206  /// Is the prim itself visible
207  bool IsVisible() const { return _sharedData.visible; }
208 
209  HD_API
210  void UpdateReprSelector(HdSceneDelegate* delegate,
211  HdDirtyBits *dirtyBits);
212 
213  HD_API
214  virtual void UpdateRenderTag(HdSceneDelegate *delegate,
215  HdRenderParam *renderParam);
216 
217 protected:
218  // ---------------------------------------------------------------------- //
219  /// \name Rprim Hydra Engine API : Pre-Sync & Sync-Phase
220  // ---------------------------------------------------------------------- //
221 
222  /// This callback from Rprim gives the prim an opportunity to set
223  /// additional dirty bits based on those already set. This is done
224  /// before the dirty bits are passed to the scene delegate, so can be
225  /// used to communicate that extra information is needed by the prim to
226  /// process the changes.
227  ///
228  /// The return value is the new set of dirty bits, which replaces the bits
229  /// passed in.
230  ///
231  /// See HdRprim::PropagateRprimDirtyBits()
232  virtual HdDirtyBits _PropagateDirtyBits(HdDirtyBits bits) const = 0;
233 
234  /// Initialize the given representation of this Rprim.
235  /// This is called prior to syncing the prim, the first time the repr
236  /// is used.
237  ///
238  /// reprToken is the name of the representation to initalize.
239  ///
240  /// dirtyBits is an in/out value. It is initialized to the dirty bits
241  /// from the change tracker. InitRepr can then set additional dirty bits
242  /// if additional data is required from the scene delegate when this
243  /// repr is synced. InitRepr occurs before dirty bit propagation.
244  ///
245  /// See HdRprim::InitRepr()
246  virtual void _InitRepr(TfToken const &reprToken,
247  HdDirtyBits *dirtyBits) = 0;
248 
249  // ---------------------------------------------------------------------- //
250  /// \name Rprim Shared API
251  // ---------------------------------------------------------------------- //
252  HD_API
253  HdReprSharedPtr const & _GetRepr(TfToken const &reprToken) const;
254 
255  HD_API
256  void _UpdateVisibility(HdSceneDelegate *sceneDelegate,
257  HdDirtyBits *dirtyBits);
258 
259  HD_API
260  void _UpdateInstancer(HdSceneDelegate *sceneDelegate,
261  HdDirtyBits *dirtyBits);
262 
263 private:
264  SdfPath _instancerId;
265  SdfPath _materialId;
266 
267  // Used for id renders.
268  int32_t _primId;
269 
270 protected:
271  // shared data across reprs: bufferArrayRanges, bounds, visibility
273 
274  // authored repr selector
276 
277  // authored render tag
279 
280  // total number of reprs is relatively small (less than 5 or so
281  // in most case), we use linear container for efficiency.
282  using _ReprVector = std::vector<std::pair<TfToken, HdReprSharedPtr>>;
284 
286  {
287  _ReprComparator(TfToken const &name) : _name(name) {}
288  bool operator() (const std::pair<TfToken, HdReprSharedPtr> &e) const {
289  return _name == e.first;
290  }
291  private:
292  TfToken _name;
293  };
294 
295 
296  // Repr configuration descriptors. All concrete types (HdMesh, HdPoints ..)
297  // have this static map to lookup descriptors for the given reprToken.
298  //
299  // N : # of descriptors for the repr.
300  //
301  template<typename DESC_TYPE, int N=1>
303  {
304  using DescArray = std::array<DESC_TYPE, N>;
305  static const int MAX_DESCS = N;
306 
307  DescArray Find(TfToken const &reprToken) const {
308  // linear search, we expect only a handful reprs configured.
309  TF_FOR_ALL (it, _configs) {
310  if (it->first == reprToken) return it->second;
311  }
312  TF_CODING_ERROR("Repr %s not found", reprToken.GetText());
313  return DescArray();
314  }
315  void AddOrUpdate(TfToken const &reprToken, DescArray descs) {
316  for (auto& config : _configs) {
317  if (config.first == reprToken) {
318  // Overrwrite the existing entry.
319  config.second = descs;
320  return;
321  }
322  }
323  _configs.push_back(std::make_pair(reprToken, descs));
324  }
325  std::vector<std::pair<TfToken, DescArray> > _configs;
326  };
327 
328 };
329 
330 ////////////////////////////////////////////////////////////////////////////////
331 //
332 // Delegate API Wrappers
333 //
334 TfToken
336 {
337  return delegate->GetRenderTag(GetId());
338 }
339 
340 GfRange3d
342 {
343  return delegate->GetExtent(GetId());
344 }
345 
348  HdInterpolation interpolation) const
349 {
350  return delegate->GetPrimvarDescriptors(GetId(), interpolation);
351 }
352 
353 inline VtValue
355 {
356  return delegate->Get(GetId(), name);
357 }
358 
359 inline VtValue
361  VtIntArray *indices) const
362 {
363  return delegate->GetIndexedPrimvar(GetId(), name, indices);
364 }
365 
367 
368 #endif //PXR_IMAGING_HD_RPRIM_H
bool IsVisible() const
Is the prim itself visible.
Definition: rprim.h:207
TfToken _renderTag
Definition: rprim.h:278
SdfPath const & GetInstancerId() const
Definition: rprim.h:157
GLsizei GLenum const void * indices
Definition: glcorearb.h:406
virtual HD_API VtValue GetIndexedPrimvar(SdfPath const &id, TfToken const &key, VtIntArray *outIndices)
HD_API const HdRepr::DrawItemUniquePtrVector & GetDrawItems(TfToken const &reprToken) const
virtual void _InitRepr(TfToken const &reprToken, HdDirtyBits *dirtyBits)=0
uint32_t HdDirtyBits
Definition: types.h:143
#define TF_CODING_ERROR
DescArray Find(TfToken const &reprToken) const
Definition: rprim.h:307
virtual HD_API TfTokenVector const & GetBuiltinPrimvarNames() const =0
#define HD_API
Definition: api.h:23
std::shared_ptr< HdRepr > HdReprSharedPtr
Definition: rprim.h:30
std::vector< std::pair< TfToken, DescArray > > _configs
Definition: rprim.h:325
SdfPath const & GetMaterialId() const
Definition: rprim.h:162
TfToken const & GetRenderTag() const
Definition: rprim.h:172
HD_API void _UpdateInstancer(HdSceneDelegate *sceneDelegate, HdDirtyBits *dirtyBits)
HD_API HdReprSharedPtr const & _GetRepr(TfToken const &reprToken) const
int32_t GetPrimId() const
Return the unique instance id.
Definition: rprim.h:149
HD_API void SetPrimId(int32_t primId)
Set the unique instance id.
Definition: token.h:70
static const int MAX_DESCS
Definition: rprim.h:305
virtual HdDirtyBits GetInitialDirtyBitsMask() const =0
Definition: rprim.h:37
HdRprimSharedData _sharedData
Definition: rprim.h:272
bool operator()(const std::pair< TfToken, HdReprSharedPtr > &e) const
Definition: rprim.h:288
HdPrimvarDescriptorVector GetPrimvarDescriptors(HdSceneDelegate *delegate, HdInterpolation interpolation) const
Primvar Query.
Definition: rprim.h:347
VtValue GetPrimvar(HdSceneDelegate *delegate, const TfToken &name) const
Definition: rprim.h:354
HD_API HdRprim(SdfPath const &id)
virtual void Sync(HdSceneDelegate *delegate, HdRenderParam *renderParam, HdDirtyBits *dirtyBits, TfToken const &reprToken)=0
virtual HD_API HdPrimvarDescriptorVector GetPrimvarDescriptors(SdfPath const &id, HdInterpolation interpolation)
Returns descriptors for all primvars of the given interpolation type.
std::vector< TfToken > TfTokenVector
Convenience types.
Definition: token.h:440
virtual HD_API GfRange3d GetExtent(SdfPath const &id)
virtual HD_API TfToken GetRenderTag(SdfPath const &id)
GLuint const GLchar * name
Definition: glcorearb.h:786
std::vector< std::pair< TfToken, HdReprSharedPtr >> _ReprVector
Definition: rprim.h:282
Definition: path.h:273
char const * GetText() const
Definition: token.h:179
HdReprSelector _authoredReprSelector
Definition: rprim.h:275
HD_API bool IsDirty(HdChangeTracker &changeTracker) const
Returns true if any dirty flags are set for this rprim.
virtual HdDirtyBits _PropagateDirtyBits(HdDirtyBits bits) const =0
virtual HD_API void Finalize(HdRenderParam *renderParam)
virtual HD_API VtValue Get(SdfPath const &id, TfToken const &key)
Returns a named value.
std::vector< DrawItemUniquePtr > DrawItemUniquePtrVector
Definition: repr.h:143
PXR_NAMESPACE_CLOSE_SCOPE PXR_NAMESPACE_OPEN_SCOPE
Definition: path.h:1425
VtValue GetIndexedPrimvar(HdSceneDelegate *delegate, const TfToken &name, VtIntArray *indices) const
Definition: rprim.h:360
SdfPath const & GetId() const
Definition: rprim.h:146
_ReprComparator(TfToken const &name)
Definition: rprim.h:287
HdReprSelector const & GetReprSelector() const
Definition: rprim.h:168
_ReprVector _reprs
Definition: rprim.h:283
std::array< DESC_TYPE, N > DescArray
Definition: rprim.h:304
HD_API void SetMaterialId(SdfPath const &materialId)
Sets a new material binding to be used by this rprim.
HD_API void _UpdateVisibility(HdSceneDelegate *sceneDelegate, HdDirtyBits *dirtyBits)
virtual HD_API void UpdateRenderTag(HdSceneDelegate *delegate, HdRenderParam *renderParam)
HdInterpolation
Definition: enums.h:177
#define PXR_NAMESPACE_CLOSE_SCOPE
Definition: pxr.h:74
GA_API const UT_StringHolder N
void AddOrUpdate(TfToken const &reprToken, DescArray descs)
Definition: rprim.h:315
#define TF_FOR_ALL(iter, c)
Definition: iterator.h:373
HD_API void UpdateReprSelector(HdSceneDelegate *delegate, HdDirtyBits *dirtyBits)
std::vector< HdPrimvarDescriptor > HdPrimvarDescriptorVector
HD_API void InitRepr(HdSceneDelegate *delegate, TfToken const &reprToken, HdDirtyBits *dirtyBits)
virtual HD_API ~HdRprim()
HD_API VtMatrix4dArray GetInstancerTransforms(HdSceneDelegate *delegate)
HD_API bool CanSkipDirtyBitPropagationAndSync(HdDirtyBits bits) const
Definition: value.h:146
GfRange3d GetExtent(HdSceneDelegate *delegate) const
Returns the bounds of the rprim in local, untransformed space.
Definition: rprim.h:341
HD_API HdDirtyBits PropagateRprimDirtyBits(HdDirtyBits bits)