1 //-*****************************************************************************
2 //
3 // Copyright (c) 2009-2012,
4 //  Sony Pictures Imageworks Inc. and
5 //  Industrial Light & Magic, a division of Lucasfilm Entertainment Company Ltd.
6 //
7 // All rights reserved.
8 //
9 // Redistribution and use in source and binary forms, with or without
10 // modification, are permitted provided that the following conditions are
11 // met:
12 // *       Redistributions of source code must retain the above copyright
13 // notice, this list of conditions and the following disclaimer.
14 // *       Redistributions in binary form must reproduce the above
15 // copyright notice, this list of conditions and the following disclaimer
16 // in the documentation and/or other materials provided with the
17 // distribution.
18 // *       Neither the name of Sony Pictures Imageworks, nor
19 // Industrial Light & Magic, nor the names of their contributors may be used
20 // to endorse or promote products derived from this software without specific
21 // prior written permission.
22 //
23 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
26 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
27 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
28 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
29 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
30 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
31 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
32 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
33 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34 //
35 //-*****************************************************************************
36 
37 #ifndef Alembic_AbcGeom_INuPatch_h
38 #define Alembic_AbcGeom_INuPatch_h
39 
40 #include <Alembic/Util/Export.h>
41 #include <Alembic/AbcGeom/Foundation.h>
42 #include <Alembic/AbcGeom/SchemaInfoDeclarations.h>
43 #include <Alembic/AbcGeom/IGeomParam.h>
44 #include <Alembic/AbcGeom/IGeomBase.h>
45 
46 namespace Alembic {
47 namespace AbcGeom {
48 namespace ALEMBIC_VERSION_NS {
49 
50 //-*****************************************************************************
51 class ALEMBIC_EXPORT INuPatchSchema : public IGeomBaseSchema<NuPatchSchemaInfo>
52 {
53 public:
54     class Sample
55     {
56     public:
57         typedef Sample this_type;
58 
59         // Users don't ever create this data directly.
Sample()60         Sample() { reset(); }
61 
getPositions()62         Abc::P3fArraySamplePtr getPositions() const { return m_positions; }
getVelocities()63         Abc::V3fArraySamplePtr getVelocities() const { return m_velocities; }
getNumU()64         int32_t getNumU() const { return m_numU; }
getNumV()65         int32_t getNumV() const { return m_numV; }
getUOrder()66         int32_t getUOrder() const { return m_uOrder; }
getVOrder()67         int32_t getVOrder() const { return m_vOrder; }
getUKnot()68         Abc::FloatArraySamplePtr getUKnot() const { return m_uKnot; }
getVKnot()69         Abc::FloatArraySamplePtr getVKnot() const { return m_vKnot; }
70 
71         // if this is NULL then the weight value of the position for each
72         // point is 1
getPositionWeights()73         Abc::FloatArraySamplePtr getPositionWeights() const { return m_positionWeights; }
74 
75         // trim curve
getTrimNumLoops()76         int32_t getTrimNumLoops() const { return m_trimNumLoops; }
getTrimNumVertices()77         Abc::Int32ArraySamplePtr getTrimNumVertices() const { return m_trimNumVertices; }
getTrimNumCurves()78         Abc::Int32ArraySamplePtr getTrimNumCurves() const { return m_trimNumCurves; }
getTrimOrders()79         Abc::Int32ArraySamplePtr getTrimOrders() const { return m_trimOrder; }
getTrimKnots()80         Abc::FloatArraySamplePtr getTrimKnots() const { return m_trimKnot; }
getTrimMins()81         Abc::FloatArraySamplePtr getTrimMins() const { return m_trimMin; }
getTrimMaxes()82         Abc::FloatArraySamplePtr getTrimMaxes() const { return m_trimMax; }
getTrimU()83         Abc::FloatArraySamplePtr getTrimU() const { return m_trimU; }
getTrimV()84         Abc::FloatArraySamplePtr getTrimV() const { return m_trimV; }
getTrimW()85         Abc::FloatArraySamplePtr getTrimW() const { return m_trimW; }
86 
hasTrimCurve()87         bool hasTrimCurve() const { return m_trimNumLoops != 0; }
88 
valid()89         bool valid() const
90         {
91             return m_positions && m_numU && m_numV && m_uOrder && m_vOrder &&
92                 m_uKnot && m_vKnot;
93         }
94 
getSelfBounds()95         Abc::Box3d getSelfBounds() const { return m_selfBounds; }
96 
reset()97         void reset()
98         {
99             m_positions.reset();
100             m_velocities.reset();
101             m_numU = 0;
102             m_numV = 0;
103             m_uOrder = 0;
104             m_vOrder = 0;
105             m_uKnot.reset();
106             m_vKnot.reset();
107             m_positionWeights.reset();
108 
109             m_selfBounds.makeEmpty();
110 
111             // trim curve
112             m_trimNumLoops = 0;
113             m_trimNumCurves.reset();
114             m_trimNumVertices.reset();
115             m_trimOrder.reset();
116             m_trimKnot.reset();
117             m_trimMin.reset();
118             m_trimMax.reset();
119             m_trimU.reset();
120             m_trimV.reset();
121             m_trimW.reset();
122         }
123 
124         ALEMBIC_OPERATOR_BOOL( valid() );
125 
126     protected:
127 
128         friend class INuPatchSchema;
129 
130         Abc::P3fArraySamplePtr m_positions;
131         Abc::V3fArraySamplePtr m_velocities;
132         int32_t m_numU;
133         int32_t m_numV;
134         int32_t m_uOrder;
135         int32_t m_vOrder;
136         Abc::FloatArraySamplePtr m_uKnot;
137         Abc::FloatArraySamplePtr m_vKnot;
138         Abc::FloatArraySamplePtr m_positionWeights;
139 
140         // trim curve
141         int32_t m_trimNumLoops;
142         Abc::Int32ArraySamplePtr m_trimNumCurves;
143         Abc::Int32ArraySamplePtr m_trimNumVertices;
144         Abc::Int32ArraySamplePtr m_trimOrder;
145         Abc::FloatArraySamplePtr m_trimKnot;
146         Abc::FloatArraySamplePtr m_trimMin;
147         Abc::FloatArraySamplePtr m_trimMax;
148         Abc::FloatArraySamplePtr m_trimU;
149         Abc::FloatArraySamplePtr m_trimV;
150         Abc::FloatArraySamplePtr m_trimW;
151         bool m_hasTrimCurve;
152 
153         // bounds
154         Abc::Box3d m_selfBounds;
155 
156     };
157 
158     //-*************************************************************************
159     // NuPatch Schema
160     //-*************************************************************************
161 public:
162     //! By convention we always define this_type in AbcGeom classes.
163     //! Used by unspecified-bool-type conversion below
164     typedef INuPatchSchema this_type;
165     typedef Sample sample_type;
166 
167     //-*************************************************************************
168     // CONSTRUCTION, DESTRUCTION, ASSIGNMENT
169     //-*************************************************************************
170 
171     //! The default constructor
INuPatchSchema()172     INuPatchSchema()
173     {
174         m_hasTrimCurve = false;
175     }
176 
177     //! copy constructor
INuPatchSchema(const INuPatchSchema & iCopy)178     INuPatchSchema(const INuPatchSchema& iCopy)
179         : IGeomBaseSchema<NuPatchSchemaInfo>()
180     {
181         *this = iCopy;
182     }
183 
184     //! This constructor creates a new nurbs patch reader.
185     //! The first argument is the parent ICompoundProperty, from which the
186     //! error handler policy for is derived.  The second argument is the name
187     //! of the ICompoundProperty that contains this schemas properties.  The
188     //! remaining optional arguments can be used to override the
189     //! ErrorHandlerPolicy and to specify schema interpretation matching.
190     INuPatchSchema( const ICompoundProperty &iParent,
191                     const std::string &iName,
192                     const Abc::Argument &iArg0 = Abc::Argument(),
193                     const Abc::Argument &iArg1 = Abc::Argument() )
194       : IGeomBaseSchema<NuPatchSchemaInfo>( iParent, iName, iArg0, iArg1 )
195     {
196         init( iArg0, iArg1 );
197     }
198 
199     //! This constructor wraps an existing ICompoundProperty as the nurbs
200     //! reader, and the error handler policy is derived from it.
201     //! The  remaining optional arguments can be used to override the
202     //! ErrorHandlerPolicy and to specify schema interpretation matching.
203     explicit INuPatchSchema( const ICompoundProperty &iProp,
204                              const Abc::Argument &iArg0 = Abc::Argument(),
205                              const Abc::Argument &iArg1 = Abc::Argument() )
206 
207       : IGeomBaseSchema<NuPatchSchemaInfo>( iProp, iArg0, iArg1 )
208     {
209         init( iArg0, iArg1 );
210     }
211 
212     //! Return the number of samples contained in the property.
213     //! This can be any number, including zero.
214     //! This returns the number of samples that were written, independently
215     //! of whether or not they were constant.
getNumSamples()216     size_t getNumSamples() const
217     { return m_positionsProperty.getNumSamples(); }
218 
219     //! Return the topological variance.
220     //! This indicates how the mesh may change.
221     MeshTopologyVariance getTopologyVariance() const;
222 
223     //! Ask if we're constant - no change in value amongst samples,
224     //! regardless of the time sampling.
isConstant()225     bool isConstant() const { return getTopologyVariance() == kConstantTopology; }
226 
227     //! Time information.
getTimeSampling()228     AbcA::TimeSamplingPtr getTimeSampling() const
229     {
230         return m_positionsProperty.getTimeSampling();
231     }
232 
233     void get( sample_type &oSample,
234               const Abc::ISampleSelector &iSS = Abc::ISampleSelector() ) const;
235 
236     Sample getValue( const Abc::ISampleSelector &iSS = Abc::ISampleSelector() ) const
237     {
238         Sample smp;
239         get( smp, iSS );
240         return smp;
241     }
242 
getPositionsProperty()243     Abc::IP3fArrayProperty getPositionsProperty() const { return m_positionsProperty; }
getUKnotsProperty()244     Abc::IFloatArrayProperty getUKnotsProperty() const { return m_uKnotProperty; }
getVKnotsProperty()245     Abc::IFloatArrayProperty getVKnotsProperty() const { return m_vKnotProperty; }
246 
getVelocitiesProperty()247     Abc::IV3fArrayProperty getVelocitiesProperty() const
248     {
249         return m_velocitiesProperty;
250     }
251 
252     // if this property is invalid then the weight for every point is 1
getPositionWeightsProperty()253     Abc::IFloatArrayProperty getPositionWeightsProperty() const
254     {
255         return m_positionWeightsProperty;
256     }
257 
getNormalsParam()258     IN3fGeomParam getNormalsParam() const
259     {
260         return m_normalsParam;
261     }
262 
getUVsParam()263     IV2fGeomParam getUVsParam() const
264     {
265         return m_uvsParam;
266     }
267 
268 
hasTrimCurve()269     bool hasTrimCurve() const { return m_hasTrimCurve; }
270     bool trimCurveTopologyIsHomogenous() const;
271     bool trimCurveTopologyIsConstant() const;
272 
273 
274     //-*************************************************************************
275     // ABC BASE MECHANISMS
276     // These functions are used by Abc to deal with errors, rewrapping,
277     // and so on.
278     //-*************************************************************************
279 
280     //! Reset returns this function set to an empty, default
281     //! state.
reset()282     void reset()
283     {
284         m_positionsProperty.reset();
285         m_velocitiesProperty.reset();
286         m_numUProperty.reset();
287         m_numVProperty.reset();
288         m_uOrderProperty.reset();
289         m_vOrderProperty.reset();
290         m_uKnotProperty.reset();
291         m_vKnotProperty.reset();
292         m_positionWeightsProperty.reset();
293 
294         m_normalsParam.reset();
295         m_uvsParam.reset();
296 
297         // reset trim curve attributes
298         m_trimNumLoopsProperty.reset();
299         m_trimNumCurvesProperty.reset();
300         m_trimNumVerticesProperty.reset();
301         m_trimOrderProperty.reset();
302         m_trimKnotProperty.reset();
303         m_trimMinProperty.reset();
304         m_trimMaxProperty.reset();
305         m_trimUProperty.reset();
306         m_trimVProperty.reset();
307         m_trimWProperty.reset();
308 
309         IGeomBaseSchema<NuPatchSchemaInfo>::reset();
310     }
311 
312     //! Valid returns whether this function set is
313     //! valid.
valid()314     bool valid() const
315     {
316         return ( IGeomBaseSchema<NuPatchSchemaInfo>::valid() &&
317                  m_positionsProperty.valid() &&
318                  m_numUProperty.valid() &&
319                  m_numVProperty.valid() &&
320                  m_uOrderProperty.valid() &&
321                  m_vOrderProperty.valid() &&
322                  m_uKnotProperty.valid() &&
323                  m_vKnotProperty.valid() );
324     }
325 
326     //! unspecified-bool-type operator overload.
327     //! ...
328     ALEMBIC_OVERRIDE_OPERATOR_BOOL( INuPatchSchema::valid() );
329 
330 protected:
331     bool hasTrimProps() const;
332 
333 protected:
334     void init( const Abc::Argument &iArg0,
335                const Abc::Argument &iArg1 );
336 
337     // required properties
338     Abc::IP3fArrayProperty m_positionsProperty;
339     Abc::IInt32Property m_numUProperty;
340     Abc::IInt32Property m_numVProperty;
341     Abc::IInt32Property m_uOrderProperty;
342     Abc::IInt32Property m_vOrderProperty;
343     Abc::IFloatArrayProperty m_uKnotProperty;
344     Abc::IFloatArrayProperty m_vKnotProperty;
345 
346     // optional
347     Abc::IV3fArrayProperty m_velocitiesProperty;
348     Abc::IFloatArrayProperty m_positionWeightsProperty;
349     IN3fGeomParam m_normalsParam;
350     IV2fGeomParam m_uvsParam;
351 
352     // optional trim curve properties
353     Abc::IInt32Property m_trimNumLoopsProperty;
354     Abc::IInt32ArrayProperty m_trimNumVerticesProperty;
355     Abc::IInt32ArrayProperty m_trimNumCurvesProperty;
356     Abc::IInt32ArrayProperty m_trimOrderProperty;
357     Abc::IFloatArrayProperty m_trimKnotProperty;
358     Abc::IFloatArrayProperty m_trimMinProperty;
359     Abc::IFloatArrayProperty m_trimMaxProperty;
360     Abc::IFloatArrayProperty m_trimUProperty;
361     Abc::IFloatArrayProperty m_trimVProperty;
362     Abc::IFloatArrayProperty m_trimWProperty;
363 
364     bool m_hasTrimCurve;
365 };
366 
367 //-*****************************************************************************
368 typedef Abc::ISchemaObject<INuPatchSchema> INuPatch;
369 
370 typedef Util::shared_ptr< INuPatch > INuPatchPtr;
371 
372 } // End namespace ALEMBIC_VERSION_NS
373 
374 using namespace ALEMBIC_VERSION_NS;
375 
376 } // End namespace AbcGeom
377 } // End namespace Alembic
378 
379 #endif
380