Esempio n. 1
0
bool
GusdUSD_StageProxy::MultiAccessor::_GetPrims(
    const UT_Array<SdfPath>& primPaths,
    UT_Array<UsdPrim>& prims,
    GusdUT_ErrorContext* err)
{
    if(!_Load(primPaths))
        return false;

    prims.setSize(primPaths.size());

    std::atomic_bool workerInterrupt(false);
    UTparallelFor(UT_BlockedRange<size_t>(0, primPaths.size()),
                  _GetPrimsFn(*this, primPaths, prims, err, workerInterrupt));
    return !UTgetInterrupt()->opInterrupt() && !workerInterrupt;
}
Esempio n. 2
0
void RainData::shiftPositions(  GU_Detail* gdp, const GA_Range &range )
    {
        UTparallelFor(GA_SplittableRange(range), ParallelShift( this, gdp ), 2, 1);
    }
Esempio n. 3
0
bool
GusdUSD_StageProxy::MultiAccessor::_Load(const UT_Array<SdfPath>& paths)
{
    if(paths.isEmpty())
        return true;

    UT_ASSERT_P(paths.size() == _size);

    typedef tbb::concurrent_unordered_set<
        SdfPath,SdfPath::Hash> ConcurrentPathSet;

    struct _ComputeUnloadedPrimsFn
    {
        _ComputeUnloadedPrimsFn(const UT_Array<SdfPath>& paths,
                                const UT_Array<exint>& indexMap,
                                const UT_Array<_PrimLoader*>& loaders,
                                UT_Array<ConcurrentPathSet*>& pathSets)
            : _paths(paths), _indexMap(indexMap),
              _loaders(loaders), _pathSets(pathSets) {}

        void    operator()(const UT_BlockedRange<size_t>& r) const
                {
                    auto* boss = UTgetInterrupt();
                    char bcnt = 0;

                    for(size_t i = r.begin(); i < r.end(); ++i) {
                        if(BOOST_UNLIKELY(!++bcnt && boss->opInterrupt()))
                            return;
                        
                        exint idx = _indexMap(i);
                        if(idx >= 0) {
                            if(auto* loader = _loaders(idx)) {
                                const SdfPath& path = _paths(i);
                                if(!path.IsEmpty() && !loader->IsLoaded(path))
                                    _pathSets(idx)->insert(path);
                            }
                        }
                    }
                }

    private:
        const UT_Array<SdfPath>&        _paths;
        const UT_Array<exint>&          _indexMap;
        const UT_Array<_PrimLoader*>&   _loaders;
        UT_Array<ConcurrentPathSet*>    _pathSets;
    };

    /* Compute sets of unloaded prims.
       This constitutes the bulk of binding time, so do this parallel.*/
    UT_Array<_PrimLoader*> loaders(_numAccessors, _numAccessors);
    UT_Array<ConcurrentPathSet*> pathSets(_numAccessors, _numAccessors);
    for(exint i = 0; i < _numAccessors; ++i) {
        if ( _accessors[i] ) {
            auto* loader = _accessors[i].GetProxy()->_primLoader;
            if(loader) {
                loaders(i) = loader;
                pathSets(i) = new ConcurrentPathSet;
            }
        }
    }

    UTparallelFor(UT_BlockedRange<size_t>(0, _size),
                  _ComputeUnloadedPrimsFn(paths, _indexMap, loaders, pathSets));

    if(UTgetInterrupt()->opInterrupt())
        return false;

    /* Load the actual prims.
       This could be done in parallel, but is probably not worth it since
       there's only work to perform the first time a prim load is requested.*/
    for(exint i = 0; i < _numAccessors; ++i) {
        if(auto* pathSet = pathSets(i)) {
            SdfPathSet pathsToLoad(pathSet->begin(), pathSet->end());
            _accessors[i]._Load(pathsToLoad);
            
            delete pathSet;
        }
    }

    return true;
}