IECoreScene::PrimitiveVariable FromMayaMeshConverter::points() const { MFnMesh fnMesh; const MDagPath *d = dagPath( true ); if( d ) { fnMesh.setObject( *d ); } else { fnMesh.setObject( object() ); } V3fVectorDataPtr points = new V3fVectorData; points->setInterpretation( GeometricData::Point ); int numVerts = fnMesh.numVertices(); points->writable().resize( numVerts ); if( space() == MSpace::kObject ) { const V3f* rawPoints = ( const V3f* )fnMesh.getRawPoints(0); copy( rawPoints, rawPoints + numVerts, points->writable().begin() ); } else { MFloatPointArray mPoints; fnMesh.getPoints( mPoints, space() ); std::transform( MArrayIter<MFloatPointArray>::begin( mPoints ), MArrayIter<MFloatPointArray>::end( mPoints ), points->writable().begin(), VecConvert<MFloatPoint, V3f>() ); } return PrimitiveVariable( PrimitiveVariable::Vertex, points ); }
IECoreScene::PrimitiveVariable FromMayaMeshConverter::normals() const { MFnMesh fnMesh; const MDagPath *d = dagPath( true ); if( d ) { fnMesh.setObject( *d ); } else { fnMesh.setObject( object() ); } V3fVectorDataPtr normalsData = new V3fVectorData; normalsData->setInterpretation( GeometricData::Normal ); vector<V3f> &normals = normalsData->writable(); normals.reserve( fnMesh.numFaceVertices() ); int numPolygons = fnMesh.numPolygons(); V3f blankVector; if( space() == MSpace::kObject ) { const float* rawNormals = fnMesh.getRawNormals(0); MIntArray normalIds; for( int i=0; i<numPolygons; i++ ) { fnMesh.getFaceNormalIds( i, normalIds ); for( unsigned j=0; j < normalIds.length(); ++j ) { const float* normalIt = rawNormals + 3 * normalIds[j]; normals.push_back( blankVector ); V3f& nn = normals.back(); nn.x = *normalIt++; nn.y = *normalIt++; nn.z = *normalIt; } } } else { MFloatVectorArray faceNormals; for( int i=0; i<numPolygons; i++ ) { fnMesh.getFaceVertexNormals( i, faceNormals, space() ); for( unsigned j=0; j<faceNormals.length(); j++ ) { MFloatVector& n = faceNormals[j]; normals.push_back( blankVector ); V3f& nn = normals.back(); nn.x = n.x; nn.y = n.y; nn.z = n.z; } } } return PrimitiveVariable( PrimitiveVariable::FaceVarying, normalsData ); }
MeshPrimitive::MeshPrimitive( ConstIntVectorDataPtr verticesPerFace, ConstIntVectorDataPtr vertexIds, const std::string &interpolation, V3fVectorDataPtr p ) { setTopology( verticesPerFace, vertexIds, interpolation ); if( p ) { V3fVectorDataPtr pData = p->copy(); pData->setInterpretation( GeometricData::Point ); variables.insert( PrimitiveVariableMap::value_type("P", PrimitiveVariable(PrimitiveVariable::Vertex, pData)) ); } }
NURBSPrimitive::NURBSPrimitive( int uOrder, ConstFloatVectorDataPtr uKnot, float uMin, float uMax, int vOrder, ConstFloatVectorDataPtr vKnot, float vMin, float vMax, ConstV3fVectorDataPtr p ) { setTopology( uOrder, uKnot, uMin, uMax, vOrder, vKnot, vMin, vMax ); if( p ) { V3fVectorDataPtr pData = p->copy(); pData->setInterpretation( GeometricData::Point ); variables.insert( PrimitiveVariableMap::value_type( "P", PrimitiveVariable( PrimitiveVariable::Vertex, pData ) ) ); } }
CurvesPrimitive::CurvesPrimitive( ConstIntVectorDataPtr vertsPerCurve, const CubicBasisf &basis, bool periodic, ConstV3fVectorDataPtr p ) : m_basis( CubicBasisf::linear() ) { setTopology( vertsPerCurve, basis, periodic ); if( p ) { V3fVectorDataPtr pData = p->copy(); pData->setInterpretation( GeometricData::Point ); variables["P"] = PrimitiveVariable( PrimitiveVariable::Vertex, pData ); } }
IECore::ConstObjectPtr Grid::computeObject( const SceneNode::ScenePath &path, const Gaffer::Context *context, const ScenePlug *parent ) const { if( path.size() == 2 ) { IntVectorDataPtr vertsPerCurveData = new IntVectorData; vector<int> &vertsPerCurve = vertsPerCurveData->writable(); V3fVectorDataPtr pData = new V3fVectorData; pData->setInterpretation( GeometricData::Point ); vector<V3f> &p = pData->writable(); bool periodic = false; Color3f cs( 1 ); const V2f halfDimensions = dimensionsPlug()->getValue() / 2.0f; if( path.back() == g_gridLinesName ) { const float spacing = spacingPlug()->getValue(); const V2i n = V2f( halfDimensions / spacing ) - V2f( 0.01 ); for( int d = 0; d < 2; ++d ) { const int d0 = d; const int d1 = d == 0 ? 1 : 0; for( int i = -n[d]; i <= n[d]; ++i ) { if( i == 0 ) { continue; } vertsPerCurve.push_back( 2 ); V3f e( 0 ); e[d0] = i * spacing; e[d1] = -halfDimensions[d1]; p.push_back( e ); e[d1] = halfDimensions[d1]; p.push_back( e ); } } cs = gridColorPlug()->getValue(); } else if( path.back() == g_centerLinesName ) { vertsPerCurve.push_back( 2 ); p.push_back( V3f( halfDimensions.x, 0, 0 ) ); p.push_back( V3f( -halfDimensions.x, 0, 0 ) ); vertsPerCurve.push_back( 2 ); p.push_back( V3f( 0, halfDimensions.y, 0 ) ); p.push_back( V3f( 0, -halfDimensions.y, 0 ) ); cs = centerColorPlug()->getValue(); } else if( path.back() == g_borderLinesName ) { vertsPerCurve.push_back( 4 ); p.push_back( V3f( -halfDimensions.x, -halfDimensions.y, 0 ) ); p.push_back( V3f( halfDimensions.x, -halfDimensions.y, 0 ) ); p.push_back( V3f( halfDimensions.x, halfDimensions.y, 0 ) ); p.push_back( V3f( -halfDimensions.x, halfDimensions.y, 0 ) ); periodic = true; cs = borderColorPlug()->getValue(); } CurvesPrimitivePtr result = new CurvesPrimitive( vertsPerCurveData, CubicBasisf::linear(), periodic, pData ); result->variables["Cs"] = PrimitiveVariable( PrimitiveVariable::Constant, new Color3fData( cs ) ); return result; } return outPlug()->objectPlug()->defaultValue(); }
ObjectPtr SLOReader::doOperation( const CompoundObject * operands ) { tbb::mutex::scoped_lock lock( g_mutex ); if( Slo_SetShader( (char *)fileName().c_str() ) ) { throw Exception( boost::str( boost::format( "Unable to set shader to \"%s\"" ) % fileName() ) ); } string name = Slo_GetName(); string type = Slo_TypetoStr( Slo_GetType() ); ShaderPtr result = new Shader( name, type ); CompoundDataPtr typeHints = new CompoundData; result->blindData()->writable().insert( pair<string, DataPtr>( "ri:parameterTypeHints", typeHints ) ); // we lose the ordering of parameter names when we put them in result->parameters(), // so we stick the correct order in the blind data as a workaround for anyone interested // in the true ordering. StringVectorDataPtr orderedParameterNames = new StringVectorData; result->blindData()->writable().insert( pair<string, DataPtr>( "ri:orderedParameterNames", orderedParameterNames ) ); // we don't have a way of communicating which parameters are outputs in the Shader::parametersData(), // so we work around that using the blind data too. StringVectorDataPtr outputParameterNames = new StringVectorData; result->blindData()->writable().insert( pair<string, DataPtr>( "ri:outputParameterNames", outputParameterNames ) ); int numArgs = Slo_GetNArgs(); for( int i=1; i<=numArgs; i++ ) { DataPtr data = 0; SLO_VISSYMDEF *arg = Slo_GetArgById( i ); // find geometric interpretation, if this is relevant: GeometricData::Interpretation interpretation; switch( arg->svd_type ) { case SLO_TYPE_POINT : interpretation = GeometricData::Point; break; case SLO_TYPE_VECTOR : interpretation = GeometricData::Vector; break; case SLO_TYPE_NORMAL : interpretation = GeometricData::Normal; break; default: interpretation = GeometricData::None; break; } switch( arg->svd_type ) { case SLO_TYPE_POINT : case SLO_TYPE_VECTOR : case SLO_TYPE_NORMAL : { if( arg->svd_arraylen==0 ) { const SLO_POINT *p = arg->svd_default.pointval; if( p ) { data = new V3fData( V3f( p->xval, p->yval, p->zval ), interpretation ); } else { // 0 length and null value signifies a variable length array V3fVectorDataPtr vData = new V3fVectorData; vData->setInterpretation( interpretation ); data = vData; } } else { V3fVectorDataPtr vData = new V3fVectorData; for( int j=0; j<arg->svd_arraylen; j++ ) { SLO_VISSYMDEF *a = Slo_GetArrayArgElement( arg, j ); const SLO_POINT *p = a->svd_default.pointval; vData->writable().push_back( V3f( p->xval, p->yval, p->zval ) ); } vData->setInterpretation( interpretation ); data = vData; } typeHints->writable().insert( pair<string, DataPtr>( arg->svd_name, new StringData( Slo_TypetoStr( arg->svd_type ) ) ) ); break; } case SLO_TYPE_COLOR : { if( arg->svd_arraylen==0 ) { const SLO_POINT *p = arg->svd_default.pointval; if( p ) { data = new Color3fData( Color3f( p->xval, p->yval, p->zval ) ); } else { // 0 length and null value signifies a variable length array data = new Color3fVectorData(); } } else { Color3fVectorDataPtr vData = new Color3fVectorData(); data = vData; for( int j=0; j<arg->svd_arraylen; j++ ) { SLO_VISSYMDEF *a = Slo_GetArrayArgElement( arg, j ); const SLO_POINT *p = a->svd_default.pointval; vData->writable().push_back( Color3f( p->xval, p->yval, p->zval ) ); } } } break; case SLO_TYPE_SCALAR : { if( arg->svd_arraylen==0 ) { const float *value = arg->svd_default.scalarval; if( value ) { data = new FloatData( *value ); } else { // 0 length and null value signifies a variable length array data = new FloatVectorData(); } } else { FloatVectorDataPtr vData = new FloatVectorData(); data = vData; for( int j=0; j<arg->svd_arraylen; j++ ) { SLO_VISSYMDEF *a = Slo_GetArrayArgElement( arg, j ); vData->writable().push_back( *(a->svd_default.scalarval) ); } if( arg->svd_arraylen==3 ) { // allow V3fData and V3fVectorData to be mapped to float[3] parameters. typeHints->writable().insert( pair<string, DataPtr>( arg->svd_name, new StringData( "float[3]" ) ) ); } } } break; case SLO_TYPE_STRING : { if( arg->svd_arraylen==0 ) { const char *defaultValue = arg->svd_default.stringval; if( defaultValue ) { data = new StringData( defaultValue ); } else { // 0 length and null value signifies a variable length array data = new StringVectorData(); } } else { StringVectorDataPtr vData = new StringVectorData(); data = vData; for( int j=0; j<arg->svd_arraylen; j++ ) { SLO_VISSYMDEF *a = Slo_GetArrayArgElement( arg, j ); // sometimes the default value for an element of a string array can be a null pointer. // i'm not sure what the meaning of this is. the 3delight shaderinfo utility reports such values // as "(null)", so that's what we do too. const char *defaultValue = a->svd_default.stringval; vData->writable().push_back( defaultValue ? defaultValue : "(null)" ); } } } break; case SLO_TYPE_MATRIX : { if( arg->svd_arraylen==0 ) { const float *m = arg->svd_default.matrixval; if( m ) { M44f mm( m[0], m[1], m[2], m[3], m[4], m[5], m[6], m[7], m[8], m[9], m[10], m[11], m[12], m[13], m[14], m[15] ); data = new M44fData( mm ); } else { // 0 length and null value signifies a variable length array data = new M44fVectorData(); } } else { M44fVectorDataPtr vData = new M44fVectorData(); data = vData; for( int j=0; j<arg->svd_arraylen; j++ ) { SLO_VISSYMDEF *a = Slo_GetArrayArgElement( arg, j ); const float *m = a->svd_default.matrixval; M44f mm( m[0], m[1], m[2], m[3], m[4], m[5], m[6], m[7], m[8], m[9], m[10], m[11], m[12], m[13], m[14], m[15] ); vData->writable().push_back( mm ); } } } break; case SLO_TYPE_SHADER : { if( arg->svd_arraylen==0 ) { if( !arg->svd_valisvalid ) { // variable length array data = new StringVectorData(); } else { data = new StringData(); } } else { StringVectorDataPtr sData = new StringVectorData(); data = sData; sData->writable().resize( arg->svd_arraylen ); } typeHints->writable().insert( pair<string, DataPtr>( arg->svd_name, new StringData( Slo_TypetoStr( arg->svd_type ) ) ) ); } break; default : msg( Msg::Warning, "SLOReader::read", format( "Parameter \"%s\" has unsupported type." ) % arg->svd_name ); } if( data ) { orderedParameterNames->writable().push_back( arg->svd_name ); result->parameters().insert( CompoundDataMap::value_type( arg->svd_name, data ) ); if( arg->svd_storage == SLO_STOR_OUTPUTPARAMETER ) { outputParameterNames->writable().push_back( arg->svd_name ); } } } // shader annotations CompoundDataPtr annotations = new CompoundData; result->blindData()->writable().insert( pair<string, DataPtr>( "ri:annotations", annotations ) ); #ifndef PRMANEXPORT for( int i=1, n=Slo_GetNAnnotations(); i <= n; i++ ) { const char *key = Slo_GetAnnotationKeyById( i ); annotations->writable()[key] = new StringData( Slo_GetAnnotationByKey( key ) ); } #endif Slo_EndShader(); return result; }