Beispiel #1
0
Ogre::MeshPtr CMapLoader::LoadModel(const char * path)
{
	MapResource<Ogre::MeshPtr> res;
	Ogre::MeshPtr pMesh;

	// Check if this model was already loaded
	pMesh = Ogre::MeshManager::getSingleton().getByName(path);
	if(!pMesh.isNull())
		return pMesh;

	sectionitem_t * item = LoadItem(path, &res.map);
	if(item == NULL)
		return Ogre::MeshPtr(NULL);

	pMesh = Ogre::MeshManager::getSingleton().createManual(path,
		Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);

	Ogre::DataStreamPtr stream(new Ogre::MemoryDataStream(item->data, item->size, false, true));
	Ogre::MeshSerializer serializer;
	serializer.importMesh(stream, pMesh.getPointer());

	// No need to keep this in memory
	mapUnloadItem(item);

	// Track this resource
	res.data = pMesh;
	meshes.push_back(res);
	
	return pMesh;
}
Beispiel #2
0
bool OgreMeshAsset::DeserializeFromData(const u8 *data_, size_t numBytes, bool allowAsynchronous)
{
    PROFILE(OgreMeshAsset_LoadFromFileInMemory);

    /// Force an unload of this data first.
    Unload();

    /// @todo Duplicate allowAsynchronous code in OgreMeshAsset and TextureAsset.
    if ((OGRE_THREAD_SUPPORT == 0) || !assetAPI->Cache() || assetAPI->IsHeadless() || IsAssimpFileType() ||
        assetAPI->GetFramework()->HasCommandLineParameter("--noAsyncAssetLoad") ||
        assetAPI->GetFramework()->HasCommandLineParameter("--no_async_asset_load")) /**< @todo Remove support for the deprecated underscore version at some point. */
    {
        allowAsynchronous = false;
    }

    QString cacheDiskSource;
    if (allowAsynchronous)
    {
        cacheDiskSource = assetAPI->Cache()->FindInCache(Name());
        if (cacheDiskSource.isEmpty())
            allowAsynchronous = false;
    }
    
    // Asynchronous loading
    // 1. AssetAPI allows a asynch load. This is false when called from LoadFromFile(), LoadFromCache() etc.
    // 2. We have a rendering window for Ogre as Ogre::ResourceBackgroundQueue does not work otherwise. Its not properly initialized without a rendering window.
    // 3. The Ogre we are building against has thread support.
    if (allowAsynchronous)
    {
        // We can only do threaded loading from disk, and not any disk location but only from asset cache.
        // local:// refs will return empty string here and those will fall back to the non-threaded loading.
        // Do not change this to do DiskCache() as that directory for local:// refs will not be a known resource location for ogre.
        QFileInfo fileInfo(cacheDiskSource);
        std::string sanitatedAssetRef = fileInfo.fileName().toStdString();
        //! \todo - Should we set this somewhere for async path?: ogreMesh->setAutoBuildEdgeLists(false);
        loadTicket_ = Ogre::ResourceBackgroundQueue::getSingleton().load(Ogre::MeshManager::getSingleton().getResourceType(),
                          sanitatedAssetRef, OgreRenderer::OgreRenderingModule::CACHE_RESOURCE_GROUP, false, 0, 0, this);
        return true;
    }

    if (!data_)
    {
        LogError("OgreMeshAsset::DeserializeFromData: Cannot deserialize from null input data");
        return false;
    }
    
    // Synchronous loading
    if (ogreMesh.isNull())
    {   
        ogreMesh = Ogre::MeshManager::getSingleton().createManual(
            AssetAPI::SanitateAssetRef(this->Name()).toStdString(), Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
        if (ogreMesh.isNull())
        {
            LogError("OgreMeshAsset::DeserializeFromData: Failed to create mesh " + Name());
            return false; 
        }
        ogreMesh->setAutoBuildEdgeLists(false);
    }

    // Convert file to Ogre mesh using assimp
    if (IsAssimpFileType())
    {
#ifdef ASSIMP_ENABLED
        emit ExternalConversionRequested(this, data_, numBytes);
        return true;
#else
        LogError(QString("OgreMeshAsset::DeserializeFromData: cannot convert " + Name() + " to Ogre mesh. OpenAssetImport is not enabled."));
        return false;
#endif
    }

    try
    {
        std::vector<u8> tempData(data_, data_ + numBytes);
#include "DisableMemoryLeakCheck.h"
        Ogre::DataStreamPtr stream(new Ogre::MemoryDataStream((void*)&tempData[0], numBytes, false));
#include "EnableMemoryLeakCheck.h"
        Ogre::MeshSerializer serializer;
        serializer.importMesh(stream, ogreMesh.getPointer()); // Note: importMesh *adds* submeshes to an existing mesh. It doesn't replace old ones.
    }
    catch (Ogre::Exception &e)
    {
        LogError(QString("OgreMeshAsset::DeserializeFromData: Ogre::MeshSerializer::importMesh failed when loading asset '" + Name() + "': ") + e.what());

        if(IsAssimpFileType())
            LogError(QString("OgreMeshAsset::DeserializeFromData: cannot convert " + Name() + " to Ogre mesh. OpenAssetImport is not enabled."));

        return false;
    }

    if (GenerateMeshData())
    {        
        // We did a synchronous load, must call AssetLoadCompleted here.
        assetAPI->AssetLoadCompleted(Name());
        return true;
    }
    else 
        return false;
}
Beispiel #3
0
    bool OgreMeshResource::SetData(Foundation::AssetPtr source)
    {
        if (!source)
        {
            OgreRenderingModule::LogError("Null source asset data pointer");     
            return false;
        }
        if (!source->GetSize())
        {
            OgreRenderingModule::LogError("Zero sized mesh asset");     
            return false;
        }
                
        try
        {
            if (ogre_mesh_.isNull())
            {   
                ogre_mesh_ = Ogre::MeshManager::getSingleton().createManual(
                    id_, Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
                if (ogre_mesh_.isNull())
                {
                    OgreRenderingModule::LogError("Failed to create mesh " + id_);
                    return false; 
                }   
                ogre_mesh_->setAutoBuildEdgeLists(false);
            }

            Ogre::DataStreamPtr stream(new Ogre::MemoryDataStream((void*)source->GetData(), source->GetSize(), false));
            Ogre::MeshSerializer serializer;
            serializer.importMesh(stream, ogre_mesh_.getPointer());
            
            // Generate tangents to mesh
            try
            {
                unsigned short src, dest;
                if (!ogre_mesh_->suggestTangentVectorBuildParams(Ogre::VES_TANGENT, src, dest))
                    ogre_mesh_->buildTangentVectors(Ogre::VES_TANGENT, src, dest);
            }
            catch (...) {}
            
            // Generate extremity points to submeshes, 1 should be enough
            try
            {
                for(uint i = 0; i < ogre_mesh_->getNumSubMeshes(); ++i)
                {
                    Ogre::SubMesh *smesh = ogre_mesh_->getSubMesh(i);
                    if (smesh)
                        smesh->generateExtremes(1);
                }
            }
            catch (...) {}
            
            // Assign default materials that won't complain
            original_materials_.clear();
            for (uint i = 0; i < ogre_mesh_->getNumSubMeshes(); ++i)
            {
                Ogre::SubMesh* submesh = ogre_mesh_->getSubMesh(i);
                if (submesh)
                {
                    original_materials_.push_back(submesh->getMaterialName());
                    submesh->setMaterialName("UnlitTextured");
                }
            }
            
        }
        catch (Ogre::Exception &e)
        {
            OgreRenderingModule::LogError("Failed to create mesh " + id_ + ": " + std::string(e.what()));
            RemoveMesh();
            return false;
        }

        OgreRenderingModule::LogDebug("Ogre mesh " + id_ + " created");
        return true;
    }
Beispiel #4
0
AssetLoadState OgreMeshAsset::DeserializeFromData(const u8 *data_, size_t numBytes)
{
    PROFILE(OgreMeshAsset_LoadFromFileInMemory);
    assert(data_);
    if (!data_)
        return ASSET_LOAD_FAILED;
    
    // Force an unload of this data first.
    Unload();

    if (OGRE_THREAD_SUPPORT != 0)
    {
        // We can only do threaded loading from disk, and not any disk location but only from asset cache.
        // local:// refs will return empty string here and those will fall back to the non-threaded loading.
        // Do not change this to do DiskCache() as that directory for local:// refs will not be a known resource location for ogre.
        QString cacheDiskSource = assetAPI->GetAssetCache()->GetDiskSource(QUrl(Name()));
        if (!cacheDiskSource.isEmpty())
        {
            QFileInfo fileInfo(cacheDiskSource);
            std::string sanitatedAssetRef = fileInfo.fileName().toStdString(); 
            loadTicket_ = Ogre::ResourceBackgroundQueue::getSingleton().load(Ogre::MeshManager::getSingleton().getResourceType(),
                                                                             sanitatedAssetRef, OgreRenderer::OgreRenderingModule::CACHE_RESOURCE_GROUP,
                                                                             false, 0, 0, this);
            return ASSET_LOAD_PROCESSING;
        }
    }

    if (ogreMesh.isNull())
    {   
        ogreMesh = Ogre::MeshManager::getSingleton().createManual(
            OgreRenderer::SanitateAssetIdForOgre(this->Name().toStdString()), Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
        if (ogreMesh.isNull())
        {
            LogError("Failed to create mesh " + Name().toStdString());
            return ASSET_LOAD_FAILED; 
        }
        ogreMesh->setAutoBuildEdgeLists(false);
    }

    std::vector<u8> tempData(data_, data_ + numBytes);
#include "DisableMemoryLeakCheck.h"
    Ogre::DataStreamPtr stream(new Ogre::MemoryDataStream((void*)&tempData[0], numBytes, false));
#include "EnableMemoryLeakCheck.h"
    Ogre::MeshSerializer serializer;
    serializer.importMesh(stream, ogreMesh.getPointer()); // Note: importMesh *adds* submeshes to an existing mesh. It doesn't replace old ones.
    
    // Generate tangents to mesh
    try
    {
        unsigned short src, dest;
        ///\bug Crashes if called for a mesh that has null or zero vertices in the vertex buffer, or null or zero indices in the index buffer.
        if (!ogreMesh->suggestTangentVectorBuildParams(Ogre::VES_TANGENT, src, dest))
            ogreMesh->buildTangentVectors(Ogre::VES_TANGENT, src, dest);
    }
    catch (...) {}
    
    // Generate extremity points to submeshes, 1 should be enough
    try
    {
        for(uint i = 0; i < ogreMesh->getNumSubMeshes(); ++i)
        {
            Ogre::SubMesh *smesh = ogreMesh->getSubMesh(i);
            if (smesh)
                smesh->generateExtremes(1);
        }
    }
    catch (...) {}
        
    try
    {
        // Assign default materials that won't complain
        SetDefaultMaterial();
        // Set asset references the mesh has
        //ResetReferences();
    }
    catch (Ogre::Exception &e)
    {
        LogError("Failed to create mesh " + this->Name().toStdString() + ": " + std::string(e.what()));
        Unload();
        return ASSET_LOAD_FAILED;
    }

    //internal_name_ = SanitateAssetIdForOgre(id_);
    
    LogDebug("Ogre mesh " + this->Name().toStdString() + " created");
    return ASSET_LOAD_SUCCESFULL;
}