26#include <wx/filename.h>
39#define SG_VERSION_TAG "VERSION:2"
43std::recursive_mutex modelImportMutex;
49 modelImportMutex.lock();
55 modelImportMutex.unlock();
92 bool reuse,
bool renameNodes )
94 std::lock_guard<std::recursive_mutex> guard( modelImportMutex );
96 if(
nullptr == filename || filename[0] == 0 )
99 wxString ofile = wxString::FromUTF8Unchecked( filename );
101 if( wxFileName::Exists( ofile ) )
107 if( !wxFileName::FileExists( ofile ) )
117 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] failed to open file '%s'" ),
118 __FILE__, __FUNCTION__, __LINE__, filename );
123 op.imbue( std::locale::classic() );
124 op <<
"#VRML V2.0 utf8\n";
142 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] problems encountered writing file '%s'" ),
143 __FILE__, __FUNCTION__, __LINE__, filename );
151 std::lock_guard<std::recursive_mutex> guard( modelImportMutex );
161 std::lock_guard<std::recursive_mutex> guard( modelImportMutex );
178 const char* aPluginInfo )
180 std::lock_guard<std::recursive_mutex> guard( modelImportMutex );
182 if(
nullptr == aFileName || aFileName[0] == 0 )
185 wxString ofile = wxString::FromUTF8Unchecked( aFileName );
187 wxCHECK( aNode,
false );
189 if( wxFileName::Exists( ofile ) )
193 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] file exists not overwriting '%s'" ),
194 __FILE__, __FUNCTION__, __LINE__, aFileName );
200 if( !wxFileName::FileExists( aFileName ) )
202 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] specified path is a directory '%s'" ),
203 __FILE__, __FUNCTION__, __LINE__, aFileName );
213 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] failed to open file '%s'" ),
214 __FILE__, __FUNCTION__, __LINE__, aFileName );
221 if(
nullptr != aPluginInfo && aPluginInfo[0] != 0 )
222 output <<
"(" << aPluginInfo <<
")";
224 output <<
"(INTERNAL:0.0.0.0)";
226 bool rval = aNode->
WriteCache( output,
nullptr );
231 wxLogTrace( MASK_3D_SG,
232 wxT(
"%s:%s:%d * [INFO] problems encountered writing cache file '%s'" ),
233 __FILE__, __FUNCTION__, __LINE__, aFileName );
236 wxRemoveFile( ofile );
244 bool (*aTagCheck)(
const char*,
void* ) )
246 std::lock_guard<std::recursive_mutex> guard( modelImportMutex );
248 if(
nullptr == aFileName || aFileName[0] == 0 )
251 wxString ofile = wxString::FromUTF8Unchecked( aFileName );
253 if( !wxFileName::FileExists( aFileName ) )
255 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] no such file '%s'" ),
256 __FILE__, __FUNCTION__, __LINE__, aFileName );
261 std::unique_ptr<SGNODE> np = std::make_unique<SCENEGRAPH>(
nullptr );
267 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] failed to open file '%s'" ),
268 __FILE__, __FUNCTION__, __LINE__, aFileName );
283 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] corrupt data; missing left parenthesis"
284 " at position '%d'" ),
285 __FILE__, __FUNCTION__, __LINE__,
286 static_cast<int>( file.tellg() ) );
294 while(
')' != schar && file.good() )
296 name.push_back( schar );
318 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] corrupt data; missing left parenthesis"
319 " at position '%d'" ),
320 __FILE__, __FUNCTION__, __LINE__,
321 static_cast<int>( file.tellg() ) );
329 while(
')' != schar && file.good() )
331 name.push_back( schar );
336 if(
nullptr != aTagCheck &&
nullptr != aPluginMgr
337 && !aTagCheck(
name.c_str(), aPluginMgr ) )
345 bool rval = np->ReadCache( file,
nullptr );
350 wxLogTrace( MASK_3D_SG, wxT(
"%s:%s:%d * [INFO] problems encountered reading cache file "
352 __FILE__, __FUNCTION__, __LINE__,
364 if(
nullptr == aNode )
371 std::vector< SMESH > meshes;
385 materials.
matorder.push_back( &app );
386 materials.
matmap.emplace( &app, 0 );
388 if( aNode->
Prepare(
nullptr, materials, meshes ) )
396 size_t j = materials.
matorder.size();
399 for(
size_t i = 0; i < j; ++i )
402 model->m_Materials = lmat;
403 model->m_MaterialsSize = j;
409 for(
size_t i = 0; i < j; ++i )
410 lmesh[i] = meshes[i];
412 model->m_Meshes = lmesh;
413 model->m_MeshesSize = j;
418 size_t j = meshes.size();
420 for(
size_t i = 0; i < j; ++i )
429 if(
nullptr == aModel ||
nullptr == *aModel )
472 unsigned char* Revision )
noexcept
490 glm::dvec3 tri = glm::dvec3( 0.0, 0.0, 0.0 );
493 pts[0] = glm::dvec3( p1.
x, p1.
y, p1.
z );
494 pts[1] = glm::dvec3( p2.
x, p2.
y, p2.
z );
495 pts[2] = glm::dvec3( p3.
x, p3.
y, p3.
z );
502 tri = glm::cross( pts[1] - pts[0], pts[2] - pts[0] );
503 (void)glm::normalize( tri );
505 return SGVECTOR( tri.x, tri.y, tri.z );
511 if(
nullptr == aNode )
520 if(
nullptr == aNode )
529 if(
nullptr == aParent ||
nullptr == aChild )
538 if(
nullptr == aParent ||
nullptr == aChild )
547 if(
nullptr == aObject ||
nullptr == aRefPtr || aObject != *aRefPtr )
Define the basic data set required to represent a 3D model.
bool Prepare(const glm::dmat4 *aTransform, S3D::MATLIST &materials, std::vector< SMESH > &meshes)
Defines the generic material appearance of a scenegraph object.
void GetColor(float &aRedVal, float &aGreenVal, float &aBlueVal) const noexcept
The base class of all Scene Graph nodes.
void ResetNodeIndex(void) noexcept
Reset the global SG* node indices in preparation for write operations.
virtual bool WriteCache(std::ostream &aFile, SGNODE *parentNode)=0
Write this node's data to a binary cache file.
virtual bool AddRefNode(SGNODE *aNode)=0
SGNODE * GetParent(void) const noexcept
Returns a pointer to the parent SGNODE of this object or NULL if the object has no parent (ie.
virtual void ReNameNodes(void)=0
Rename a node and all its child nodes in preparation for write operations.
S3D::SGTYPES GetNodeType(void) const noexcept
Return the type of this node instance.
virtual bool AddChildNode(SGNODE *aNode)=0
void AssociateWrapper(SGNODE **aWrapperRef) noexcept
Associate this object with a handle to itself.
virtual bool WriteVRML(std::ostream &aFile, bool aReuseFlag)=0
Writes this node's data to a VRML file.
static void formatMaterial(SMATERIAL &mat, SGAPPEARANCE const *app)
defines the API calls for the manipulation of SG* classes
SGLIB_API void Init3DMaterial(SMATERIAL &aMat)
Initializes an SMATERIAL structure.
void INIT_SMESH(SMESH &aMesh) noexcept
SGLIB_API void UnlockModelImport() noexcept
SGLIB_API void RenameNodes(SGNODE *aNode)
Rename a node and all children nodes based on the current values of the global SG* class indices.
SGLIB_API void Free3DModel(S3DMODEL &aModel)
Free memory used internally by an S3DMODEL structure.
SGLIB_API void Free3DMesh(SMESH &aMesh)
Free memory used internally by an SMESH structure.
SGLIB_API SGNODE * ReadCache(const char *aFileName, void *aPluginMgr, bool(*aTagCheck)(const char *, void *))
Read a binary cache file and creates an SGNODE tree.
SGLIB_API S3D::SGTYPES GetSGNodeType(SGNODE *aNode)
SGLIB_API void Init3DMesh(SMESH &aMesh)
Create and initialize an SMESH structure.
SGLIB_API bool WriteCache(const char *aFileName, bool overwrite, SGNODE *aNode, const char *aPluginInfo)
Write the SGNODE tree to a binary cache file.
SGLIB_API bool WriteVRML(const char *filename, bool overwrite, SGNODE *aTopNode, bool reuse, bool renameNodes)
Write out the given node and its subnodes to a VRML2 file.
void INIT_SMATERIAL(SMATERIAL &aMaterial)
SGLIB_API S3DMODEL * New3DModel(void)
Create and initialize an S3DMODEL structure.
SGLIB_API void ResetNodeIndex(SGNODE *aNode)
Reset the global SG* class indices.
SGLIB_API SGNODE * GetSGNodeParent(SGNODE *aNode)
SGLIB_API SGVECTOR CalcTriNorm(const SGPOINT &p1, const SGPOINT &p2, const SGPOINT &p3)
Return the normal vector of a triangle described by vertices p1, p2, p3.
SGLIB_API void DestroyNode(SGNODE *aNode) noexcept
Delete the given SG* class node.
bool degenerate(glm::dvec3 *pts) noexcept
void FREE_SMESH(SMESH &aMesh) noexcept
void INIT_S3DMODEL(S3DMODEL &aModel) noexcept
SGLIB_API S3DMODEL * GetModel(SCENEGRAPH *aNode)
Create an S3DMODEL representation of aNode (raw data, no transforms).
SGLIB_API bool AddSGNodeChild(SGNODE *aParent, SGNODE *aChild)
void FREE_S3DMODEL(S3DMODEL &aModel)
SGLIB_API void GetLibVersion(unsigned char *Major, unsigned char *Minor, unsigned char *Patch, unsigned char *Revision) noexcept
Retrieve version information of the kicad_3dsg library.
SGLIB_API void AssociateSGNodeWrapper(SGNODE *aObject, SGNODE **aRefPtr)
SGLIB_API bool AddSGNodeRef(SGNODE *aParent, SGNODE *aChild)
SGLIB_API void LockModelImport() noexcept
Serialize parser and scene-name operations.
SGLIB_API void Destroy3DModel(S3DMODEL **aModel)
Free memory used by an S3DMODEL structure and sets the pointer to the structure to NULL.
Define a number of macros to aid in repetitious code which is probably best expressed as a preprocess...
defines the library version of the intermediate scenegraph (SG) implementation
#define KICADSG_VERSION_MAJOR
#define KICADSG_VERSION_REVISION
#define KICADSG_VERSION_PATCH
#define KICADSG_VERSION_MINOR
#define OPEN_OSTREAM(var, name)
#define CLOSE_STREAM(var)
#define OPEN_ISTREAM(var, name)
Store the a model based on meshes and materials.
std::vector< SGAPPEARANCE const * > matorder
std::map< SGAPPEARANCE const *, int > matmap
float m_Transparency
1.0 is completely transparent, 0.0 completely opaque
SFVEC3F m_Diffuse
Default diffuse color if m_Color is NULL.
Per-vertex normal/color/texcoors structure.