/* * Copyright 2006 Sony Computer Entertainment Inc. * * Licensed under the MIT Open Source License, for details please see license.txt or the website * http://www.opensource.org/licenses/mit-license.php * */ #include <dae.h> #include <dae/daeDatabase.h> #include <dae/daeDom.h> #include <dae/daeIDRef.h> #include <dae/daeMetaElement.h> #include <modules/daeSTLDatabase.h> #include <dae/daeErrorHandler.h> #include <dae/daeRawResolver.h> #include <dae/daeStandardURIResolver.h> #include <dom/domTypes.h> #include <dom/domCOLLADA.h> #ifdef DOM_INCLUDE_LIBXML #include <modules/daeLIBXMLPlugin.h> #endif #ifdef DOM_INCLUDE_TINYXML #include <dae/daeTinyXMLPlugin.h> #endif using namespace std; // Don't include domConstants.h because it varies depending on the dom version, // just extern the one thing we need (COLLADA_VERSION) which all versions of // domConstants.h/.cpp are required to define. extern daeString COLLADA_VERSION; daeInt DAEInstanceCount = 0; DAE::charEncoding DAE::globalCharEncoding = DAE::Utf8; void DAE::cleanup() { //Contributed by Nus - Wed, 08 Nov 2006 daeStringRef::releaseStringTable(); //---------------------- #ifndef NO_BOOST try { boost::filesystem::remove_all(cdom::getSafeTmpDir()); } catch (...) { daeErrorHandler::get()->handleWarning("Could not remove temporary directory in DAE::cleanup()\n"); } #endif } void DAE::init(daeDatabase* database_, daeIOPlugin* ioPlugin) { database = NULL; plugin = NULL; defaultDatabase = false; defaultPlugin = false; metas.setCount(colladaTypeCount()); initializeDomMeta(*this); DAEInstanceCount++; // The order of the URI resolvers is significant, so be careful uriResolvers.list().append(new daeRawResolver(*this)); uriResolvers.list().append(new daeStandardURIResolver(*this)); idRefResolvers.addResolver(new daeDefaultIDRefResolver(*this)); setDatabase(database_); setIOPlugin(ioPlugin); } DAE::~DAE() { if (defaultDatabase) delete database; if (defaultPlugin) delete plugin; if ( --DAEInstanceCount <= 0 ) cleanup(); } // Database setup daeDatabase* DAE::getDatabase() { return database; } daeInt DAE::setDatabase(daeDatabase* _database) { if (defaultDatabase) delete database; if (_database) { defaultDatabase = false; database = _database; } else { //create default database database = new daeSTLDatabase(*this); defaultDatabase = true; } database->setMeta(getMeta(domCOLLADA::ID())); return DAE_OK; } // IO Plugin setup daeIOPlugin* DAE::getIOPlugin() { return plugin; } daeInt DAE::setIOPlugin(daeIOPlugin* _plugin) { if (defaultPlugin) delete plugin; if (_plugin) { defaultPlugin = false; plugin = _plugin; } else { plugin = NULL; defaultPlugin = true; //create default plugin #ifdef DOM_INCLUDE_LIBXML plugin = new daeLIBXMLPlugin(*this); #else #ifdef DOM_INCLUDE_TINYXML plugin = new daeTinyXMLPlugin; #endif #endif if (!plugin) { daeErrorHandler::get()->handleWarning("No IOPlugin Set"); plugin = new daeIOEmpty; return DAE_ERROR; } } int res = plugin->setMeta(getMeta(domCOLLADA::ID())); if (res != DAE_OK) { if (defaultPlugin) { defaultPlugin = false; delete plugin; } plugin = NULL; } return res; } // Take a path (either a URI ref or a file system path) and return a full URI, // using the current working directory as the base URI if a relative URI // reference is given. string DAE::makeFullUri(const string& path) { daeURI uri(*this, cdom::nativePathToUri(path)); return uri.str(); } domCOLLADA* DAE::add(const string& path) { close(path); string uri = makeFullUri(path); database->insertDocument(uri.c_str()); return getRoot(uri); } domCOLLADA* DAE::openCommon(const string& path, daeString buffer) { close(path); string uri = makeFullUri(path); plugin->setDatabase(database); if (plugin->read(daeURI(*this, uri.c_str()), buffer) != DAE_OK) return NULL; return getRoot(uri); } domCOLLADA* DAE::open(const string& path) { return openCommon(path, NULL); } domCOLLADA* DAE::openFromMemory(const string& path, daeString buffer) { return openCommon(path, buffer); } bool DAE::writeCommon(const string& docPath, const string& pathToWriteTo, bool replace) { string docUri = makeFullUri(docPath), uriToWriteTo = makeFullUri(pathToWriteTo); plugin->setDatabase(database); if (daeDocument* doc = getDoc(docUri)) return plugin->write(daeURI(*this, uriToWriteTo.c_str()), doc, replace) == DAE_OK; return false; } bool DAE::write(const string& path) { return writeCommon(path, path, true); } bool DAE::writeTo(const string& docPath, const string& pathToWriteTo) { return writeCommon(docPath, pathToWriteTo, true); } bool DAE::writeAll() { for (int i = 0; i < getDocCount(); i++) if (save((daeUInt)i, true) != DAE_OK) return false; return true; } void DAE::close(const string& path) { database->removeDocument(getDoc(makeFullUri(path).c_str())); } daeInt DAE::clear() { database->clear(); rawRefCache.clear(); sidRefCache.clear(); return DAE_OK; } // Deprecated methods daeInt DAE::load(daeString uri, daeString docBuffer) { return openCommon(uri, docBuffer) ? DAE_OK : DAE_ERROR; } daeInt DAE::save(daeString uri, daeBool replace) { return writeCommon(uri, uri, replace) ? DAE_OK : DAE_ERROR; } daeInt DAE::save(daeUInt documentIndex, daeBool replace) { if ((int)documentIndex >= getDocCount()) return DAE_ERROR; // Save it out to the URI it was loaded from daeString uri = getDoc((int)documentIndex)->getDocumentURI()->getURI(); return writeCommon(uri, uri, replace) ? DAE_OK : DAE_ERROR; } daeInt DAE::saveAs(daeString uriToSaveTo, daeString docUri, daeBool replace) { return writeCommon(docUri, uriToSaveTo, replace) ? DAE_OK : DAE_ERROR; } daeInt DAE::saveAs(daeString uriToSaveTo, daeUInt documentIndex, daeBool replace) { if ((int)documentIndex >= getDocCount()) return DAE_ERROR; daeString docUri = getDoc((int)documentIndex)->getDocumentURI()->getURI(); return writeCommon(docUri, uriToSaveTo, replace) ? DAE_OK : DAE_ERROR; } daeInt DAE::unload(daeString uri) { close(uri); return DAE_OK; } int DAE::getDocCount() { return (int)database->getDocumentCount(); } daeDocument* DAE::getDoc(int i) { return database->getDocument(i); } daeDocument* DAE::getDoc(const string& path) { return database->getDocument(makeFullUri(path).c_str(), true); } domCOLLADA* DAE::getRoot(const string& path) { if (daeDocument* doc = getDoc(path)) return (domCOLLADA*)doc->getDomRoot(); return NULL; } bool DAE::setRoot(const string& path, domCOLLADA* root) { if (daeDocument* doc = getDoc(path)) doc->setDomRoot(root); else database->insertDocument(makeFullUri(path).c_str(), root); return getRoot(path) != NULL; } domCOLLADA* DAE::getDom(daeString uri) { return getRoot(uri); } daeInt DAE::setDom(daeString uri, domCOLLADA* dom) { return setRoot(uri, dom); } daeString DAE::getDomVersion() { return(COLLADA_VERSION); } daeAtomicTypeList& DAE::getAtomicTypes() { return atomicTypes; } daeMetaElement* DAE::getMeta(daeInt typeID) { if (typeID < 0 || typeID >= daeInt(metas.getCount())) return NULL; return metas[typeID]; } daeMetaElementRefArray& DAE::getAllMetas() { return metas; } void DAE::setMeta(daeInt typeID, daeMetaElement& meta) { if (typeID < 0 || typeID >= daeInt(metas.getCount())) return; metas[typeID] = &meta; } daeURIResolverList& DAE::getURIResolvers() { return uriResolvers; } daeURI& DAE::getBaseURI() { return baseUri; } void DAE::setBaseURI(const daeURI& uri) { baseUri = uri; } void DAE::setBaseURI(const string& uri) { baseUri = uri.c_str(); } daeIDRefResolverList& DAE::getIDRefResolvers() { return idRefResolvers; } daeRawRefCache& DAE::getRawRefCache() { return rawRefCache; } daeSidRefCache& DAE::getSidRefCache() { return sidRefCache; } void DAE::dummyFunction1() { } DAE::charEncoding DAE::getGlobalCharEncoding() { return globalCharEncoding; } void DAE::setGlobalCharEncoding(charEncoding encoding) { globalCharEncoding = encoding; } DAE::charEncoding DAE::getCharEncoding() { return localCharEncoding.get() ? *localCharEncoding : getGlobalCharEncoding(); } void DAE::setCharEncoding(charEncoding encoding) { localCharEncoding.reset(new charEncoding(encoding)); }