void getObjectTimeSpan(IObject obj, chrono_t& first, chrono_t& last, bool doChildren) { if ( Alembic::AbcGeom::IPolyMesh::matches(obj.getHeader()) ) { IPolyMesh iPoly(obj, Alembic::Abc::kWrapExisting); getPolyMeshTimeSpan(iPoly, first, last); } else if ( Alembic::AbcGeom::ISubD::matches(obj.getHeader()) ) { ISubD iSub(obj, Alembic::Abc::kWrapExisting); getSubDTimeSpan(iSub, first, last); } else if ( Alembic::AbcGeom::IXform::matches(obj.getHeader()) ) { IXform iXf(obj, Alembic::Abc::kWrapExisting); getXformTimeSpan(iXf, first, last, false); } else if ( Alembic::AbcGeom::ICamera::matches(obj.getHeader()) ) { ICamera iCam(obj, Alembic::Abc::kWrapExisting); getCameraTimeSpan(iCam, first, last); } if (doChildren) { // do this object's children too for (unsigned i=0; i < obj.getNumChildren(); ++i) { IObject child( obj.getChild( i )); getObjectTimeSpan(child, first, last, doChildren); } } }
void getXformTimeSpan(IXform iXf, chrono_t& first, chrono_t& last, bool inherits) { IXformSchema xf = iXf.getSchema(); TimeSamplingPtr ts = xf.getTimeSampling(); first = std::min(first, ts->getSampleTime(0) ); if (xf.isConstant()) { last = first; } else { last = std::max(last, ts->getSampleTime(xf.getNumSamples()-1) ); } if (inherits && xf.getInheritsXforms()) { IObject parent = iXf.getParent(); // Once the Archive's Top Object is reached, IObject::getParent() will // return an invalid IObject, and that will evaluate to False. while ( parent ) { if ( Alembic::AbcGeom::IXform::matches(parent.getHeader()) ) { IXform x( parent, kWrapExisting ); getXformTimeSpan(x, first, last, inherits); } } } }
void accumXform( Imath::M44d &xf, IObject obj, chrono_t curTime, bool interpolate) { if ( IXform::matches( obj.getHeader() ) ) { Imath::M44d mtx; IXform x( obj, kWrapExisting ); XformSample xs; x.getSchema().get( xs ); if (!x.getSchema().isConstant()) { TimeSamplingPtr timeSampler = x.getSchema().getTimeSampling(); if (interpolate) { //std::pair<index_t, chrono_t> lSamp;// = timeSampler->getFloorIndex(curTime, x.getSchema().getNumSamples()); Alembic::AbcCoreAbstract::index_t floorIdx, ceilIdx; double amt = getWeightAndIndex(curTime, timeSampler, x.getSchema().getNumSamples(), floorIdx, ceilIdx); if (amt != 0 && floorIdx != ceilIdx) { const ISampleSelector iss_start(floorIdx);//lSamp.first); Imath::M44d mtx_start = x.getSchema().getValue(iss_start).getMatrix(); //std::pair<index_t, chrono_t> rSamp = timeSampler->getCeilIndex(curTime, x.getSchema().getNumSamples()); const ISampleSelector iss_end(ceilIdx);//rSamp.first); Imath::M44d mtx_end = x.getSchema().getValue(iss_end).getMatrix(); Imath::V3d s_l,s_r,h_l,h_r,t_l,t_r; Imath::Quatd quat_l,quat_r; DecomposeXForm(mtx_start, s_l, h_l, quat_l, t_l); DecomposeXForm(mtx_end, s_r, h_r, quat_r, t_r); if ((quat_l ^ quat_r) < 0) { quat_r = -quat_r; } mtx = RecomposeXForm(Imath::lerp(s_l, s_r, amt), Imath::lerp(h_l, h_r, amt), Imath::slerp(quat_l, quat_r, amt), Imath::lerp(t_l, t_r, amt)); } else { const ISampleSelector iss(curTime); xs = x.getSchema().getValue(iss); mtx = xs.getMatrix(); } } else { // no interpolation, get nearest sample const ISampleSelector iss(curTime); xs = x.getSchema().getValue(iss); mtx = xs.getMatrix(); } } else { mtx = xs.getMatrix(); } xf *= mtx; } }