gltfio: add 'detach' methods to allow ownership transfer

These new methods allow gltfio to be integrated into internal Google
libraries.
This commit is contained in:
Philip Rideout
2022-08-09 09:39:07 -07:00
parent efba9a636a
commit 75004e9d3e
5 changed files with 61 additions and 16 deletions

View File

@@ -11,6 +11,7 @@ A new header is inserted each time a *tag* is created.
- WebGL: added missing IBL builder to TypeScript annotations
- engine: Fix incorrect precision restoration when computing accurate world translations
- engine: make `MaterialInstance` public API friendly to `std::string_view` parameters
- gltfio: add 'detach' methods to allow ownership transfer of entities and components
## v1.25.4

View File

@@ -334,6 +334,23 @@ public:
void addEntitiesToScene(filament::Scene& targetScene, const Entity* entities, size_t count,
SceneMask sceneFilter);
/**
* Releases ownership of entities and their Filament components.
*
* This makes the client take responsibility for destroying Filament
* components (e.g. Renderable, TransformManager component) as well as
* the underlying entities.
*/
void detachFilamentComponents();
/**
* Releases ownership of material instances.
*
* This makes the client take responsibility for destroying MaterialInstance
* objects. The getMaterialInstances query becomes invalid after detachment.
*/
void detachMaterialInstances();
/*! \cond PRIVATE */
FilamentInstance** getAssetInstances() noexcept;

View File

@@ -255,9 +255,17 @@ struct FFilamentAsset : public FilamentAsset {
void addEntitiesToScene(filament::Scene& targetScene, const Entity* entities, size_t count,
SceneMask sceneFilter);
void detachFilamentComponents() {
mDetachedFilamentComponents = true;
}
void detachMaterialInstances() {
mMaterialInstances.clear();
}
// end public API
void takeOwnership(filament::Texture* texture) {
void attachTexture(filament::Texture* texture) {
mTextures.push_back(texture);
}
@@ -299,6 +307,7 @@ struct FFilamentAsset : public FilamentAsset {
DependencyGraph mDependencyGraph;
tsl::htrie_map<char, std::vector<utils::Entity>> mNameToEntity;
utils::CString mAssetExtras;
bool mDetachedFilamentComponents = false;
// Sentinels for situations where ResourceLoader needs to generate data.
const cgltf_accessor mGenerateNormals = {};

View File

@@ -33,10 +33,11 @@ using namespace utils;
namespace filament::gltfio {
FFilamentAsset::~FFilamentAsset() {
// Free transient load-time data if they haven't been freed yet.
releaseSourceData();
// The only things we need to free in the instances are their animators.
// The union of all instance entities will be destroyed below.
// Destroy all instance objects and their animators. Instance entities / components are
// destroyed later in this method because they are owned by the asset.
for (FFilamentInstance* instance : mInstances) {
delete instance->animator;
delete instance;
@@ -45,21 +46,30 @@ FFilamentAsset::~FFilamentAsset() {
delete mAnimator;
delete mWireframe;
mEngine->destroy(mRoot);
mEntityManager->destroy(mRoot);
for (auto entity : mEntities) {
// Destroy the entity's renderable, light, transform, and camera components.
mEngine->destroy(entity);
// Destroy the name component.
if (mNameManager) {
// Destroy name components.
if (mNameManager) {
for (auto entity : mEntities) {
mNameManager->removeComponent(entity);
}
// Destroy the node component.
mNodeManager->destroy(entity);
// Destroy the actual entity.
mEntityManager->destroy(entity);
}
// Destroy gltfio node components.
for (auto entity : mEntities) {
mNodeManager->destroy(entity);
}
// Destroy all renderable, light, transform, and camera components,
// then destroy the actual entities. This includes instances.
if (!mDetachedFilamentComponents) {
mEngine->destroy(mRoot);
mEntityManager->destroy(mRoot);
for (auto entity : mEntities) {
mEngine->destroy(entity);
mEntityManager->destroy(entity);
}
}
for (auto mi : mMaterialInstances) {
mEngine->destroy(mi);
}
@@ -283,6 +293,14 @@ void FFilamentAsset::addEntitiesToScene(Scene& targetScene, const Entity* entiti
}
}
void FilamentAsset::detachFilamentComponents() {
upcast(this)->detachFilamentComponents();
}
void FilamentAsset::detachMaterialInstances() {
upcast(this)->detachMaterialInstances();
}
size_t FilamentAsset::getEntityCount() const noexcept {
return upcast(this)->getEntityCount();
}

View File

@@ -687,7 +687,7 @@ Texture* ResourceLoader::Impl::getOrCreateTexture(FFilamentAsset* asset, const T
<< provider->getPushMessage() << io::endl;
asset->mDependencyGraph.markAsError(tb.materialInstance);
} else {
asset->takeOwnership(texture);
asset->attachTexture(texture);
}
return texture;