osgDB Wrapper Associates Revision Tagging

This commit is contained in:
Julien Valentin
2016-06-14 11:43:45 +01:00
committed by Robert Osfield
parent dcac0c1611
commit 2ac8379cfc
6 changed files with 186 additions and 65 deletions

View File

@@ -509,12 +509,12 @@ bool ClassInterface::getSupportedProperties(const osg::Object* object, PropertyM
if (searchAssociates)
{
const osgDB::StringList& associates = ow->getAssociates();
for(osgDB::StringList::const_iterator aitr = associates.begin();
const ObjectWrapper::RevisionAssociateList& associates = ow->getAssociates();
for(ObjectWrapper::RevisionAssociateList::const_iterator aitr = associates.begin();
aitr != associates.end();
++aitr)
{
osgDB::ObjectWrapper* associate_wrapper = osgDB::Registry::instance()->getObjectWrapperManager()->findWrapper(*aitr);
osgDB::ObjectWrapper* associate_wrapper = osgDB::Registry::instance()->getObjectWrapperManager()->findWrapper(aitr->_name);
if (associate_wrapper)
{
const osgDB::ObjectWrapper::SerializerList& associate_serializers = associate_wrapper->getSerializerList();
@@ -560,12 +560,12 @@ bool ClassInterface::isObjectOfType(const osg::Object* object, const std::string
return false;
}
const osgDB::StringList& associates = ow->getAssociates();
for(osgDB::StringList::const_iterator aitr = associates.begin();
const ObjectWrapper::RevisionAssociateList& associates = ow->getAssociates();
for(ObjectWrapper::RevisionAssociateList::const_iterator aitr = associates.begin();
aitr != associates.end();
++aitr)
{
if ((*aitr)==compoundClassName) return true;
if ((aitr->_name)==compoundClassName) return true;
}
return false;
}
@@ -584,12 +584,12 @@ bool ClassInterface::run(void* objectPtr, const std::string& compoundClassName,
if (mo->run(objectPtr, inputParameters, outputParameters)) return true;
}
const osgDB::StringList& associates = ow->getAssociates();
for(osgDB::StringList::const_iterator aitr = associates.begin();
const ObjectWrapper::RevisionAssociateList& associates = ow->getAssociates();
for(ObjectWrapper::RevisionAssociateList::const_iterator aitr = associates.begin();
aitr != associates.end();
++aitr)
{
osgDB::ObjectWrapper* aow = osgDB::Registry::instance()->getObjectWrapperManager()->findWrapper(*aitr);
osgDB::ObjectWrapper* aow = osgDB::Registry::instance()->getObjectWrapperManager()->findWrapper(aitr->_name);
if (aow)
{
const ObjectWrapper::MethodObjectMap& methodObjectMap = aow->getMethodObjectMap();
@@ -620,12 +620,12 @@ bool ClassInterface::hasMethod(const std::string& compoundClassName, const std::
ObjectWrapper::MethodObjectMap::const_iterator oitr = ow_methodObjectMap.find(methodName);
if (oitr!=ow_methodObjectMap.end()) return true;
const osgDB::StringList& associates = ow->getAssociates();
for(osgDB::StringList::const_iterator aitr = associates.begin();
const ObjectWrapper::RevisionAssociateList& associates = ow->getAssociates();
for(ObjectWrapper::RevisionAssociateList::const_iterator aitr = associates.begin();
aitr != associates.end();
++aitr)
{
osgDB::ObjectWrapper* aow = osgDB::Registry::instance()->getObjectWrapperManager()->findWrapper(*aitr);
osgDB::ObjectWrapper* aow = osgDB::Registry::instance()->getObjectWrapperManager()->findWrapper(aitr->_name);
if (aow)
{
const ObjectWrapper::MethodObjectMap& methodObjectMap = aow->getMethodObjectMap();

View File

@@ -905,26 +905,36 @@ osg::ref_ptr<osg::Object> InputStream::readObjectFields( const std::string& clas
<< className << std::endl;
return NULL;
}
int inputVersion = getFileVersion(wrapper->getDomain());
osg::ref_ptr<osg::Object> obj = existingObj ? existingObj : wrapper->createInstance();
_identifierMap[id] = obj;
if ( obj.valid() )
{
const StringList& associates = wrapper->getAssociates();
for ( StringList::const_iterator itr=associates.begin(); itr!=associates.end(); ++itr )
const ObjectWrapper::RevisionAssociateList& associates = wrapper->getAssociates();
for ( ObjectWrapper::RevisionAssociateList::const_iterator itr=associates.begin(); itr!=associates.end(); ++itr )
{
ObjectWrapper* assocWrapper = Registry::instance()->getObjectWrapperManager()->findWrapper(*itr);
if ( !assocWrapper )
if ( itr->_firstVersion <= inputVersion &&
inputVersion <= itr->_lastVersion)
{
OSG_WARN << "InputStream::readObject(): Unsupported associated class "
<< *itr << std::endl;
continue;
}
_fields.push_back( assocWrapper->getName() );
assocWrapper->read( *this, *obj );
if ( getException() ) return NULL;
ObjectWrapper* assocWrapper = Registry::instance()->getObjectWrapperManager()->findWrapper(itr->_name);
if ( !assocWrapper )
{
OSG_WARN << "InputStream::readObject(): Unsupported associated class "
<< itr->_name << std::endl;
continue;
}
_fields.push_back( assocWrapper->getName() );
assocWrapper->read( *this, *obj );
if ( getException() ) return NULL;
_fields.pop_back();
_fields.pop_back();
}
else
{
/* OSG_INFO << "InputStream::readObject():"<<className<<" Ignoring associated class due to version mismatch"
<< itr->_name<<"["<<itr->_firstVersion <<","<<itr->_lastVersion <<"]for version "<<inputVersion<< std::endl;*/
}
}
}
return obj;

View File

@@ -80,6 +80,24 @@ void osgDB::split( const std::string& src, StringList& list, char separator )
}
}
void ObjectWrapper::splitAssociates( const std::string& src, ObjectWrapper::RevisionAssociateList& list, char separator )
{
std::string::size_type start = src.find_first_not_of(separator);
while ( start!=std::string::npos )
{
std::string::size_type end = src.find_first_of(separator, start);
if ( end!=std::string::npos )
{
list.push_back( ObjectWrapperAssociate(std::string(src, start, end-start)) );
start = src.find_first_not_of(separator, end);
}
else
{
list.push_back( ObjectWrapperAssociate(std::string(src, start, src.size()-start)) );
start = end;
}
}
}
////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// ObjectWrapper
@@ -87,19 +105,72 @@ void osgDB::split( const std::string& src, StringList& list, char separator )
ObjectWrapper::ObjectWrapper( CreateInstanceFunc* createInstanceFunc, const std::string& name,
const std::string& associates )
: osg::Referenced(),
_createInstanceFunc(createInstanceFunc), _name(name), _version(0)
_createInstanceFunc(createInstanceFunc), _name(name), _version(0),_isAssociatesRevisionsInheritanceDone(false)
{
split( associates, _associates );
splitAssociates( associates, _associates );
}
ObjectWrapper::ObjectWrapper( CreateInstanceFunc* createInstanceFunc, const std::string& domain, const std::string& name,
const std::string& associates )
: osg::Referenced(),
_createInstanceFunc(createInstanceFunc), _domain(domain), _name(name), _version(0)
_createInstanceFunc(createInstanceFunc), _domain(domain), _name(name), _version(0),_isAssociatesRevisionsInheritanceDone(false)
{
split( associates, _associates );
splitAssociates( associates, _associates );
}
void ObjectWrapper::setupAssociatesRevisionsInheritanceIfRequired()
{
if(!_isAssociatesRevisionsInheritanceDone)
{
///for each associate wrapper
for ( ObjectWrapper::RevisionAssociateList::const_iterator itr=_associates.begin(); itr!=_associates.end(); ++itr )
{
ObjectWrapper* assocWrapper = Registry::instance()->getObjectWrapperManager()->findWrapper(itr->_name);
if ( assocWrapper && assocWrapper != this )
{
///crawl association revisions in associates
for ( ObjectWrapper::RevisionAssociateList::const_iterator itr2=assocWrapper->getAssociates().begin(); itr2!=assocWrapper->getAssociates().end(); ++itr2 )
{
for ( ObjectWrapper::RevisionAssociateList::iterator itr3=_associates.begin(); itr3!=_associates.end(); ++itr3 )
{
///they share associates
if(itr3->_name==itr2->_name)
{
itr3->_firstVersion=itr3->_firstVersion>itr2->_firstVersion? itr3->_firstVersion:itr2->_firstVersion;
itr3->_lastVersion=itr3->_lastVersion<itr2->_lastVersion? itr3->_lastVersion:itr2->_lastVersion;
}
}
}
}
}
_isAssociatesRevisionsInheritanceDone=true;
}
}
void ObjectWrapper::markAssociateAsAdded(const std::string& name)
{
for ( ObjectWrapper::RevisionAssociateList:: iterator itr=_associates.begin(); itr!=_associates.end(); ++itr )
{
if(itr->_name==name)
{
itr->_firstVersion=_version;
return;
}
}
OSG_NOTIFY(osg::WARN)<<"ObjectWrapper::associateAddedAtVersion: Associate class "<<name<<" not defined for wrapper "<<_name<<std::endl;
}
void ObjectWrapper::markAssociateAsRemoved(const std::string& name)
{
for ( ObjectWrapper::RevisionAssociateList:: iterator itr=_associates.begin(); itr!=_associates.end(); ++itr )
{
if(itr->_name==name)
{
itr->_lastVersion = _version-1;
return;
}
}
OSG_NOTIFY(osg::WARN)<<"ObjectWrapper::associateRemovedAtVersion: Associate class "<<name<<" not defined for wrapper "<<_name<<std::endl;
}
void ObjectWrapper::addSerializer( BaseSerializer* s, BaseSerializer::Type t )
{
s->_firstVersion = _version;
@@ -127,9 +198,9 @@ BaseSerializer* ObjectWrapper::getSerializer( const std::string& name )
return itr->get();
}
for ( StringList::const_iterator itr=_associates.begin(); itr!=_associates.end(); ++itr )
for ( RevisionAssociateList::const_iterator itr=_associates.begin(); itr!=_associates.end(); ++itr )
{
const std::string& assocName = *itr;
const std::string& assocName = itr->_name;
ObjectWrapper* assocWrapper = Registry::instance()->getObjectWrapperManager()->findWrapper(assocName);
if ( !assocWrapper )
{
@@ -163,9 +234,9 @@ BaseSerializer* ObjectWrapper::getSerializer( const std::string& name, BaseSeria
}
}
for ( StringList::const_iterator itr=_associates.begin(); itr!=_associates.end(); ++itr )
for ( RevisionAssociateList::const_iterator itr=_associates.begin(); itr!=_associates.end(); ++itr )
{
const std::string& assocName = *itr;
const std::string& assocName = itr->_name;
ObjectWrapper* assocWrapper = Registry::instance()->getObjectWrapperManager()->findWrapper(assocName);
if ( !assocWrapper )
{
@@ -681,17 +752,22 @@ ObjectWrapper* ObjectWrapperManager::findWrapper( const std::string& name )
{
std::string libName = std::string( name, 0, posDoubleColon );
ObjectWrapper* found=0;
std::string nodeKitLib = osgDB::Registry::instance()->createLibraryNameForNodeKit(libName);
if ( osgDB::Registry::instance()->loadLibrary(nodeKitLib)==osgDB::Registry::LOADED )
return findWrapper(name);
found= findWrapper(name);
std::string pluginLib = osgDB::Registry::instance()->createLibraryNameForExtension(std::string("serializers_")+libName);
if ( osgDB::Registry::instance()->loadLibrary(pluginLib)==osgDB::Registry::LOADED )
return findWrapper(name);
found= findWrapper(name);
pluginLib = osgDB::Registry::instance()->createLibraryNameForExtension(libName);
if ( osgDB::Registry::instance()->loadLibrary(pluginLib)==osgDB::Registry::LOADED )
return findWrapper(name);
found= findWrapper(name);
if (found) found->setupAssociatesRevisionsInheritanceIfRequired();
return found;
}
return NULL;
}

View File

@@ -645,44 +645,54 @@ void OutputStream::writeObjectFields( const osg::Object* obj, const std::string&
<< name << std::endl;
return;
}
int outputVersion = getFileVersion(wrapper->getDomain());
const StringList& associates = wrapper->getAssociates();
for ( StringList::const_iterator itr=associates.begin(); itr!=associates.end(); ++itr )
const ObjectWrapper::RevisionAssociateList& associates = wrapper->getAssociates();
for ( ObjectWrapper::RevisionAssociateList::const_iterator itr=associates.begin(); itr!=associates.end(); ++itr )
{
const std::string& assocName = *itr;
ObjectWrapper* assocWrapper = Registry::instance()->getObjectWrapperManager()->findWrapper(assocName);
if ( !assocWrapper )
if ( itr->_firstVersion <= outputVersion &&
outputVersion <= itr->_lastVersion)
{
OSG_WARN << "OutputStream::writeObject(): Unsupported associated class "
<< assocName << std::endl;
continue;
}
else if ( _useSchemaData )
{
if ( _inbuiltSchemaMap.find(assocName)==_inbuiltSchemaMap.end() )
const std::string& assocName = itr->_name;
ObjectWrapper* assocWrapper = Registry::instance()->getObjectWrapperManager()->findWrapper(assocName);
if ( !assocWrapper )
{
StringList properties;
ObjectWrapper::TypeList types;
assocWrapper->writeSchema( properties, types );
unsigned int size = osg::minimum( properties.size(), types.size() );
if ( size>0 )
OSG_WARN << "OutputStream::writeObject(): Unsupported associated class "
<< assocName << std::endl;
continue;
}
else if ( _useSchemaData )
{
if ( _inbuiltSchemaMap.find(assocName)==_inbuiltSchemaMap.end() )
{
std::stringstream propertiesStream;
for ( unsigned int i=0; i<size; ++i )
StringList properties;
ObjectWrapper::TypeList types;
assocWrapper->writeSchema( properties, types );
unsigned int size = osg::minimum( properties.size(), types.size() );
if ( size>0 )
{
propertiesStream << properties[i] << ":" << types[i] << " ";
std::stringstream propertiesStream;
for ( unsigned int i=0; i<size; ++i )
{
propertiesStream << properties[i] << ":" << types[i] << " ";
}
_inbuiltSchemaMap[assocName] = propertiesStream.str();
}
_inbuiltSchemaMap[assocName] = propertiesStream.str();
}
}
_fields.push_back( assocWrapper->getName() );
assocWrapper->write( *this, *obj );
if ( getException() ) return;
_fields.pop_back();
}
else
{
/*OSG_INFO << "OutputStream::writeObject():"<<name<<" Ignoring associated class due to version mismatch "
<< itr->_name<<"["<<itr->_firstVersion <<","<<itr->_lastVersion <<"]for output version "<<outputVersion<< std::endl;*/
}
_fields.push_back( assocWrapper->getName() );
assocWrapper->write( *this, *obj );
if ( getException() ) return;
_fields.pop_back();
}
}