ObjectPtr FromHoudiniGroupConverter::doDetailConversion( const GU_Detail *geo, const CompoundObject *operands ) const { GU_DetailHandle handle; handle.allocateAndSet( (GU_Detail*)geo, false ); FromHoudiniGeometryConverterPtr converter = FromHoudiniGeometryConverter::create( handle ); if ( !converter || converter->isInstanceOf( FromHoudiniGroupConverter::staticTypeId() ) ) { /// \todo: if we're in PrimitiveGroup mode, but names exist, we return 0 when we should be returning a Group return 0; } // transfer the common parameter values CompoundParameter *parameters = converter->parameters(); const CompoundParameter::ParameterMap ¶meterMap = parameters->parameters(); const CompoundObject::ObjectMap &values = operands->members(); for ( CompoundObject::ObjectMap::const_iterator it = values.begin(); it != values.end(); ++it ) { CompoundParameter::ParameterMap::const_iterator pIt = parameterMap.find( it->first ); if ( pIt != parameterMap.end() && pIt->second->defaultValue()->typeId() == it->second->typeId() ) { parameters->setParameterValue( it->first, it->second ); } } return converter->convert(); }
void SOP_ParameterisedHolder::setInputParameterValues( float now ) { for ( unsigned int i=0; i < m_inputParameters.size(); i++ ) { useInputSource( i, m_dirty, false ); IECore::ParameterPtr inputParameter = m_inputParameters[i]; GU_DetailHandle inputHandle = inputGeoHandle( i ); GU_DetailHandleAutoReadLock readHandle( inputHandle ); const GU_Detail *inputGdp = readHandle.getGdp(); if ( !inputGdp ) { continue; } const GA_ROAttributeRef attrRef = inputGdp->findAttribute( GA_ATTRIB_DETAIL, GA_SCOPE_PRIVATE, "IECoreHoudiniNodePassData" ); if ( attrRef.isValid() ) { // looks like data passed from another ParameterisedHolder const GA_Attribute *attr = attrRef.getAttribute(); const GA_AIFBlindData *blindData = attr->getAIFBlindData(); const NodePassData passData = blindData->getValue<NodePassData>( attr, 0 ); SOP_ParameterisedHolder *sop = dynamic_cast<SOP_ParameterisedHolder*>( const_cast<OP_Node*>( passData.nodePtr() ) ); IECore::ConstObjectPtr result = 0; if ( passData.type() == IECoreHoudini::NodePassData::CORTEX_OPHOLDER ) { IECore::OpPtr op = IECore::runTimeCast<IECore::Op>( sop->getParameterised() ); result = op->resultParameter()->getValue(); } else if ( passData.type() == IECoreHoudini::NodePassData::CORTEX_PROCEDURALHOLDER ) { IECore::ParameterisedProcedural *procedural = IECore::runTimeCast<IECore::ParameterisedProcedural>( sop->getParameterised() ); IECore::CapturingRendererPtr renderer = new IECore::CapturingRenderer(); // We are acquiring and releasing the GIL here to ensure that it is released when we render. This has // to be done because a procedural might jump between c++ and python a few times (i.e. if it spawns // subprocedurals that are implemented in python). In a normal call to cookMySop, this wouldn't be an // issue, but if cookMySop was called from HOM, hou.Node.cook appears to be holding onto the GIL. IECorePython::ScopedGILLock gilLock; { IECorePython::ScopedGILRelease gilRelease; { IECore::WorldBlock worldBlock( renderer ); procedural->render( renderer ); } } result = IECore::runTimeCast<const IECore::Object>( renderer->world() ); } else { continue; } try { inputParameter->setValidatedValue( IECore::constPointerCast<IECore::Object>( result ) ); } catch ( const IECore::Exception &e ) { addError( SOP_MESSAGE, e.what() ); } } else { // looks like a regular Houdini detail IECore::ObjectParameterPtr objectParameter = IECore::runTimeCast<IECore::ObjectParameter>( inputParameter ); if ( !objectParameter ) { continue; } FromHoudiniGeometryConverterPtr converter = FromHoudiniGeometryConverter::create( inputHandle, objectParameter->validTypes() ); if ( !converter ) { continue; } // set converter parameters from the node values const CompoundParameter::ParameterVector &converterParameters = converter->parameters()->orderedParameters(); for ( CompoundParameter::ParameterVector::const_iterator it=converterParameters.begin(); it != converterParameters.end(); ++it ) { updateParameter( *it, now, "parm_" + inputParameter->name() + "_" ); } try { IECore::ObjectPtr converted = converter->convert(); if ( converted ) { inputParameter->setValidatedValue( converted ); } } catch ( const IECore::Exception &e ) { addError( SOP_MESSAGE, e.what() ); } catch ( std::runtime_error &e ) { addError( SOP_MESSAGE, e.what() ); } } } }