Improved 3D cache manager's ability to replace outdated cache models
This commit is contained in:
parent
b1d35965f5
commit
8dd744f635
|
@ -51,6 +51,15 @@
|
|||
|
||||
#define CACHE_CONFIG_NAME wxT( "cache.cfg" )
|
||||
|
||||
static bool checkTag( const char* aTag, void* aPluginMgrPtr )
|
||||
{
|
||||
if( NULL == aTag || NULL == aPluginMgrPtr )
|
||||
return false;
|
||||
|
||||
S3D_PLUGIN_MANAGER *pp = (S3D_PLUGIN_MANAGER*) aPluginMgrPtr;
|
||||
|
||||
return pp->CheckTag( aTag );
|
||||
}
|
||||
|
||||
static const wxString sha1ToWXString( const unsigned char* aSHA1Sum )
|
||||
{
|
||||
|
@ -136,6 +145,7 @@ public:
|
|||
const wxString GetCacheBaseName( void );
|
||||
|
||||
unsigned char sha1sum[20];
|
||||
std::string pluginInfo; // PluginName:Version string
|
||||
SCENEGRAPH* sceneData;
|
||||
S3DMODEL* renderData;
|
||||
};
|
||||
|
@ -310,7 +320,7 @@ SCENEGRAPH* S3D_CACHE::checkCache( const wxString& aFileName, S3D_CACHE_ENTRY**
|
|||
if( wxFileName::FileExists( cachename ) && loadCacheData( ep ) )
|
||||
return ep->sceneData;
|
||||
|
||||
ep->sceneData = m_Plugins->Load3DModel( aFileName );
|
||||
ep->sceneData = m_Plugins->Load3DModel( aFileName, ep->pluginInfo );
|
||||
|
||||
if( NULL != ep->sceneData )
|
||||
saveCacheData( ep );
|
||||
|
@ -405,7 +415,7 @@ bool S3D_CACHE::loadCacheData( S3D_CACHE_ENTRY* aCacheItem )
|
|||
if( NULL != aCacheItem->sceneData )
|
||||
S3D::DestroyNode( (SGNODE*) aCacheItem->sceneData );
|
||||
|
||||
aCacheItem->sceneData = (SCENEGRAPH*)S3D::ReadCache( fname.ToUTF8() );
|
||||
aCacheItem->sceneData = (SCENEGRAPH*)S3D::ReadCache( fname.ToUTF8(), m_Plugins, checkTag );
|
||||
|
||||
if( NULL == aCacheItem->sceneData )
|
||||
return false;
|
||||
|
@ -475,7 +485,8 @@ bool S3D_CACHE::saveCacheData( S3D_CACHE_ENTRY* aCacheItem )
|
|||
}
|
||||
}
|
||||
|
||||
return S3D::WriteCache( fname.ToUTF8(), true, (SGNODE*)aCacheItem->sceneData );
|
||||
return S3D::WriteCache( fname.ToUTF8(), true, (SGNODE*)aCacheItem->sceneData,
|
||||
aCacheItem->pluginInfo.c_str() );
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* This program source code file is part of KiCad, a free EDA CAD application.
|
||||
*
|
||||
* Copyright (C) 2015 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
* Copyright (C) 2015-2016 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
@ -27,6 +27,7 @@
|
|||
#include <unistd.h>
|
||||
#include <sys/types.h>
|
||||
#include <string>
|
||||
#include <sstream>
|
||||
|
||||
#include <wx/string.h>
|
||||
#include <wx/dir.h>
|
||||
|
@ -398,7 +399,7 @@ std::list< wxString > const* S3D_PLUGIN_MANAGER::GetFileFilters( void ) const
|
|||
}
|
||||
|
||||
|
||||
SCENEGRAPH* S3D_PLUGIN_MANAGER::Load3DModel( const wxString& aFileName )
|
||||
SCENEGRAPH* S3D_PLUGIN_MANAGER::Load3DModel( const wxString& aFileName, std::string& aPluginInfo )
|
||||
{
|
||||
wxFileName raw( aFileName );
|
||||
wxString ext = raw.GetExt();
|
||||
|
@ -416,8 +417,11 @@ SCENEGRAPH* S3D_PLUGIN_MANAGER::Load3DModel( const wxString& aFileName )
|
|||
SCENEGRAPH* sp = sL->second->Load( aFileName.ToUTF8() );
|
||||
|
||||
if( NULL != sp )
|
||||
{
|
||||
sL->second->GetPluginInfo( aPluginInfo );
|
||||
return sp;
|
||||
}
|
||||
}
|
||||
|
||||
++sL;
|
||||
}
|
||||
|
@ -444,3 +448,45 @@ void S3D_PLUGIN_MANAGER::ClosePlugins( void )
|
|||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
bool S3D_PLUGIN_MANAGER::CheckTag( const char* aTag )
|
||||
{
|
||||
if( NULL == aTag || aTag[0] == 0 || m_Plugins.empty() )
|
||||
return false;
|
||||
|
||||
std::string tname = aTag;
|
||||
std::string pname; // plugin name
|
||||
|
||||
size_t cpos = tname.find( ':' );
|
||||
|
||||
// if there is no colon or plugin name then the tag is bad
|
||||
if( cpos == std::string::npos || cpos == 0 )
|
||||
return false;
|
||||
|
||||
pname = tname.substr( 0, cpos );
|
||||
std::string ptag; // tag from the plugin
|
||||
|
||||
std::list< KICAD_PLUGIN_LDR_3D* >::iterator pS = m_Plugins.begin();
|
||||
std::list< KICAD_PLUGIN_LDR_3D* >::iterator pE = m_Plugins.end();
|
||||
|
||||
while( pS != pE )
|
||||
{
|
||||
ptag.clear();
|
||||
(*pS)->GetPluginInfo( ptag );
|
||||
|
||||
// if the plugin name matches then the version
|
||||
// must also match
|
||||
if( !ptag.compare( 0, pname.size(), pname ) )
|
||||
{
|
||||
if( ptag.compare( tname ) )
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
++pS;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* This program source code file is part of KiCad, a free EDA CAD application.
|
||||
*
|
||||
* Copyright (C) 2015 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
* Copyright (C) 2016 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
@ -31,6 +31,7 @@
|
|||
|
||||
#include <map>
|
||||
#include <list>
|
||||
#include <string>
|
||||
#include <wx/string.h>
|
||||
|
||||
class wxWindow;
|
||||
|
@ -82,7 +83,7 @@ public:
|
|||
*/
|
||||
std::list< wxString > const* GetFileFilters( void ) const;
|
||||
|
||||
SCENEGRAPH* Load3DModel( const wxString& aFileName );
|
||||
SCENEGRAPH* Load3DModel( const wxString& aFileName, std::string& aPluginInfo );
|
||||
|
||||
/**
|
||||
* Function ClosePlugins
|
||||
|
@ -91,6 +92,13 @@ public:
|
|||
* reloaded as calls are made to load specific models.
|
||||
*/
|
||||
void ClosePlugins( void );
|
||||
|
||||
/**
|
||||
* Function CheckTag
|
||||
* checks the given tag and returns true if the plugin named in the tag
|
||||
* is not loaded or the plugin is loaded and the version matches
|
||||
*/
|
||||
bool CheckTag( const char* aTag );
|
||||
};
|
||||
|
||||
#endif // PLUGIN_MANAGER_3D_H
|
||||
|
|
|
@ -48,6 +48,10 @@
|
|||
static char BadNode[] = " * [BUG] NULL pointer passed for aNode\n";
|
||||
#endif
|
||||
|
||||
// version format of the cache file
|
||||
#define SG_VERSION_TAG "VERSION:2"
|
||||
|
||||
|
||||
static void formatMaterial( SMATERIAL& mat, SGAPPEARANCE const* app )
|
||||
{
|
||||
float v0, v1, v2;
|
||||
|
@ -229,7 +233,8 @@ void S3D::DestroyNode( SGNODE* aNode )
|
|||
}
|
||||
|
||||
|
||||
bool S3D::WriteCache( const char* aFileName, bool overwrite, SGNODE* aNode )
|
||||
bool S3D::WriteCache( const char* aFileName, bool overwrite, SGNODE* aNode,
|
||||
const char* aPluginInfo )
|
||||
{
|
||||
if( NULL == aFileName || aFileName[0] == 0 )
|
||||
return false;
|
||||
|
@ -281,23 +286,34 @@ bool S3D::WriteCache( const char* aFileName, bool overwrite, SGNODE* aNode )
|
|||
return false;
|
||||
}
|
||||
|
||||
output << "(" << SG_VERSION_TAG << ")";
|
||||
|
||||
if( NULL != aPluginInfo && aPluginInfo[0] != 0 )
|
||||
output << "(" << aPluginInfo << ")";
|
||||
else
|
||||
output << "(INTERNAL:0.0.0.0)";
|
||||
|
||||
bool rval = aNode->WriteCache( output, NULL );
|
||||
output.close();
|
||||
|
||||
#ifdef DEBUG
|
||||
if( !rval )
|
||||
{
|
||||
#ifdef DEBUG
|
||||
std::cerr << __FILE__ << ": " << __FUNCTION__ << ": " << __LINE__ << "\n";
|
||||
std::cerr << " * [INFO] problems encountered writing cache file '";
|
||||
std::cerr << aFileName << "'\n";
|
||||
}
|
||||
#endif
|
||||
|
||||
// delete the defective file
|
||||
wxRemoveFile( ofile );
|
||||
}
|
||||
|
||||
return rval;
|
||||
}
|
||||
|
||||
|
||||
SGNODE* S3D::ReadCache( const char* aFileName )
|
||||
SGNODE* S3D::ReadCache( const char* aFileName, void* aPluginMgr,
|
||||
bool (*aTagCheck)( const char*, void* ) )
|
||||
{
|
||||
if( NULL == aFileName || aFileName[0] == 0 )
|
||||
return NULL;
|
||||
|
@ -336,6 +352,79 @@ SGNODE* S3D::ReadCache( const char* aFileName )
|
|||
return NULL;
|
||||
}
|
||||
|
||||
// from SG_VERSION_TAG 1, read the version tag; if it's not the expected tag
|
||||
// then we fail to read the cache file
|
||||
do
|
||||
{
|
||||
std::string name;
|
||||
char schar;
|
||||
file.get( schar );
|
||||
|
||||
if( '(' != schar )
|
||||
{
|
||||
#ifdef DEBUG
|
||||
std::cerr << __FILE__ << ": " << __FUNCTION__ << ": " << __LINE__ << "\n";
|
||||
std::cerr << " * [INFO] corrupt data; missing left parenthesis at position ";
|
||||
std::cerr << file.tellg() << "\n";
|
||||
#endif
|
||||
|
||||
file.close();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
file.get( schar );
|
||||
|
||||
while( ')' != schar && file.good() )
|
||||
{
|
||||
name.push_back( schar );
|
||||
file.get( schar );
|
||||
}
|
||||
|
||||
if( name.compare( SG_VERSION_TAG ) )
|
||||
{
|
||||
file.close();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
} while( 0 );
|
||||
|
||||
// from SG_VERSION_TAG 2, read the PluginInfo string and check that it matches
|
||||
// version tag; if it's not the expected tag then we fail to read the file
|
||||
do
|
||||
{
|
||||
std::string name;
|
||||
char schar;
|
||||
file.get( schar );
|
||||
|
||||
if( '(' != schar )
|
||||
{
|
||||
#ifdef DEBUG
|
||||
std::cerr << __FILE__ << ": " << __FUNCTION__ << ": " << __LINE__ << "\n";
|
||||
std::cerr << " * [INFO] corrupt data; missing left parenthesis at position ";
|
||||
std::cerr << file.tellg() << "\n";
|
||||
#endif
|
||||
|
||||
file.close();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
file.get( schar );
|
||||
|
||||
while( ')' != schar && file.good() )
|
||||
{
|
||||
name.push_back( schar );
|
||||
file.get( schar );
|
||||
}
|
||||
|
||||
// check the plugin tag
|
||||
if( NULL != aTagCheck && NULL != aPluginMgr && !aTagCheck( name.c_str(), aPluginMgr ) )
|
||||
{
|
||||
file.close();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
} while( 0 );
|
||||
|
||||
bool rval = np->ReadCache( file, NULL );
|
||||
file.close();
|
||||
|
||||
|
|
|
@ -33,9 +33,6 @@
|
|||
#include "3d_cache/sg/sg_helpers.h"
|
||||
|
||||
|
||||
// version format of the cache file
|
||||
#define SG_VERSION_TAG "VERSION:1"
|
||||
|
||||
SCENEGRAPH::SCENEGRAPH( SGNODE* aParent ) : SGNODE( aParent )
|
||||
{
|
||||
m_SGtype = S3D::SGTYPE_TRANSFORM;
|
||||
|
@ -370,7 +367,6 @@ bool SCENEGRAPH::WriteCache( std::ofstream& aFile, SGNODE* parentNode )
|
|||
// ensure unique node names
|
||||
ResetNodeIndex();
|
||||
ReNameNodes();
|
||||
aFile << "[" << SG_VERSION_TAG << "]";
|
||||
}
|
||||
|
||||
if( aFile.fail() )
|
||||
|
@ -467,36 +463,6 @@ bool SCENEGRAPH::ReadCache( std::ifstream& aFile, SGNODE* parentNode )
|
|||
|
||||
if( NULL == parentNode )
|
||||
{
|
||||
// read the tag; if it's not the expected tag then we fail to read the cache file
|
||||
do
|
||||
{
|
||||
char schar;
|
||||
aFile.get( schar );
|
||||
|
||||
if( '[' != schar )
|
||||
{
|
||||
#ifdef DEBUG
|
||||
std::cerr << __FILE__ << ": " << __FUNCTION__ << ": " << __LINE__ << "\n";
|
||||
std::cerr << " * [INFO] corrupt data; missing left bracket at position ";
|
||||
std::cerr << aFile.tellg() << "\n";
|
||||
#endif
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
aFile.get( schar );
|
||||
|
||||
while( ']' != schar && aFile.good() )
|
||||
{
|
||||
name.push_back( schar );
|
||||
aFile.get( schar );
|
||||
}
|
||||
|
||||
if( name.compare( SG_VERSION_TAG ) )
|
||||
return false;
|
||||
|
||||
} while( 0 );
|
||||
|
||||
// we need to read the tag and verify its type
|
||||
if( S3D::SGTYPE_TRANSFORM != S3D::ReadTag( aFile, name ) )
|
||||
{
|
||||
|
|
|
@ -69,7 +69,8 @@ namespace S3D
|
|||
* @param aNode is any node within the node tree which is to be written
|
||||
* @return true on success
|
||||
*/
|
||||
SGLIB_API bool WriteCache( const char* aFileName, bool overwrite, SGNODE* aNode );
|
||||
SGLIB_API bool WriteCache( const char* aFileName, bool overwrite, SGNODE* aNode,
|
||||
const char* aPluginInfo );
|
||||
|
||||
/**
|
||||
* Function ReadCache
|
||||
|
@ -80,7 +81,8 @@ namespace S3D
|
|||
* if desired this node can be associated with an IFSG_TRANSFORM wrapper via
|
||||
* the IFSG_TRANSFORM::Attach() function.
|
||||
*/
|
||||
SGLIB_API SGNODE* ReadCache( const char* aFileName );
|
||||
SGLIB_API SGNODE* ReadCache( const char* aFileName, void* aPluginMgr,
|
||||
bool (*aTagCheck)( const char*, void* ) );
|
||||
|
||||
/**
|
||||
* Function WriteVRML
|
||||
|
|
|
@ -143,6 +143,11 @@ bool WRL1BASE::Read( WRLPROC& proc )
|
|||
std::string glob;
|
||||
WRL1NODES ntype;
|
||||
|
||||
// Note: according to the VRML1 specification, a file may contain
|
||||
// only one grouping node at the top level. The following code
|
||||
// supports non-conformant VRML1 files by processing all top level
|
||||
// grouping nodes.
|
||||
|
||||
while( proc.ReadName( glob ) )
|
||||
{
|
||||
|
||||
|
@ -728,6 +733,10 @@ SGNODE* WRL1BASE::TranslateToSG( SGNODE* aParent, WRL1STATUS* /*sp*/ )
|
|||
if( m_Items.size() == 1 )
|
||||
return (*m_Items.begin())->TranslateToSG( NULL, NULL );
|
||||
|
||||
// Note: according to the VRML1 specification, a file may contain
|
||||
// only one grouping node at the top level. The following code
|
||||
// supports non-conformant VRML1 files.
|
||||
|
||||
m_current.Init();
|
||||
|
||||
IFSG_TRANSFORM txNode( true );
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* This program source code file is part of KiCad, a free EDA CAD application.
|
||||
*
|
||||
* Copyright (C) 2015 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
* Copyright (C) 2015-2016 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
@ -241,6 +241,16 @@ bool KICAD_PLUGIN_LDR::open( const wxString& aFullFileName, const char* aPluginC
|
|||
#endif
|
||||
|
||||
ok = true;
|
||||
|
||||
// set the plugin info string
|
||||
m_pluginInfo = GetKicadPluginName();
|
||||
std::ostringstream ostr;
|
||||
unsigned char r0, r1, r2, r3;
|
||||
GetVersion( &r0, &r1, &r2, &r3 );
|
||||
ostr << ":" << (unsigned int)r0 << "." << (unsigned int)r1;
|
||||
ostr << "." << (unsigned int)r2 << "." << (unsigned int)r3;
|
||||
m_pluginInfo.append( ostr.str() );
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -452,3 +462,9 @@ bool KICAD_PLUGIN_LDR::GetVersion( unsigned char* Major, unsigned char* Minor,
|
|||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void KICAD_PLUGIN_LDR::GetPluginInfo( std::string& aPluginInfo )
|
||||
{
|
||||
aPluginInfo = m_pluginInfo;
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* This program source code file is part of KiCad, a free EDA CAD application.
|
||||
*
|
||||
* Copyright (C) 2015 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
* Copyright (C) 2015-2016 Cirilo Bernardo <cirilo.bernardo@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
@ -64,6 +64,7 @@ private:
|
|||
GET_VERSION m_getVersion;
|
||||
|
||||
wxString m_fileName; // name of last opened Plugin
|
||||
std::string m_pluginInfo; // Name:Version tag for plugin
|
||||
|
||||
protected:
|
||||
std::string m_error; // error message
|
||||
|
@ -144,6 +145,8 @@ public:
|
|||
// returns false if no plugin is loaded
|
||||
bool GetVersion( unsigned char* Major, unsigned char* Minor,
|
||||
unsigned char* Patch, unsigned char* Revision );
|
||||
|
||||
void GetPluginInfo( std::string& aPluginInfo );
|
||||
};
|
||||
|
||||
#endif // PLUGINLDR_H
|
||||
|
|
Loading…
Reference in New Issue