RixShading.h Source File

RixShading.h
1 #ifndef RixShading_h
2 #define RixShading_h
3 /* $Revision: #13 $ $Date: 2016/03/17 $ */
4 /*
5 # ------------------------------------------------------------------------------
6 #
7 # Copyright (c) 2011-2015 Pixar Animation Studios. All rights reserved.
8 #
9 # The information in this file (the "Software") is provided for the
10 # exclusive use of the software licensees of Pixar. Licensees have
11 # the right to incorporate the Software into other products for use
12 # by other authorized software licensees of Pixar, without fee.
13 # Except as expressly permitted herein, the Software may not be
14 # disclosed to third parties, copied or duplicated in any form, in
15 # whole or in part, without the prior written permission of
16 # Pixar Animation Studios.
17 #
18 # The copyright notices in the Software and this entire statement,
19 # including the above license grant, this restriction and the
20 # following disclaimer, must be included in all copies of the
21 # Software, in whole or in part, and all permitted derivative works of
22 # the Software, unless such copies or derivative works are solely
23 # in the form of machine-executable object code generated by a
24 # source language processor.
25 #
26 # PIXAR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
27 # ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT
28 # SHALL PIXAR BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES
29 # OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
30 # WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
31 # ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
32 # SOFTWARE.
33 #
34 # Pixar
35 # 1200 Park Ave
36 # Emeryville CA 94608
37 #
38 # ------------------------------------------------------------------------------
39 */
40 
75 #include "RixInterfaces.h"
76 #include <cassert>
77 #include <cstring> // for memcpy
78 #include <algorithm> // for std::fill_n
79 
80 #define k_RixShadingVersion 200 // XXY (XX: MAJOR, Y:MINOR)
81 
82 class RixBxdfFactory;
83 class RixBsdf;
84 class RixLightFilter;
85 class RixOpacity;
87 class RixDisplayServices;
88 class RixParameterList;
89 class RixLPEState;
90 struct RixSCParamInfo;
91 struct RtRayGeometry;
92 struct RtHitPoint;
93 struct RixBXLobeTraits;
94 
95 enum RtHitSides
96 {
97  k_SidesFront=1,
98  k_SidesBack=2,
99  k_SidesBoth=3
100 };
101 
102 
106 enum RixShadingInterface
107 {
108  k_RixInvalid=0,
109  k_RixPattern,
110  k_RixBxdfFactory,
111  k_RixIntegrator,
112  k_RixLightFilter,
113  k_RixProjection
114 };
115 
120 enum RixSCSyncMsg
121 {
123  k_RixSCRenderBegin,
124  k_RixSCRenderEnd,
125  k_RixSCInstanceEdit,
126  k_RixSCCancel,
128  k_RixSCIncrementBarrier
129 };
131 
137 {
138 public:
139  virtual int GetVersion() const { return m_version; }
140  virtual int GetInterface() const { return k_RixInvalid; }
141  virtual int Init(RixContext &ctx, char const *pluginPath) = 0;
142  virtual RixSCParamInfo const *GetParamTable() = 0;
143  virtual void Finalize(RixContext &ctx) = 0;
144 
149  virtual void Synchronize(RixContext & /* ctx */, RixSCSyncMsg /* syncMsg */,
150  RixParameterList const * /* parameterList */)
151  {
152  }
153 
182  {
183  InstanceData() : data(NULL), datalen(0), freefunc(NULL) {}
184  RtPointer data;
185  size_t datalen;
186  void (*freefunc)(RtPointer);
187  };
188  virtual int CreateInstanceData(RixContext &,
189  char const * /* handle */,
190  RixParameterList const *,
191  InstanceData * /* result */)
192  {
193  return -1; // 0 is success
194  }
195 
196 
197 protected:
198  RixShadingPlugin(int version) : m_version(version) {}
199  virtual ~RixShadingPlugin() {}
200  int m_version;
201 };
202 
206 enum RixSCType
207 {
208  k_RixSCInvalidType=0,
209  k_RixSCAnyType, // signals a dynamic binding scenario
210  k_RixSCInteger,
211  k_RixSCFloat,
212  k_RixSCFloat2,
213  k_RixSCFloat3,
214  k_RixSCColor,
215  k_RixSCPoint,
216  k_RixSCVector,
217  k_RixSCNormal,
218  k_RixSCMatrix,
219  k_RixSCString,
220  k_RixSCBxdf, // always uniform
221  k_RixSCLightFilter, // always uniform
222  k_RixSCStructBegin, // always uniform
223  k_RixSCStructEnd // always uniform
224 };
225 
230 enum RixSCDetail
231 {
232  k_RixSCInvalidDetail=0,
233  k_RixSCUniform, // needs an eval per shading "grid"
234  k_RixSCVarying, // needs an eval per shading point
235  k_RixSCAnyDetail
236 };
237 
241 enum RixSCAccess
242 {
243  k_RixSCInput=0,
244  k_RixSCOutput,
245  k_RixSCInvalidAccess
246 };
247 
252 enum RixSCVolumeSelector
253 {
254  k_RixSCAnyVolume,
255  k_RixSCIncidentVolume,
256  k_RixSCOppositeVolume
257 };
258 
263 enum RixSCConnectionInfo
264 {
265  k_RixSCDefaultValue = 0,
266  k_RixSCParameterListValue,
267  k_RixSCNetworkValue
268 };
269 
274 {
276  RixSCParamInfo(char const *nm, RixSCType t,
277  RixSCAccess a = k_RixSCInput,
278  int len = -1) :
279  name(nm),
280  customtype(NULL),
281  type(t),
282  access(a),
283  arraylen(len)
284  {
285  }
286 
288  RixSCParamInfo(char const *structnm, char const *nm,
289  RixSCType t, RixSCAccess a = k_RixSCInput,
290  int len = -1) :
291  name(nm),
292  customtype(structnm),
293  type(t),
294  access(a),
295  arraylen(len)
296  {
297  }
298 
301  name(NULL),
302  customtype(NULL),
303  type(k_RixSCInvalidType),
304  access(k_RixSCInvalidAccess),
305  arraylen(-1)
306  {
307  }
308 
309  char const *name;
310  char const *customtype; // NULL unless struct
311  RixSCType type;
312  RixSCAccess access;
313  int arraylen; // -1 means no array, 0 means empty
314  bool IsArray() const { return (arraylen != -1); }
315 };
316 
324 enum RixSCShadingMode
325 {
326  k_RixSCInvalidShadingMode,
327  k_RixSCPresenceQuery,
328  k_RixSCOpacityQuery,
329  k_RixSCScatterQuery,
330  k_RixSCVolumeTransmissionQuery,
331  k_RixSCVolumeScatterQuery,
332  k_RixSCPatternQuery
335 };
336 
343 {
344 public:
345  virtual RtInt GetNumParams() const = 0;
346 
353  virtual RtInt GetParamId(char const *name, RtInt *paramid) const = 0;
354 
358  virtual RtInt GetParamId(int plistIndex, RtInt *paramid) const = 0;
359 
364  virtual RtInt GetParamInfo(RtInt paramid, RixSCType *type,
365  RixSCConnectionInfo *cinfo,
366  int *arraylength=NULL) const = 0;
367 
370  RtInt GetParamInfo(RtInt paramid, RixSCType *type,
371  bool *isconnected, int *arraylength=NULL) const
372  {
373  RixSCConnectionInfo cinfo;
374  int err = GetParamInfo(paramid, type, &cinfo, arraylength);
375  if(isconnected)
376  *isconnected = (cinfo == k_RixSCNetworkValue);
377  return err;
378  }
379 
390  virtual RixSCDetail EvalParam(RtInt paramid, RtInt arrayindex,
391  RtInt * result) const = 0;
392  virtual RixSCDetail EvalParam(RtInt paramid, RtInt arrayindex,
393  RtFloat * result) const = 0;
394  virtual RixSCDetail EvalParam(RtInt paramid, RtInt arrayindex,
395  RtColorRGB * result) const = 0;
396  virtual RixSCDetail EvalParam(RtInt paramid, RtInt arrayindex,
397  RtFloat3 * result) const = 0;
398  virtual RixSCDetail EvalParam(RtInt paramid, RtInt arrayindex,
399  RtMatrix4x4 * result) const = 0;
400  virtual RixSCDetail EvalParam(RtInt paramid, RtInt arrayindex,
401  RtConstString * result) const = 0;
402  virtual RixSCDetail EvalParam(RtInt paramid, RtInt arrayindex,
403  RixLightFilter ** result,
404  RtConstPointer * instance) const = 0;
405 protected:
406  virtual ~RixParameterList() {}
407 };
408 
433 class RixShadingContext : public RixContext
434 {
435 public:
442  struct Id
443  {
444  Id() : shadingCtxNum(-6666)
445  {
446  }
447  Id(unsigned int i) : integratorCtxNum(static_cast<short>(i >> 16)),
448  shadingCtxNum(static_cast<short>(i & 0xFFFF))
449  {
450  }
451  // Convert to a serialized integral representation.
452  unsigned int Serialize() const
453  {
454  return ((unsigned int) integratorCtxNum << 16) |
455  ((unsigned int) shadingCtxNum & 0xFFFF);
456  }
457  void Invalidate() { shadingCtxNum = -6666; }
458  bool IsValid() const { return shadingCtxNum != -6666; }
459  short integratorCtxNum;
460  short shadingCtxNum;
461  } shadingCtxId;
462 
465  RtInt numPts;
466 
469  struct
470  {
471  unsigned eyePath : 1;
472  unsigned lightPath : 1;
473  unsigned primaryHit : 1;
474  unsigned missContext : 1;
475  unsigned reyesGrid : 1 ;
476 
481  RixSCShadingMode shadingMode;
482  union
483  {
487 
488  // The opacity shader is non-NULL when computing presence and
489  // transmission.
490  RixOpacity *opacity;
491  } shader;
492 
493  // The volume shader is non-NULL when invoking volume integrators.
494  RixVolumeIntegrator *volume;
495 
496  } scTraits; // "uniform" traits associated with the shading context
497 
498  bool HasHits() const { return (scTraits.missContext == 0); }
499  bool HasMisses() const { return (scTraits.missContext == 1); }
500 
501  RixBsdf *GetBsdf() const
502  {
503  assert(scTraits.shadingMode == k_RixSCScatterQuery ||
504  scTraits.shadingMode == k_RixSCVolumeScatterQuery);
505  return scTraits.shader.bsdf;
506  }
507 
508  RixOpacity *GetOpacity() const
509  {
510  assert(scTraits.shadingMode == k_RixSCOpacityQuery ||
511  scTraits.shadingMode == k_RixSCPresenceQuery ||
512  scTraits.shadingMode == k_RixSCVolumeTransmissionQuery);
513  return scTraits.shader.opacity;
514  }
515 
516  RixVolumeIntegrator *GetVolume() const
517  {
518  assert(scTraits.shadingMode == k_RixSCScatterQuery ||
519  scTraits.shadingMode == k_RixSCVolumeScatterQuery ||
520  scTraits.shadingMode == k_RixSCVolumeTransmissionQuery);
521  return scTraits.volume;
522  }
523 
534  virtual bool HasVolume(RixSCVolumeSelector) const = 0;
535  virtual RixVolumeIntegrator *BeginVolume(RixSCVolumeSelector,
536  RtInt nrays, RtRayGeometry *rays) const = 0;
537  virtual void EndVolume(RixVolumeIntegrator *) const = 0;
540  RtRayGeometry *rays) const
541  {
542  return BeginVolume(k_RixSCIncidentVolume, nrays, rays);
543  }
544  RixVolumeIntegrator *BeginOppositeVol(RtInt nrays,
545  RtRayGeometry *rays) const
546  {
547  return BeginVolume(k_RixSCOppositeVolume, nrays, rays);
548  }
549 
575  virtual RixShadingContext *BeginVolumeSampling() const = 0;
576  virtual RixShadingContext const *EndVolumeSampling(RixShadingContext *,
577  RixBXLobeTraits const *exposeVol=NULL,
578  RtInt const *membership=NULL) const = 0;
579 
582  virtual std::vector<const RixShadingContext *> const *
583  GetOverlappingVolumes() const = 0;
584 
591  {
592  k_SSDiffusion // beam diffusion
593  };
594  virtual RixVolumeIntegrator *GetBuiltinVolume(BuiltinVolume,
595  RixBxdfFactory *) const = 0;
596 
604 
610  RtInt *rayId;
611 
616  RtColorRGB *transmission;
617 
618  // If the shading context was created via an importance sampling method,
619  // this is the associated weight the integrator needs to multiply in.
620  RtFloat *pointWeight;
621 
623  mutable void *lightingServicesData;
624 
629  {
630  k_NullBsdf
631  };
632  virtual RixBsdf *GetBuiltinBsdf(BuiltinBsdf, RixBxdfFactory *) const = 0;
633 
638  virtual RixDisplayServices *GetDisplayServices(int version = 1) const = 0;
639 
640  enum BuiltinVar
641  {
642  k_P=0,
643  k_PRadius,
644  k_Po, // undisplaced P
645  k_Nn, // normalized shading normal
646  k_Ngn, // normalized geometric normal
647  k_Non, // undisplaced N
648  k_Tn, // normalized shading tangent
649  k_Vn, // normalized view vector, points away from shading points
650  k_VLen, // length of V: from the P to previous P
651  k_curvature, // local surface curvature
652  k_incidentRaySpread, // spread of incident ray: how much the ray radius increased for each unit distance the ray travelled
653  k_incidentRayRadius, // radius of incident ray at hit pt
654  k_incidentLobeSampled, // RixBXLobeSampled of incident rays (as RtInt)
655  k_mpSize, // size of micropoly that ray hit (0 for non-tessel. surfaces)
656  k_biasR, // bias to apply for rays leaving the surface
657  k_biasT, // bias to apply for rays passing through the surface
658  k_u,
659  k_v,
660  k_w,
661  k_du, k_dufp = k_du, // k_dufp is an alias for k_du (fp: ray footprint)
662  k_dv, k_dvfp = k_dv,
663  k_dw, k_dwfp = k_dw,
664  k_dPdu,
665  k_dPdv,
666  k_dPdw,
667  k_dPdtime,
668  k_time,
669  k_Id, // the RtInt assigned via Attribute "identifier" "id"
670  k_outsideIOR,
671  k_Oi,
672  k_lpeState,
673  k_launchShadingCtxId,
674  k_motionFore, // 2D raster-space motion vectors (optical flow)
675  k_motionBack,
676  k_numBuiltinVars
677  };
678  virtual void GetBuiltinVar(BuiltinVar, RtInt const**var) const = 0;
679  virtual void GetBuiltinVar(BuiltinVar, RtFloat const**var) const = 0;
680  virtual void GetBuiltinVar(BuiltinVar, RtFloat3 const**var) const = 0;
681  virtual void GetBuiltinVar(BuiltinVar, RixLPEState * const**var) const = 0;
682 
685  virtual void SetBuiltinVar(BuiltinVar, RtFloat *var) = 0;
686  virtual void SetBuiltinVar(BuiltinVar, RtFloat3 *var) = 0;
687 
698  virtual RixSCDetail GetPrimVar(char const *name,
699  RixSCType *type, RtInt *arraylen) const = 0;
700  virtual RixSCDetail GetPrimVar(char const *name, RtFloat fill,
701  RtFloat const **var,
702  RtFloat const **radius=NULL) const = 0;
703  virtual RixSCDetail GetPrimVar(char const *name, RtFloat2 fill,
704  RtFloat2 const **var,
705  RtFloat const **radius=NULL) const = 0;
706  virtual RixSCDetail GetPrimVar(char const *name, RtFloat3 fill,
707  RtFloat3 const **var,
708  RtFloat const **radius=NULL) const = 0;
709  virtual RixSCDetail GetPrimVar(char const *name,
710  RtConstString **var) const = 0;
711 
717 
718  virtual RixSCDetail GetPrimVar(char const *name,
719  RtFloat const **var,
720  RtFloat const **dXdu,
721  RtFloat const **dXdv) const = 0;
722  virtual RixSCDetail GetPrimVar(char const *name,
723  RtFloat2 const **var,
724  RtFloat const **dXdu,
725  RtFloat const **dYdu,
726  RtFloat const **dXdv,
727  RtFloat const **dYdv) const = 0;
728  virtual RixSCDetail GetPrimVar(char const *name,
729  RtFloat3 const **var,
730  RtFloat const **dXdu,
731  RtFloat const **dYdu,
732  RtFloat const **dZdu,
733  RtFloat const **dXdv,
734  RtFloat const **dYdv,
735  RtFloat const **dZdv) const = 0;
736 
739  virtual void SetPrimVar(char const *name, RixSCDetail d,
740  RtFloat *var, RtFloat *radius) = 0;
741  virtual void SetPrimVar(char const *name, RixSCDetail d,
742  RtFloat2 *var, RtFloat *radius) = 0;
743  virtual void SetPrimVar(char const *name, RixSCDetail d,
744  RtFloat3 *var, RtFloat *radius) = 0;
745  virtual void SetPrimVar(char const *name, RixSCDetail d,
746  RtString *var) = 0;
747 
748  enum TransformInterpretation
749  {
750  k_AsPoints,
751  k_AsVectors,
752  k_AsNormals
753  };
754 
759  virtual int Transform(TransformInterpretation interp,
760  char const *fromSpace, char const *toSpace,
761  RtFloat3 *var, RtFloat *radius = NULL) const = 0;
762 
768  virtual int GetTransform(char const *fromSpace, char const *toSpace,
769  RtMatrix4x4 const **matrix, int *numMatrices) const = 0;
770 
776  virtual RixShadingContext *CreateMutableContext() const = 0;
777 
782  virtual RixShadingContext const *GetPrimaryContext() const = 0;
783 
790  virtual RixShadingContext const *
791  GetContextById(RixShadingContext::Id sctxId) const = 0;
792 
827  virtual RixSCDetail EvalParam(RtInt id, RtInt arrayindex,
828  RtInt const ** result,
829  RtInt const *dflt=NULL,
830  bool promoteToVarying=false) const = 0;
831  virtual RixSCDetail EvalParam(RtInt id, RtInt arrayindex,
832  RtFloat const ** result,
833  RtFloat const *dflt=NULL,
834  bool promoteToVarying=false) const = 0;
835  virtual RixSCDetail EvalParam(RtInt id, RtInt arrayindex,
836  RtColorRGB const ** result,
837  RtColorRGB const *dflt=NULL,
838  bool promoteToVarying=false) const = 0;
839  virtual RixSCDetail EvalParam(RtInt id, RtInt arrayindex,
840  RtFloat3 const ** result,
841  RtFloat3 const *dflt=NULL,
842  bool promoteToVarying=false) const = 0;
843  virtual RixSCDetail EvalParam(RtInt id, RtInt arrayindex,
844  RtMatrix4x4 const ** result,
845  RtMatrix4x4 const *dflt=NULL,
846  bool promoteToVarying=false) const = 0;
847  virtual RixSCDetail EvalParam(RtInt id, RtInt arrayindex,
848  RtConstString** result,
849  RtConstString *dflt=NULL,
850  bool promoteToVarying=false) const = 0;
851  virtual RixSCDetail EvalParam(RtInt id, RtInt arrayindex,
852  RixBxdfFactory** result,
853  RixBxdfFactory *dflt=NULL,
854  bool promoteToVarying=false) const = 0;
855 
856  enum MemCategory
857  {
858  k_BxdfMem,
859  k_PatternMem
860  };
861 
868  template <class T>
869  RixSCDetail EvalAndCopyParam(RtInt id, RtInt arrayindex,
870  T ** result,
871  T const *dflt=NULL,
872  bool promoteToVarying=false,
873  MemCategory mcat=k_BxdfMem) const
874  {
875  T const *constResult;
876  RixSCDetail d = EvalParam(id, arrayindex, &constResult, dflt);
877  switch(d)
878  {
879  case k_RixSCVarying:
880  *result = (T *) Allocate(this->numPts, sizeof(T), mcat);
881  memcpy(*result, constResult, this->numPts*sizeof(T));
882  break;
883  case k_RixSCUniform:
884  if(promoteToVarying)
885  {
886  *result = (T *) Allocate(this->numPts, sizeof(T), mcat);
887  std::fill_n(*result, this->numPts, constResult[0]);
888  }
889  else
890  {
891  *result = (T *) Allocate(1, sizeof(T), mcat);
892  (*result)[0] = constResult[0];
893  }
894  break;
895  default:
896  *result = 0x0;
897  break;
898  }
899  return d;
900  }
901 
907  virtual RtInt GetParamId(char const *name, RtInt *paramid) const = 0;
908 
913  virtual RtInt GetParamInfo(RtInt paramid, RixSCType *type,
914  RixSCConnectionInfo *cinfo,
915  int *arraylength=NULL) const = 0;
916 
919  RtInt GetParamInfo(RtInt paramid, RixSCType *type,
920  bool *isconnected, int *arraylength=NULL) const
921  {
922  RixSCConnectionInfo cinfo;
923  int err = GetParamInfo(paramid, type, &cinfo, arraylength);
924  if(isconnected)
925  *isconnected = (cinfo == k_RixSCNetworkValue);
926  return err;
927  }
928 
935  virtual void GetNearestHits(RtInt numRays, RtRayGeometry const *rays,
936  // result:
937  RtHitPoint *hits,
938  // optional parameters:
939  char const *subset=NULL,
940  RtHitSides hitSides=k_SidesBoth) const = 0;
941 
947  virtual void GetLightEmission(RtColorRGB *e) const = 0;
948 
957  virtual void *Allocate(size_t n, size_t size, MemCategory m) const = 0;
958 
966  template <class T>
967  T *New(size_t nObjs, MemCategory cat=k_BxdfMem) const
968  {
969  T *mem = static_cast<T*>(Allocate(nObjs, sizeof(T), cat));
970  return new (mem) T[nObjs];
971  }
972 
984  class Allocator
985  {
986  public:
987  Allocator(RixShadingContext const *sctx) : m_sctx(sctx) {}
988  template <typename T>
989  T *Allocate(RtInt num)
990  {
991  if(num == 0) return NULL;
992  return (T *) m_sctx->Allocate(num, sizeof(T), k_BxdfMem);
993  }
994  template <typename T>
995  T *AllocFor(MemCategory memcat, RtInt num)
996  {
997  if(num == 0) return NULL;
998  return (T *) m_sctx->Allocate(num, sizeof(T), memcat);
999  }
1000  template <typename T>
1001  T *AllocForVolume(RtInt num)
1002  {
1003  // currently the memory-pool lifetime of volumes matches
1004  // that of Bxdf.
1005  if(num == 0) return NULL;
1006  return (T *) m_sctx->Allocate(num, sizeof(T), k_BxdfMem);
1007  }
1008  template <typename T>
1009  T *AllocForBxdf(RtInt num)
1010  {
1011  if(num == 0) return NULL;
1012  return (T *) m_sctx->Allocate(num, sizeof(T), k_BxdfMem);
1013  }
1014  template <typename T>
1015  T *AllocForPattern(RtInt num)
1016  {
1017  if(num == 0) return NULL;
1018  return (T *) m_sctx->Allocate(num, sizeof(T), k_PatternMem);
1019  }
1020 
1021  private:
1022  RixShadingContext const *m_sctx;
1023  };
1024 
1025 protected:
1026  virtual ~RixShadingContext() {}
1027 };
1028 
1029 #endif