Add project template

This commit is contained in:
s473577 2024-01-02 20:54:56 +01:00
parent aa10ba21d2
commit 70b6b74f11
967 changed files with 191566 additions and 0 deletions

224
.gitignore vendored Normal file
View File

@ -0,0 +1,224 @@
## Ignore Visual Studio temporary files, build results, and
## files generated by popular Visual Studio add-ons.
# User-specific files
*.suo
*.user
*.sln.docstates
# Build results
# Roslyn cache directories
*.ide/
# MSTest test Results
[Tt]est[Rr]esult*/
[Bb]uild[Ll]og.*
#NUNIT
*.VisualState.xml
TestResult.xml
# Build Results of an ATL Project
[Dd]ebugPS/
[Rr]eleasePS/
dlldata.c
*_i.c
*_p.c
*_i.h
*.ilk
*.meta
*.obj
*.pch
*.pdb
*.pgc
*.pgd
*.rsp
*.sbr
*.tlb
*.tli
*.tlh
*.tmp
*.tmp_proj
*.log
*.vspscc
*.vssscc
.builds
*.pidb
*.svclog
*.scc
*.idb
*.tlog
*.exe
# Chutzpah Test files
_Chutzpah*
# Visual C++ cache files
ipch/
*.aps
*.ncb
*.opensdf
*.sdf
*.cachefile
# Visual Studio profiler
*.psess
*.vsp
*.vspx
# TFS 2012 Local Workspace
$tf/
# Guidance Automation Toolkit
*.gpState
# ReSharper is a .NET coding add-in
_ReSharper*/
*.[Rr]e[Ss]harper
*.DotSettings.user
# JustCode is a .NET coding addin-in
.JustCode
# TeamCity is a build add-in
_TeamCity*
# DotCover is a Code Coverage Tool
*.dotCover
# NCrunch
_NCrunch_*
.*crunch*.local.xml
# MightyMoose
*.mm.*
AutoTest.Net/
# Web workbench (sass)
.sass-cache/
# Installshield output folder
[Ee]xpress/
# DocProject is a documentation generator add-in
DocProject/buildhelp/
DocProject/Help/*.HxT
DocProject/Help/*.HxC
DocProject/Help/*.hhc
DocProject/Help/*.hhk
DocProject/Help/*.hhp
DocProject/Help/Html2
DocProject/Help/html
# Click-Once directory
publish/
# Publish Web Output
*.[Pp]ublish.xml
*.azurePubxml
# TODO: Comment the next line if you want to checkin your web deploy settings
# but database connection strings (with potential passwords) will be unencrypted
*.pubxml
*.publishproj
# NuGet Packages
*.nupkg
# The packages folder can be ignored because of Package Restore
**/packages/*
# except build/, which is used as an MSBuild target.
!**/packages/build/
# If using the old MSBuild-Integrated Package Restore, uncomment this:
#!**/packages/repositories.config
# Windows Azure Build Output
csx/
*.build.csdef
# Windows Store app package directory
AppPackages/
# Others
sql/
*.Cache
ClientBin/
[Ss]tyle[Cc]op.*
~$*
*~
*.dbmdl
*.dbproj.schemaview
*.pfx
*.publishsettings
node_modules/
# RIA/Silverlight projects
Generated_Code/
# Backup & report files from converting an old project file
# to a newer Visual Studio version. Backup files are not needed,
# because we have git ;-)
_UpgradeReport_Files/
Backup*/
UpgradeLog*.XML
UpgradeLog*.htm
# SQL Server files
*.mdf
*.ldf
# Business Intelligence projects
*.rdl.data
*.bim.layout
*.bim_*.settings
# Microsoft Fakes
FakesAssemblies/
# =========================
# Operating System Files
# =========================
# OSX
# =========================
.DS_Store
.AppleDouble
.LSOverride
# Icon must end with two \r
Icon
# Thumbnails
._*
# Files that might appear on external disk
.Spotlight-V100
.Trashes
# Directories potentially created on remote AFP share
.AppleDB
.AppleDesktop
Network Trash Folder
Temporary Items
.apdisk
# Windows
# =========================
# Windows image file caches
Thumbs.db
ehthumbs.db
# Folder config file
Desktop.ini
# Recycle Bin used on file shares
$RECYCLE.BIN/
# Windows Installer files
*.cab
*.msi
*.msm
*.msp

Binary file not shown.

Binary file not shown.

BIN
grk/assimp-vc141-mt.dll Normal file

Binary file not shown.

BIN
grk/assimp-vc141-mtd.dll Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,8 @@
# See <http://EditorConfig.org> for details
[*.{h,hpp,inl}]
end_of_line = lf
insert_final_newline = true
trim_trailing_whitespace = true
indent_size = 4
indent_style = space

View File

@ -0,0 +1,418 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Definition of the base class for all importer worker classes. */
#ifndef INCLUDED_AI_BASEIMPORTER_H
#define INCLUDED_AI_BASEIMPORTER_H
#include "Exceptional.h"
#include <vector>
#include <set>
#include <map>
#include <assimp/types.h>
#include <assimp/ProgressHandler.hpp>
#include <assimp/ai_assert.h>
struct aiScene;
struct aiImporterDesc;
namespace Assimp {
class Importer;
class IOSystem;
class BaseProcess;
class SharedPostProcessInfo;
class IOStream;
// utility to do char4 to uint32 in a portable manner
#define AI_MAKE_MAGIC(string) ((uint32_t)((string[0] << 24) + \
(string[1] << 16) + (string[2] << 8) + string[3]))
// ---------------------------------------------------------------------------
/** FOR IMPORTER PLUGINS ONLY: The BaseImporter defines a common interface
* for all importer worker classes.
*
* The interface defines two functions: CanRead() is used to check if the
* importer can handle the format of the given file. If an implementation of
* this function returns true, the importer then calls ReadFile() which
* imports the given file. ReadFile is not overridable, it just calls
* InternReadFile() and catches any ImportErrorException that might occur.
*/
class ASSIMP_API BaseImporter {
friend class Importer;
private:
/* Pushes state into importer for the importer scale */
virtual void UpdateImporterScale( Importer* pImp );
public:
/** Constructor to be privately used by #Importer */
BaseImporter() AI_NO_EXCEPT;
/** Destructor, private as well */
virtual ~BaseImporter();
// -------------------------------------------------------------------
/** Returns whether the class can handle the format of the given file.
*
* The implementation should be as quick as possible. A check for
* the file extension is enough. If no suitable loader is found with
* this strategy, CanRead() is called again, the 'checkSig' parameter
* set to true this time. Now the implementation is expected to
* perform a full check of the file structure, possibly searching the
* first bytes of the file for magic identifiers or keywords.
*
* @param pFile Path and file name of the file to be examined.
* @param pIOHandler The IO handler to use for accessing any file.
* @param checkSig Set to true if this method is called a second time.
* This time, the implementation may take more time to examine the
* contents of the file to be loaded for magic bytes, keywords, etc
* to be able to load files with unknown/not existent file extensions.
* @return true if the class can read this file, false if not.
*/
virtual bool CanRead(
const std::string& pFile,
IOSystem* pIOHandler,
bool checkSig
) const = 0;
// -------------------------------------------------------------------
/** Imports the given file and returns the imported data.
* If the import succeeds, ownership of the data is transferred to
* the caller. If the import fails, NULL is returned. The function
* takes care that any partially constructed data is destroyed
* beforehand.
*
* @param pImp #Importer object hosting this loader.
* @param pFile Path of the file to be imported.
* @param pIOHandler IO-Handler used to open this and possible other files.
* @return The imported data or NULL if failed. If it failed a
* human-readable error description can be retrieved by calling
* GetErrorText()
*
* @note This function is not intended to be overridden. Implement
* InternReadFile() to do the import. If an exception is thrown somewhere
* in InternReadFile(), this function will catch it and transform it into
* a suitable response to the caller.
*/
aiScene* ReadFile(
Importer* pImp,
const std::string& pFile,
IOSystem* pIOHandler
);
// -------------------------------------------------------------------
/** Returns the error description of the last error that occurred.
* @return A description of the last error that occurred. An empty
* string if there was no error.
*/
const std::string& GetErrorText() const {
return m_ErrorText;
}
// -------------------------------------------------------------------
/** Called prior to ReadFile().
* The function is a request to the importer to update its configuration
* basing on the Importer's configuration property list.
* @param pImp Importer instance
*/
virtual void SetupProperties(
const Importer* pImp
);
// -------------------------------------------------------------------
/** Called by #Importer::GetImporterInfo to get a description of
* some loader features. Importers must provide this information. */
virtual const aiImporterDesc* GetInfo() const = 0;
/**
* Will be called only by scale process when scaling is requested.
*/
virtual void SetFileScale(double scale)
{
fileScale = scale;
}
virtual double GetFileScale() const
{
return fileScale;
}
enum ImporterUnits {
M,
MM,
CM,
INCHES,
FEET
};
/**
* Assimp Importer
* unit conversions available
* if you need another measurment unit add it below.
* it's currently defined in assimp that we prefer meters.
* */
std::map<ImporterUnits, double> importerUnits = {
{ImporterUnits::M, 1},
{ImporterUnits::CM, 0.01},
{ImporterUnits::MM, 0.001},
{ImporterUnits::INCHES, 0.0254},
{ImporterUnits::FEET, 0.3048}
};
virtual void SetApplicationUnits( const ImporterUnits& unit )
{
importerScale = importerUnits[unit];
applicationUnits = unit;
}
virtual const ImporterUnits& GetApplicationUnits()
{
return applicationUnits;
}
// -------------------------------------------------------------------
/** Called by #Importer::GetExtensionList for each loaded importer.
* Take the extension list contained in the structure returned by
* #GetInfo and insert all file extensions into the given set.
* @param extension set to collect file extensions in*/
void GetExtensionList(std::set<std::string>& extensions);
protected:
ImporterUnits applicationUnits = ImporterUnits::M;
double importerScale = 1.0;
double fileScale = 1.0;
// -------------------------------------------------------------------
/** Imports the given file into the given scene structure. The
* function is expected to throw an ImportErrorException if there is
* an error. If it terminates normally, the data in aiScene is
* expected to be correct. Override this function to implement the
* actual importing.
* <br>
* The output scene must meet the following requirements:<br>
* <ul>
* <li>At least a root node must be there, even if its only purpose
* is to reference one mesh.</li>
* <li>aiMesh::mPrimitiveTypes may be 0. The types of primitives
* in the mesh are determined automatically in this case.</li>
* <li>the vertex data is stored in a pseudo-indexed "verbose" format.
* In fact this means that every vertex that is referenced by
* a face is unique. Or the other way round: a vertex index may
* not occur twice in a single aiMesh.</li>
* <li>aiAnimation::mDuration may be -1. Assimp determines the length
* of the animation automatically in this case as the length of
* the longest animation channel.</li>
* <li>aiMesh::mBitangents may be NULL if tangents and normals are
* given. In this case bitangents are computed as the cross product
* between normal and tangent.</li>
* <li>There needn't be a material. If none is there a default material
* is generated. However, it is recommended practice for loaders
* to generate a default material for yourself that matches the
* default material setting for the file format better than Assimp's
* generic default material. Note that default materials *should*
* be named AI_DEFAULT_MATERIAL_NAME if they're just color-shaded
* or AI_DEFAULT_TEXTURED_MATERIAL_NAME if they define a (dummy)
* texture. </li>
* </ul>
* If the AI_SCENE_FLAGS_INCOMPLETE-Flag is <b>not</b> set:<ul>
* <li> at least one mesh must be there</li>
* <li> there may be no meshes with 0 vertices or faces</li>
* </ul>
* This won't be checked (except by the validation step): Assimp will
* crash if one of the conditions is not met!
*
* @param pFile Path of the file to be imported.
* @param pScene The scene object to hold the imported data.
* NULL is not a valid parameter.
* @param pIOHandler The IO handler to use for any file access.
* NULL is not a valid parameter. */
virtual void InternReadFile(
const std::string& pFile,
aiScene* pScene,
IOSystem* pIOHandler
) = 0;
public: // static utilities
// -------------------------------------------------------------------
/** A utility for CanRead().
*
* The function searches the header of a file for a specific token
* and returns true if this token is found. This works for text
* files only. There is a rudimentary handling of UNICODE files.
* The comparison is case independent.
*
* @param pIOSystem IO System to work with
* @param file File name of the file
* @param tokens List of tokens to search for
* @param numTokens Size of the token array
* @param searchBytes Number of bytes to be searched for the tokens.
*/
static bool SearchFileHeaderForToken(
IOSystem* pIOSystem,
const std::string& file,
const char** tokens,
unsigned int numTokens,
unsigned int searchBytes = 200,
bool tokensSol = false,
bool noAlphaBeforeTokens = false);
// -------------------------------------------------------------------
/** @brief Check whether a file has a specific file extension
* @param pFile Input file
* @param ext0 Extension to check for. Lowercase characters only, no dot!
* @param ext1 Optional second extension
* @param ext2 Optional third extension
* @note Case-insensitive
*/
static bool SimpleExtensionCheck (
const std::string& pFile,
const char* ext0,
const char* ext1 = NULL,
const char* ext2 = NULL);
// -------------------------------------------------------------------
/** @brief Extract file extension from a string
* @param pFile Input file
* @return Extension without trailing dot, all lowercase
*/
static std::string GetExtension (
const std::string& pFile);
// -------------------------------------------------------------------
/** @brief Check whether a file starts with one or more magic tokens
* @param pFile Input file
* @param pIOHandler IO system to be used
* @param magic n magic tokens
* @params num Size of magic
* @param offset Offset from file start where tokens are located
* @param Size of one token, in bytes. Maximally 16 bytes.
* @return true if one of the given tokens was found
*
* @note For convenience, the check is also performed for the
* byte-swapped variant of all tokens (big endian). Only for
* tokens of size 2,4.
*/
static bool CheckMagicToken(
IOSystem* pIOHandler,
const std::string& pFile,
const void* magic,
unsigned int num,
unsigned int offset = 0,
unsigned int size = 4);
// -------------------------------------------------------------------
/** An utility for all text file loaders. It converts a file to our
* UTF8 character set. Errors are reported, but ignored.
*
* @param data File buffer to be converted to UTF8 data. The buffer
* is resized as appropriate. */
static void ConvertToUTF8(
std::vector<char>& data);
// -------------------------------------------------------------------
/** An utility for all text file loaders. It converts a file from our
* UTF8 character set back to ISO-8859-1. Errors are reported, but ignored.
*
* @param data File buffer to be converted from UTF8 to ISO-8859-1. The buffer
* is resized as appropriate. */
static void ConvertUTF8toISO8859_1(
std::string& data);
// -------------------------------------------------------------------
/// @brief Enum to define, if empty files are ok or not.
enum TextFileMode {
ALLOW_EMPTY,
FORBID_EMPTY
};
// -------------------------------------------------------------------
/** Utility for text file loaders which copies the contents of the
* file into a memory buffer and converts it to our UTF8
* representation.
* @param stream Stream to read from.
* @param data Output buffer to be resized and filled with the
* converted text file data. The buffer is terminated with
* a binary 0.
* @param mode Whether it is OK to load empty text files. */
static void TextFileToBuffer(
IOStream* stream,
std::vector<char>& data,
TextFileMode mode = FORBID_EMPTY);
// -------------------------------------------------------------------
/** Utility function to move a std::vector into a aiScene array
* @param vec The vector to be moved
* @param out The output pointer to the allocated array.
* @param numOut The output count of elements copied. */
template<typename T>
AI_FORCE_INLINE
static void CopyVector(
std::vector<T>& vec,
T*& out,
unsigned int& outLength)
{
outLength = unsigned(vec.size());
if (outLength) {
out = new T[outLength];
std::swap_ranges(vec.begin(), vec.end(), out);
}
}
protected:
/// Error description in case there was one.
std::string m_ErrorText;
/// Currently set progress handler.
ProgressHandler* m_progress;
};
} // end of namespace Assimp
#endif // AI_BASEIMPORTER_H_INC

View File

@ -0,0 +1,125 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Bitmap.h
* @brief Defines bitmap format helper for textures
*
* Used for file formats which embed their textures into the model file.
*/
#ifndef AI_BITMAP_H_INC
#define AI_BITMAP_H_INC
#include "defs.h"
#include <stdint.h>
#include <cstddef>
struct aiTexture;
namespace Assimp {
class IOStream;
class ASSIMP_API Bitmap {
protected:
struct Header {
uint16_t type;
uint32_t size;
uint16_t reserved1;
uint16_t reserved2;
uint32_t offset;
// We define the struct size because sizeof(Header) might return a wrong result because of structure padding.
// Moreover, we must use this ugly and error prone syntax because Visual Studio neither support constexpr or sizeof(name_of_field).
static const std::size_t header_size =
sizeof(uint16_t) + // type
sizeof(uint32_t) + // size
sizeof(uint16_t) + // reserved1
sizeof(uint16_t) + // reserved2
sizeof(uint32_t); // offset
};
struct DIB {
uint32_t size;
int32_t width;
int32_t height;
uint16_t planes;
uint16_t bits_per_pixel;
uint32_t compression;
uint32_t image_size;
int32_t x_resolution;
int32_t y_resolution;
uint32_t nb_colors;
uint32_t nb_important_colors;
// We define the struct size because sizeof(DIB) might return a wrong result because of structure padding.
// Moreover, we must use this ugly and error prone syntax because Visual Studio neither support constexpr or sizeof(name_of_field).
static const std::size_t dib_size =
sizeof(uint32_t) + // size
sizeof(int32_t) + // width
sizeof(int32_t) + // height
sizeof(uint16_t) + // planes
sizeof(uint16_t) + // bits_per_pixel
sizeof(uint32_t) + // compression
sizeof(uint32_t) + // image_size
sizeof(int32_t) + // x_resolution
sizeof(int32_t) + // y_resolution
sizeof(uint32_t) + // nb_colors
sizeof(uint32_t); // nb_important_colors
};
static const std::size_t mBytesPerPixel = 4;
public:
static void Save(aiTexture* texture, IOStream* file);
protected:
static void WriteHeader(Header& header, IOStream* file);
static void WriteDIB(DIB& dib, IOStream* file);
static void WriteData(aiTexture* texture, IOStream* file);
};
}
#endif // AI_BITMAP_H_INC

View File

@ -0,0 +1,338 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Provides cheat implementations for IOSystem and IOStream to
* redirect exporter output to a blob chain.*/
#ifndef AI_BLOBIOSYSTEM_H_INCLUDED
#define AI_BLOBIOSYSTEM_H_INCLUDED
#include <assimp/IOStream.hpp>
#include <assimp/cexport.h>
#include <assimp/IOSystem.hpp>
#include <assimp/DefaultLogger.hpp>
#include <stdint.h>
#include <set>
#include <vector>
namespace Assimp {
class BlobIOSystem;
// --------------------------------------------------------------------------------------------
/** Redirect IOStream to a blob */
// --------------------------------------------------------------------------------------------
class BlobIOStream : public IOStream
{
public:
BlobIOStream(BlobIOSystem* creator, const std::string& file, size_t initial = 4096)
: buffer()
, cur_size()
, file_size()
, cursor()
, initial(initial)
, file(file)
, creator(creator)
{
}
virtual ~BlobIOStream();
public:
// -------------------------------------------------------------------
aiExportDataBlob* GetBlob()
{
aiExportDataBlob* blob = new aiExportDataBlob();
blob->size = file_size;
blob->data = buffer;
buffer = NULL;
return blob;
}
public:
// -------------------------------------------------------------------
virtual size_t Read( void *,
size_t,
size_t )
{
return 0;
}
// -------------------------------------------------------------------
virtual size_t Write(const void* pvBuffer,
size_t pSize,
size_t pCount)
{
pSize *= pCount;
if (cursor + pSize > cur_size) {
Grow(cursor + pSize);
}
memcpy(buffer+cursor, pvBuffer, pSize);
cursor += pSize;
file_size = std::max(file_size,cursor);
return pCount;
}
// -------------------------------------------------------------------
virtual aiReturn Seek(size_t pOffset,
aiOrigin pOrigin)
{
switch(pOrigin)
{
case aiOrigin_CUR:
cursor += pOffset;
break;
case aiOrigin_END:
cursor = file_size - pOffset;
break;
case aiOrigin_SET:
cursor = pOffset;
break;
default:
return AI_FAILURE;
}
if (cursor > file_size) {
Grow(cursor);
}
file_size = std::max(cursor,file_size);
return AI_SUCCESS;
}
// -------------------------------------------------------------------
virtual size_t Tell() const
{
return cursor;
}
// -------------------------------------------------------------------
virtual size_t FileSize() const
{
return file_size;
}
// -------------------------------------------------------------------
virtual void Flush()
{
// ignore
}
private:
// -------------------------------------------------------------------
void Grow(size_t need = 0)
{
// 1.5 and phi are very heap-friendly growth factors (the first
// allows for frequent re-use of heap blocks, the second
// forms a fibonacci sequence with similar characteristics -
// since this heavily depends on the heap implementation
// and other factors as well, i'll just go with 1.5 since
// it is quicker to compute).
size_t new_size = std::max(initial, std::max( need, cur_size+(cur_size>>1) ));
const uint8_t* const old = buffer;
buffer = new uint8_t[new_size];
if (old) {
memcpy(buffer,old,cur_size);
delete[] old;
}
cur_size = new_size;
}
private:
uint8_t* buffer;
size_t cur_size,file_size, cursor, initial;
const std::string file;
BlobIOSystem* const creator;
};
#define AI_BLOBIO_MAGIC "$blobfile"
// --------------------------------------------------------------------------------------------
/** Redirect IOSystem to a blob */
// --------------------------------------------------------------------------------------------
class BlobIOSystem : public IOSystem
{
friend class BlobIOStream;
typedef std::pair<std::string, aiExportDataBlob*> BlobEntry;
public:
BlobIOSystem()
{
}
virtual ~BlobIOSystem()
{
for(BlobEntry& blobby : blobs) {
delete blobby.second;
}
}
public:
// -------------------------------------------------------------------
const char* GetMagicFileName() const
{
return AI_BLOBIO_MAGIC;
}
// -------------------------------------------------------------------
aiExportDataBlob* GetBlobChain()
{
// one must be the master
aiExportDataBlob* master = NULL, *cur;
for(const BlobEntry& blobby : blobs) {
if (blobby.first == AI_BLOBIO_MAGIC) {
master = blobby.second;
break;
}
}
if (!master) {
ASSIMP_LOG_ERROR("BlobIOSystem: no data written or master file was not closed properly.");
return NULL;
}
master->name.Set("");
cur = master;
for(const BlobEntry& blobby : blobs) {
if (blobby.second == master) {
continue;
}
cur->next = blobby.second;
cur = cur->next;
// extract the file extension from the file written
const std::string::size_type s = blobby.first.find_first_of('.');
cur->name.Set(s == std::string::npos ? blobby.first : blobby.first.substr(s+1));
}
// give up blob ownership
blobs.clear();
return master;
}
public:
// -------------------------------------------------------------------
virtual bool Exists( const char* pFile) const {
return created.find(std::string(pFile)) != created.end();
}
// -------------------------------------------------------------------
virtual char getOsSeparator() const {
return '/';
}
// -------------------------------------------------------------------
virtual IOStream* Open(const char* pFile,
const char* pMode)
{
if (pMode[0] != 'w') {
return NULL;
}
created.insert(std::string(pFile));
return new BlobIOStream(this,std::string(pFile));
}
// -------------------------------------------------------------------
virtual void Close( IOStream* pFile)
{
delete pFile;
}
private:
// -------------------------------------------------------------------
void OnDestruct(const std::string& filename, BlobIOStream* child)
{
// we don't know in which the files are closed, so we
// can't reliably say that the first must be the master
// file ...
blobs.push_back( BlobEntry(filename,child->GetBlob()) );
}
private:
std::set<std::string> created;
std::vector< BlobEntry > blobs;
};
// --------------------------------------------------------------------------------------------
BlobIOStream :: ~BlobIOStream()
{
creator->OnDestruct(file,this);
delete[] buffer;
}
} // end Assimp
#endif

View File

@ -0,0 +1,287 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Helper class tp perform various byte oder swappings
(e.g. little to big endian) */
#ifndef AI_BYTESWAPPER_H_INC
#define AI_BYTESWAPPER_H_INC
#include <assimp/ai_assert.h>
#include <assimp/types.h>
#include <stdint.h>
#if _MSC_VER >= 1400
#include <stdlib.h>
#endif
namespace Assimp {
// --------------------------------------------------------------------------------------
/** Defines some useful byte order swap routines.
*
* This is required to read big-endian model formats on little-endian machines,
* and vice versa. Direct use of this class is DEPRECATED. Use #StreamReader instead. */
// --------------------------------------------------------------------------------------
class ByteSwap {
ByteSwap() AI_NO_EXCEPT {}
public:
// ----------------------------------------------------------------------
/** Swap two bytes of data
* @param[inout] _szOut A void* to save the reintcasts for the caller. */
static inline void Swap2(void* _szOut)
{
ai_assert(_szOut);
#if _MSC_VER >= 1400
uint16_t* const szOut = reinterpret_cast<uint16_t*>(_szOut);
*szOut = _byteswap_ushort(*szOut);
#else
uint8_t* const szOut = reinterpret_cast<uint8_t*>(_szOut);
std::swap(szOut[0],szOut[1]);
#endif
}
// ----------------------------------------------------------------------
/** Swap four bytes of data
* @param[inout] _szOut A void* to save the reintcasts for the caller. */
static inline void Swap4(void* _szOut)
{
ai_assert(_szOut);
#if _MSC_VER >= 1400
uint32_t* const szOut = reinterpret_cast<uint32_t*>(_szOut);
*szOut = _byteswap_ulong(*szOut);
#else
uint8_t* const szOut = reinterpret_cast<uint8_t*>(_szOut);
std::swap(szOut[0],szOut[3]);
std::swap(szOut[1],szOut[2]);
#endif
}
// ----------------------------------------------------------------------
/** Swap eight bytes of data
* @param[inout] _szOut A void* to save the reintcasts for the caller. */
static inline void Swap8(void* _szOut)
{
ai_assert(_szOut);
#if _MSC_VER >= 1400
uint64_t* const szOut = reinterpret_cast<uint64_t*>(_szOut);
*szOut = _byteswap_uint64(*szOut);
#else
uint8_t* const szOut = reinterpret_cast<uint8_t*>(_szOut);
std::swap(szOut[0],szOut[7]);
std::swap(szOut[1],szOut[6]);
std::swap(szOut[2],szOut[5]);
std::swap(szOut[3],szOut[4]);
#endif
}
// ----------------------------------------------------------------------
/** ByteSwap a float. Not a joke.
* @param[inout] fOut ehm. .. */
static inline void Swap(float* fOut) {
Swap4(fOut);
}
// ----------------------------------------------------------------------
/** ByteSwap a double. Not a joke.
* @param[inout] fOut ehm. .. */
static inline void Swap(double* fOut) {
Swap8(fOut);
}
// ----------------------------------------------------------------------
/** ByteSwap an int16t. Not a joke.
* @param[inout] fOut ehm. .. */
static inline void Swap(int16_t* fOut) {
Swap2(fOut);
}
static inline void Swap(uint16_t* fOut) {
Swap2(fOut);
}
// ----------------------------------------------------------------------
/** ByteSwap an int32t. Not a joke.
* @param[inout] fOut ehm. .. */
static inline void Swap(int32_t* fOut){
Swap4(fOut);
}
static inline void Swap(uint32_t* fOut){
Swap4(fOut);
}
// ----------------------------------------------------------------------
/** ByteSwap an int64t. Not a joke.
* @param[inout] fOut ehm. .. */
static inline void Swap(int64_t* fOut) {
Swap8(fOut);
}
static inline void Swap(uint64_t* fOut) {
Swap8(fOut);
}
// ----------------------------------------------------------------------
//! Templatized ByteSwap
//! \returns param tOut as swapped
template<typename Type>
static inline Type Swapped(Type tOut)
{
return _swapper<Type,sizeof(Type)>()(tOut);
}
private:
template <typename T, size_t size> struct _swapper;
};
template <typename T> struct ByteSwap::_swapper<T,2> {
T operator() (T tOut) {
Swap2(&tOut);
return tOut;
}
};
template <typename T> struct ByteSwap::_swapper<T,4> {
T operator() (T tOut) {
Swap4(&tOut);
return tOut;
}
};
template <typename T> struct ByteSwap::_swapper<T,8> {
T operator() (T tOut) {
Swap8(&tOut);
return tOut;
}
};
// --------------------------------------------------------------------------------------
// ByteSwap macros for BigEndian/LittleEndian support
// --------------------------------------------------------------------------------------
#if (defined AI_BUILD_BIG_ENDIAN)
# define AI_LE(t) (t)
# define AI_BE(t) ByteSwap::Swapped(t)
# define AI_LSWAP2(p)
# define AI_LSWAP4(p)
# define AI_LSWAP8(p)
# define AI_LSWAP2P(p)
# define AI_LSWAP4P(p)
# define AI_LSWAP8P(p)
# define LE_NCONST const
# define AI_SWAP2(p) ByteSwap::Swap2(&(p))
# define AI_SWAP4(p) ByteSwap::Swap4(&(p))
# define AI_SWAP8(p) ByteSwap::Swap8(&(p))
# define AI_SWAP2P(p) ByteSwap::Swap2((p))
# define AI_SWAP4P(p) ByteSwap::Swap4((p))
# define AI_SWAP8P(p) ByteSwap::Swap8((p))
# define BE_NCONST
#else
# define AI_BE(t) (t)
# define AI_LE(t) ByteSwap::Swapped(t)
# define AI_SWAP2(p)
# define AI_SWAP4(p)
# define AI_SWAP8(p)
# define AI_SWAP2P(p)
# define AI_SWAP4P(p)
# define AI_SWAP8P(p)
# define BE_NCONST const
# define AI_LSWAP2(p) ByteSwap::Swap2(&(p))
# define AI_LSWAP4(p) ByteSwap::Swap4(&(p))
# define AI_LSWAP8(p) ByteSwap::Swap8(&(p))
# define AI_LSWAP2P(p) ByteSwap::Swap2((p))
# define AI_LSWAP4P(p) ByteSwap::Swap4((p))
# define AI_LSWAP8P(p) ByteSwap::Swap8((p))
# define LE_NCONST
#endif
namespace Intern {
// --------------------------------------------------------------------------------------------
template <typename T, bool doit>
struct ByteSwapper {
void operator() (T* inout) {
ByteSwap::Swap(inout);
}
};
template <typename T>
struct ByteSwapper<T,false> {
void operator() (T*) {
}
};
// --------------------------------------------------------------------------------------------
template <bool SwapEndianess, typename T, bool RuntimeSwitch>
struct Getter {
void operator() (T* inout, bool le) {
#ifdef AI_BUILD_BIG_ENDIAN
le = le;
#else
le = !le;
#endif
if (le) {
ByteSwapper<T,(sizeof(T)>1?true:false)> () (inout);
}
else ByteSwapper<T,false> () (inout);
}
};
template <bool SwapEndianess, typename T>
struct Getter<SwapEndianess,T,false> {
void operator() (T* inout, bool /*le*/) {
// static branch
ByteSwapper<T,(SwapEndianess && sizeof(T)>1)> () (inout);
}
};
} // end Intern
} // end Assimp
#endif //!! AI_BYTESWAPPER_H_INC

View File

@ -0,0 +1,22 @@
// ===============================================================================
// May be included multiple times - resets structure packing to the defaults
// for all supported compilers. Reverts the changes made by #include <pushpack1.h>
//
// Currently this works on the following compilers:
// MSVC 7,8,9
// GCC
// BORLAND (complains about 'pack state changed but not reverted', but works)
// ===============================================================================
#ifndef AI_PUSHPACK_IS_DEFINED
# error pushpack1.h must be included after poppack1.h
#endif
// reset packing to the original value
#if defined(_MSC_VER) || defined(__BORLANDC__) || defined (__BCPLUSPLUS__)
# pragma pack( pop )
#endif
#undef PACK_STRUCT
#undef AI_PUSHPACK_IS_DEFINED

View File

@ -0,0 +1,912 @@
/* A portable stdint.h
****************************************************************************
* BSD License:
****************************************************************************
*
* Copyright (c) 2005-2016 Paul Hsieh
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
****************************************************************************
*
* Version 0.1.15.4
*
* The ANSI C standard committee, for the C99 standard, specified the
* inclusion of a new standard include file called stdint.h. This is
* a very useful and long desired include file which contains several
* very precise definitions for integer scalar types that is
* critically important for making portable several classes of
* applications including cryptography, hashing, variable length
* integer libraries and so on. But for most developers its likely
* useful just for programming sanity.
*
* The problem is that some compiler vendors chose to ignore the C99
* standard and some older compilers have no opportunity to be updated.
* Because of this situation, simply including stdint.h in your code
* makes it unportable.
*
* So that's what this file is all about. Its an attempt to build a
* single universal include file that works on as many platforms as
* possible to deliver what stdint.h is supposed to. Even compilers
* that already come with stdint.h can use this file instead without
* any loss of functionality. A few things that should be noted about
* this file:
*
* 1) It is not guaranteed to be portable and/or present an identical
* interface on all platforms. The extreme variability of the
* ANSI C standard makes this an impossibility right from the
* very get go. Its really only meant to be useful for the vast
* majority of platforms that possess the capability of
* implementing usefully and precisely defined, standard sized
* integer scalars. Systems which are not intrinsically 2s
* complement may produce invalid constants.
*
* 2) There is an unavoidable use of non-reserved symbols.
*
* 3) Other standard include files are invoked.
*
* 4) This file may come in conflict with future platforms that do
* include stdint.h. The hope is that one or the other can be
* used with no real difference.
*
* 5) In the current version, if your platform can't represent
* int32_t, int16_t and int8_t, it just dumps out with a compiler
* error.
*
* 6) 64 bit integers may or may not be defined. Test for their
* presence with the test: #ifdef INT64_MAX or #ifdef UINT64_MAX.
* Note that this is different from the C99 specification which
* requires the existence of 64 bit support in the compiler. If
* this is not defined for your platform, yet it is capable of
* dealing with 64 bits then it is because this file has not yet
* been extended to cover all of your system's capabilities.
*
* 7) (u)intptr_t may or may not be defined. Test for its presence
* with the test: #ifdef PTRDIFF_MAX. If this is not defined
* for your platform, then it is because this file has not yet
* been extended to cover all of your system's capabilities, not
* because its optional.
*
* 8) The following might not been defined even if your platform is
* capable of defining it:
*
* WCHAR_MIN
* WCHAR_MAX
* (u)int64_t
* PTRDIFF_MIN
* PTRDIFF_MAX
* (u)intptr_t
*
* 9) The following have not been defined:
*
* WINT_MIN
* WINT_MAX
*
* 10) The criteria for defining (u)int_least(*)_t isn't clear,
* except for systems which don't have a type that precisely
* defined 8, 16, or 32 bit types (which this include file does
* not support anyways). Default definitions have been given.
*
* 11) The criteria for defining (u)int_fast(*)_t isn't something I
* would trust to any particular compiler vendor or the ANSI C
* committee. It is well known that "compatible systems" are
* commonly created that have very different performance
* characteristics from the systems they are compatible with,
* especially those whose vendors make both the compiler and the
* system. Default definitions have been given, but its strongly
* recommended that users never use these definitions for any
* reason (they do *NOT* deliver any serious guarantee of
* improved performance -- not in this file, nor any vendor's
* stdint.h).
*
* 12) The following macros:
*
* PRINTF_INTMAX_MODIFIER
* PRINTF_INT64_MODIFIER
* PRINTF_INT32_MODIFIER
* PRINTF_INT16_MODIFIER
* PRINTF_LEAST64_MODIFIER
* PRINTF_LEAST32_MODIFIER
* PRINTF_LEAST16_MODIFIER
* PRINTF_INTPTR_MODIFIER
*
* are strings which have been defined as the modifiers required
* for the "d", "u" and "x" printf formats to correctly output
* (u)intmax_t, (u)int64_t, (u)int32_t, (u)int16_t, (u)least64_t,
* (u)least32_t, (u)least16_t and (u)intptr_t types respectively.
* PRINTF_INTPTR_MODIFIER is not defined for some systems which
* provide their own stdint.h. PRINTF_INT64_MODIFIER is not
* defined if INT64_MAX is not defined. These are an extension
* beyond what C99 specifies must be in stdint.h.
*
* In addition, the following macros are defined:
*
* PRINTF_INTMAX_HEX_WIDTH
* PRINTF_INT64_HEX_WIDTH
* PRINTF_INT32_HEX_WIDTH
* PRINTF_INT16_HEX_WIDTH
* PRINTF_INT8_HEX_WIDTH
* PRINTF_INTMAX_DEC_WIDTH
* PRINTF_INT64_DEC_WIDTH
* PRINTF_INT32_DEC_WIDTH
* PRINTF_INT16_DEC_WIDTH
* PRINTF_UINT8_DEC_WIDTH
* PRINTF_UINTMAX_DEC_WIDTH
* PRINTF_UINT64_DEC_WIDTH
* PRINTF_UINT32_DEC_WIDTH
* PRINTF_UINT16_DEC_WIDTH
* PRINTF_UINT8_DEC_WIDTH
*
* Which specifies the maximum number of characters required to
* print the number of that type in either hexadecimal or decimal.
* These are an extension beyond what C99 specifies must be in
* stdint.h.
*
* Compilers tested (all with 0 warnings at their highest respective
* settings): Borland Turbo C 2.0, WATCOM C/C++ 11.0 (16 bits and 32
* bits), Microsoft Visual C++ 6.0 (32 bit), Microsoft Visual Studio
* .net (VC7), Intel C++ 4.0, GNU gcc v3.3.3
*
* This file should be considered a work in progress. Suggestions for
* improvements, especially those which increase coverage are strongly
* encouraged.
*
* Acknowledgements
*
* The following people have made significant contributions to the
* development and testing of this file:
*
* Chris Howie
* John Steele Scott
* Dave Thorup
* John Dill
* Florian Wobbe
* Christopher Sean Morrison
* Mikkel Fahnoe Jorgensen
*
*/
#include <stddef.h>
#include <limits.h>
#include <signal.h>
/*
* For gcc with _STDINT_H, fill in the PRINTF_INT*_MODIFIER macros, and
* do nothing else. On the Mac OS X version of gcc this is _STDINT_H_.
*/
#if ((defined(__SUNPRO_C) && __SUNPRO_C >= 0x570) || (defined(_MSC_VER) && _MSC_VER >= 1600) || (defined(__STDC__) && __STDC__ && defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) || (defined (__WATCOMC__) && (defined (_STDINT_H_INCLUDED) || __WATCOMC__ >= 1250)) || (defined(__GNUC__) && (__GNUC__ > 3 || defined(_STDINT_H) || defined(_STDINT_H_) || defined (__UINT_FAST64_TYPE__)) )) && !defined (_PSTDINT_H_INCLUDED)
#include <stdint.h>
#define _PSTDINT_H_INCLUDED
# if defined(__GNUC__) && (defined(__x86_64__) || defined(__ppc64__)) && !(defined(__APPLE__) && defined(__MACH__))
# ifndef PRINTF_INT64_MODIFIER
# define PRINTF_INT64_MODIFIER "l"
# endif
# ifndef PRINTF_INT32_MODIFIER
# define PRINTF_INT32_MODIFIER ""
# endif
# else
# ifndef PRINTF_INT64_MODIFIER
# define PRINTF_INT64_MODIFIER "ll"
# endif
# ifndef PRINTF_INT32_MODIFIER
# if (UINT_MAX == UINT32_MAX)
# define PRINTF_INT32_MODIFIER ""
# else
# define PRINTF_INT32_MODIFIER "l"
# endif
# endif
# endif
# ifndef PRINTF_INT16_MODIFIER
# define PRINTF_INT16_MODIFIER "h"
# endif
# ifndef PRINTF_INTMAX_MODIFIER
# define PRINTF_INTMAX_MODIFIER PRINTF_INT64_MODIFIER
# endif
# ifndef PRINTF_INT64_HEX_WIDTH
# define PRINTF_INT64_HEX_WIDTH "16"
# endif
# ifndef PRINTF_UINT64_HEX_WIDTH
# define PRINTF_UINT64_HEX_WIDTH "16"
# endif
# ifndef PRINTF_INT32_HEX_WIDTH
# define PRINTF_INT32_HEX_WIDTH "8"
# endif
# ifndef PRINTF_UINT32_HEX_WIDTH
# define PRINTF_UINT32_HEX_WIDTH "8"
# endif
# ifndef PRINTF_INT16_HEX_WIDTH
# define PRINTF_INT16_HEX_WIDTH "4"
# endif
# ifndef PRINTF_UINT16_HEX_WIDTH
# define PRINTF_UINT16_HEX_WIDTH "4"
# endif
# ifndef PRINTF_INT8_HEX_WIDTH
# define PRINTF_INT8_HEX_WIDTH "2"
# endif
# ifndef PRINTF_UINT8_HEX_WIDTH
# define PRINTF_UINT8_HEX_WIDTH "2"
# endif
# ifndef PRINTF_INT64_DEC_WIDTH
# define PRINTF_INT64_DEC_WIDTH "19"
# endif
# ifndef PRINTF_UINT64_DEC_WIDTH
# define PRINTF_UINT64_DEC_WIDTH "20"
# endif
# ifndef PRINTF_INT32_DEC_WIDTH
# define PRINTF_INT32_DEC_WIDTH "10"
# endif
# ifndef PRINTF_UINT32_DEC_WIDTH
# define PRINTF_UINT32_DEC_WIDTH "10"
# endif
# ifndef PRINTF_INT16_DEC_WIDTH
# define PRINTF_INT16_DEC_WIDTH "5"
# endif
# ifndef PRINTF_UINT16_DEC_WIDTH
# define PRINTF_UINT16_DEC_WIDTH "5"
# endif
# ifndef PRINTF_INT8_DEC_WIDTH
# define PRINTF_INT8_DEC_WIDTH "3"
# endif
# ifndef PRINTF_UINT8_DEC_WIDTH
# define PRINTF_UINT8_DEC_WIDTH "3"
# endif
# ifndef PRINTF_INTMAX_HEX_WIDTH
# define PRINTF_INTMAX_HEX_WIDTH PRINTF_UINT64_HEX_WIDTH
# endif
# ifndef PRINTF_UINTMAX_HEX_WIDTH
# define PRINTF_UINTMAX_HEX_WIDTH PRINTF_UINT64_HEX_WIDTH
# endif
# ifndef PRINTF_INTMAX_DEC_WIDTH
# define PRINTF_INTMAX_DEC_WIDTH PRINTF_UINT64_DEC_WIDTH
# endif
# ifndef PRINTF_UINTMAX_DEC_WIDTH
# define PRINTF_UINTMAX_DEC_WIDTH PRINTF_UINT64_DEC_WIDTH
# endif
/*
* Something really weird is going on with Open Watcom. Just pull some of
* these duplicated definitions from Open Watcom's stdint.h file for now.
*/
# if defined (__WATCOMC__) && __WATCOMC__ >= 1250
# if !defined (INT64_C)
# define INT64_C(x) (x + (INT64_MAX - INT64_MAX))
# endif
# if !defined (UINT64_C)
# define UINT64_C(x) (x + (UINT64_MAX - UINT64_MAX))
# endif
# if !defined (INT32_C)
# define INT32_C(x) (x + (INT32_MAX - INT32_MAX))
# endif
# if !defined (UINT32_C)
# define UINT32_C(x) (x + (UINT32_MAX - UINT32_MAX))
# endif
# if !defined (INT16_C)
# define INT16_C(x) (x)
# endif
# if !defined (UINT16_C)
# define UINT16_C(x) (x)
# endif
# if !defined (INT8_C)
# define INT8_C(x) (x)
# endif
# if !defined (UINT8_C)
# define UINT8_C(x) (x)
# endif
# if !defined (UINT64_MAX)
# define UINT64_MAX 18446744073709551615ULL
# endif
# if !defined (INT64_MAX)
# define INT64_MAX 9223372036854775807LL
# endif
# if !defined (UINT32_MAX)
# define UINT32_MAX 4294967295UL
# endif
# if !defined (INT32_MAX)
# define INT32_MAX 2147483647L
# endif
# if !defined (INTMAX_MAX)
# define INTMAX_MAX INT64_MAX
# endif
# if !defined (INTMAX_MIN)
# define INTMAX_MIN INT64_MIN
# endif
# endif
#endif
/*
* I have no idea what is the truly correct thing to do on older Solaris.
* From some online discussions, this seems to be what is being
* recommended. For people who actually are developing on older Solaris,
* what I would like to know is, does this define all of the relevant
* macros of a complete stdint.h? Remember, in pstdint.h 64 bit is
* considered optional.
*/
#if (defined(__SUNPRO_C) && __SUNPRO_C >= 0x420) && !defined(_PSTDINT_H_INCLUDED)
#include <sys/inttypes.h>
#define _PSTDINT_H_INCLUDED
#endif
#ifndef _PSTDINT_H_INCLUDED
#define _PSTDINT_H_INCLUDED
#ifndef SIZE_MAX
# define SIZE_MAX (~(size_t)0)
#endif
/*
* Deduce the type assignments from limits.h under the assumption that
* integer sizes in bits are powers of 2, and follow the ANSI
* definitions.
*/
#ifndef UINT8_MAX
# define UINT8_MAX 0xff
#endif
#if !defined(uint8_t) && !defined(_UINT8_T) && !defined(vxWorks)
# if (UCHAR_MAX == UINT8_MAX) || defined (S_SPLINT_S)
typedef unsigned char uint8_t;
# define UINT8_C(v) ((uint8_t) v)
# else
# error "Platform not supported"
# endif
#endif
#ifndef INT8_MAX
# define INT8_MAX 0x7f
#endif
#ifndef INT8_MIN
# define INT8_MIN INT8_C(0x80)
#endif
#if !defined(int8_t) && !defined(_INT8_T) && !defined(vxWorks)
# if (SCHAR_MAX == INT8_MAX) || defined (S_SPLINT_S)
typedef signed char int8_t;
# define INT8_C(v) ((int8_t) v)
# else
# error "Platform not supported"
# endif
#endif
#ifndef UINT16_MAX
# define UINT16_MAX 0xffff
#endif
#if !defined(uint16_t) && !defined(_UINT16_T) && !defined(vxWorks)
#if (UINT_MAX == UINT16_MAX) || defined (S_SPLINT_S)
typedef unsigned int uint16_t;
# ifndef PRINTF_INT16_MODIFIER
# define PRINTF_INT16_MODIFIER ""
# endif
# define UINT16_C(v) ((uint16_t) (v))
#elif (USHRT_MAX == UINT16_MAX)
typedef unsigned short uint16_t;
# define UINT16_C(v) ((uint16_t) (v))
# ifndef PRINTF_INT16_MODIFIER
# define PRINTF_INT16_MODIFIER "h"
# endif
#else
#error "Platform not supported"
#endif
#endif
#ifndef INT16_MAX
# define INT16_MAX 0x7fff
#endif
#ifndef INT16_MIN
# define INT16_MIN INT16_C(0x8000)
#endif
#if !defined(int16_t) && !defined(_INT16_T) && !defined(vxWorks)
#if (INT_MAX == INT16_MAX) || defined (S_SPLINT_S)
typedef signed int int16_t;
# define INT16_C(v) ((int16_t) (v))
# ifndef PRINTF_INT16_MODIFIER
# define PRINTF_INT16_MODIFIER ""
# endif
#elif (SHRT_MAX == INT16_MAX)
typedef signed short int16_t;
# define INT16_C(v) ((int16_t) (v))
# ifndef PRINTF_INT16_MODIFIER
# define PRINTF_INT16_MODIFIER "h"
# endif
#else
#error "Platform not supported"
#endif
#endif
#ifndef UINT32_MAX
# define UINT32_MAX (0xffffffffUL)
#endif
#if !defined(uint32_t) && !defined(_UINT32_T) && !defined(vxWorks)
#if (ULONG_MAX == UINT32_MAX) || defined (S_SPLINT_S)
typedef unsigned long uint32_t;
# define UINT32_C(v) v ## UL
# ifndef PRINTF_INT32_MODIFIER
# define PRINTF_INT32_MODIFIER "l"
# endif
#elif (UINT_MAX == UINT32_MAX)
typedef unsigned int uint32_t;
# ifndef PRINTF_INT32_MODIFIER
# define PRINTF_INT32_MODIFIER ""
# endif
# define UINT32_C(v) v ## U
#elif (USHRT_MAX == UINT32_MAX)
typedef unsigned short uint32_t;
# define UINT32_C(v) ((unsigned short) (v))
# ifndef PRINTF_INT32_MODIFIER
# define PRINTF_INT32_MODIFIER ""
# endif
#else
#error "Platform not supported"
#endif
#endif
#ifndef INT32_MAX
# define INT32_MAX (0x7fffffffL)
#endif
#ifndef INT32_MIN
# define INT32_MIN INT32_C(0x80000000)
#endif
#if !defined(int32_t) && !defined(_INT32_T) && !defined(vxWorks)
#if (LONG_MAX == INT32_MAX) || defined (S_SPLINT_S)
typedef signed long int32_t;
# define INT32_C(v) v ## L
# ifndef PRINTF_INT32_MODIFIER
# define PRINTF_INT32_MODIFIER "l"
# endif
#elif (INT_MAX == INT32_MAX)
typedef signed int int32_t;
# define INT32_C(v) v
# ifndef PRINTF_INT32_MODIFIER
# define PRINTF_INT32_MODIFIER ""
# endif
#elif (SHRT_MAX == INT32_MAX)
typedef signed short int32_t;
# define INT32_C(v) ((short) (v))
# ifndef PRINTF_INT32_MODIFIER
# define PRINTF_INT32_MODIFIER ""
# endif
#else
#error "Platform not supported"
#endif
#endif
/*
* The macro stdint_int64_defined is temporarily used to record
* whether or not 64 integer support is available. It must be
* defined for any 64 integer extensions for new platforms that are
* added.
*/
#undef stdint_int64_defined
#if (defined(__STDC__) && defined(__STDC_VERSION__)) || defined (S_SPLINT_S)
# if (__STDC__ && __STDC_VERSION__ >= 199901L) || defined (S_SPLINT_S)
# define stdint_int64_defined
typedef long long int64_t;
typedef unsigned long long uint64_t;
# define UINT64_C(v) v ## ULL
# define INT64_C(v) v ## LL
# ifndef PRINTF_INT64_MODIFIER
# define PRINTF_INT64_MODIFIER "ll"
# endif
# endif
#endif
#if !defined (stdint_int64_defined)
# if defined(__GNUC__) && !defined(vxWorks)
# define stdint_int64_defined
__extension__ typedef long long int64_t;
__extension__ typedef unsigned long long uint64_t;
# define UINT64_C(v) v ## ULL
# define INT64_C(v) v ## LL
# ifndef PRINTF_INT64_MODIFIER
# define PRINTF_INT64_MODIFIER "ll"
# endif
# elif defined(__MWERKS__) || defined (__SUNPRO_C) || defined (__SUNPRO_CC) || defined (__APPLE_CC__) || defined (_LONG_LONG) || defined (_CRAYC) || defined (S_SPLINT_S)
# define stdint_int64_defined
typedef long long int64_t;
typedef unsigned long long uint64_t;
# define UINT64_C(v) v ## ULL
# define INT64_C(v) v ## LL
# ifndef PRINTF_INT64_MODIFIER
# define PRINTF_INT64_MODIFIER "ll"
# endif
# elif (defined(__WATCOMC__) && defined(__WATCOM_INT64__)) || (defined(_MSC_VER) && _INTEGRAL_MAX_BITS >= 64) || (defined (__BORLANDC__) && __BORLANDC__ > 0x460) || defined (__alpha) || defined (__DECC)
# define stdint_int64_defined
typedef __int64 int64_t;
typedef unsigned __int64 uint64_t;
# define UINT64_C(v) v ## UI64
# define INT64_C(v) v ## I64
# ifndef PRINTF_INT64_MODIFIER
# define PRINTF_INT64_MODIFIER "I64"
# endif
# endif
#endif
#if !defined (LONG_LONG_MAX) && defined (INT64_C)
# define LONG_LONG_MAX INT64_C (9223372036854775807)
#endif
#ifndef ULONG_LONG_MAX
# define ULONG_LONG_MAX UINT64_C (18446744073709551615)
#endif
#if !defined (INT64_MAX) && defined (INT64_C)
# define INT64_MAX INT64_C (9223372036854775807)
#endif
#if !defined (INT64_MIN) && defined (INT64_C)
# define INT64_MIN INT64_C (-9223372036854775808)
#endif
#if !defined (UINT64_MAX) && defined (INT64_C)
# define UINT64_MAX UINT64_C (18446744073709551615)
#endif
/*
* Width of hexadecimal for number field.
*/
#ifndef PRINTF_INT64_HEX_WIDTH
# define PRINTF_INT64_HEX_WIDTH "16"
#endif
#ifndef PRINTF_INT32_HEX_WIDTH
# define PRINTF_INT32_HEX_WIDTH "8"
#endif
#ifndef PRINTF_INT16_HEX_WIDTH
# define PRINTF_INT16_HEX_WIDTH "4"
#endif
#ifndef PRINTF_INT8_HEX_WIDTH
# define PRINTF_INT8_HEX_WIDTH "2"
#endif
#ifndef PRINTF_INT64_DEC_WIDTH
# define PRINTF_INT64_DEC_WIDTH "19"
#endif
#ifndef PRINTF_INT32_DEC_WIDTH
# define PRINTF_INT32_DEC_WIDTH "10"
#endif
#ifndef PRINTF_INT16_DEC_WIDTH
# define PRINTF_INT16_DEC_WIDTH "5"
#endif
#ifndef PRINTF_INT8_DEC_WIDTH
# define PRINTF_INT8_DEC_WIDTH "3"
#endif
#ifndef PRINTF_UINT64_DEC_WIDTH
# define PRINTF_UINT64_DEC_WIDTH "20"
#endif
#ifndef PRINTF_UINT32_DEC_WIDTH
# define PRINTF_UINT32_DEC_WIDTH "10"
#endif
#ifndef PRINTF_UINT16_DEC_WIDTH
# define PRINTF_UINT16_DEC_WIDTH "5"
#endif
#ifndef PRINTF_UINT8_DEC_WIDTH
# define PRINTF_UINT8_DEC_WIDTH "3"
#endif
/*
* Ok, lets not worry about 128 bit integers for now. Moore's law says
* we don't need to worry about that until about 2040 at which point
* we'll have bigger things to worry about.
*/
#ifdef stdint_int64_defined
typedef int64_t intmax_t;
typedef uint64_t uintmax_t;
# define INTMAX_MAX INT64_MAX
# define INTMAX_MIN INT64_MIN
# define UINTMAX_MAX UINT64_MAX
# define UINTMAX_C(v) UINT64_C(v)
# define INTMAX_C(v) INT64_C(v)
# ifndef PRINTF_INTMAX_MODIFIER
# define PRINTF_INTMAX_MODIFIER PRINTF_INT64_MODIFIER
# endif
# ifndef PRINTF_INTMAX_HEX_WIDTH
# define PRINTF_INTMAX_HEX_WIDTH PRINTF_INT64_HEX_WIDTH
# endif
# ifndef PRINTF_INTMAX_DEC_WIDTH
# define PRINTF_INTMAX_DEC_WIDTH PRINTF_INT64_DEC_WIDTH
# endif
#else
typedef int32_t intmax_t;
typedef uint32_t uintmax_t;
# define INTMAX_MAX INT32_MAX
# define UINTMAX_MAX UINT32_MAX
# define UINTMAX_C(v) UINT32_C(v)
# define INTMAX_C(v) INT32_C(v)
# ifndef PRINTF_INTMAX_MODIFIER
# define PRINTF_INTMAX_MODIFIER PRINTF_INT32_MODIFIER
# endif
# ifndef PRINTF_INTMAX_HEX_WIDTH
# define PRINTF_INTMAX_HEX_WIDTH PRINTF_INT32_HEX_WIDTH
# endif
# ifndef PRINTF_INTMAX_DEC_WIDTH
# define PRINTF_INTMAX_DEC_WIDTH PRINTF_INT32_DEC_WIDTH
# endif
#endif
/*
* Because this file currently only supports platforms which have
* precise powers of 2 as bit sizes for the default integers, the
* least definitions are all trivial. Its possible that a future
* version of this file could have different definitions.
*/
#ifndef stdint_least_defined
typedef int8_t int_least8_t;
typedef uint8_t uint_least8_t;
typedef int16_t int_least16_t;
typedef uint16_t uint_least16_t;
typedef int32_t int_least32_t;
typedef uint32_t uint_least32_t;
# define PRINTF_LEAST32_MODIFIER PRINTF_INT32_MODIFIER
# define PRINTF_LEAST16_MODIFIER PRINTF_INT16_MODIFIER
# define UINT_LEAST8_MAX UINT8_MAX
# define INT_LEAST8_MAX INT8_MAX
# define UINT_LEAST16_MAX UINT16_MAX
# define INT_LEAST16_MAX INT16_MAX
# define UINT_LEAST32_MAX UINT32_MAX
# define INT_LEAST32_MAX INT32_MAX
# define INT_LEAST8_MIN INT8_MIN
# define INT_LEAST16_MIN INT16_MIN
# define INT_LEAST32_MIN INT32_MIN
# ifdef stdint_int64_defined
typedef int64_t int_least64_t;
typedef uint64_t uint_least64_t;
# define PRINTF_LEAST64_MODIFIER PRINTF_INT64_MODIFIER
# define UINT_LEAST64_MAX UINT64_MAX
# define INT_LEAST64_MAX INT64_MAX
# define INT_LEAST64_MIN INT64_MIN
# endif
#endif
#undef stdint_least_defined
/*
* The ANSI C committee pretending to know or specify anything about
* performance is the epitome of misguided arrogance. The mandate of
* this file is to *ONLY* ever support that absolute minimum
* definition of the fast integer types, for compatibility purposes.
* No extensions, and no attempt to suggest what may or may not be a
* faster integer type will ever be made in this file. Developers are
* warned to stay away from these types when using this or any other
* stdint.h.
*/
typedef int_least8_t int_fast8_t;
typedef uint_least8_t uint_fast8_t;
typedef int_least16_t int_fast16_t;
typedef uint_least16_t uint_fast16_t;
typedef int_least32_t int_fast32_t;
typedef uint_least32_t uint_fast32_t;
#define UINT_FAST8_MAX UINT_LEAST8_MAX
#define INT_FAST8_MAX INT_LEAST8_MAX
#define UINT_FAST16_MAX UINT_LEAST16_MAX
#define INT_FAST16_MAX INT_LEAST16_MAX
#define UINT_FAST32_MAX UINT_LEAST32_MAX
#define INT_FAST32_MAX INT_LEAST32_MAX
#define INT_FAST8_MIN INT_LEAST8_MIN
#define INT_FAST16_MIN INT_LEAST16_MIN
#define INT_FAST32_MIN INT_LEAST32_MIN
#ifdef stdint_int64_defined
typedef int_least64_t int_fast64_t;
typedef uint_least64_t uint_fast64_t;
# define UINT_FAST64_MAX UINT_LEAST64_MAX
# define INT_FAST64_MAX INT_LEAST64_MAX
# define INT_FAST64_MIN INT_LEAST64_MIN
#endif
#undef stdint_int64_defined
/*
* Whatever piecemeal, per compiler thing we can do about the wchar_t
* type limits.
*/
#if defined(__WATCOMC__) || defined(_MSC_VER) || defined (__GNUC__) && !defined(vxWorks)
# include <wchar.h>
# ifndef WCHAR_MIN
# define WCHAR_MIN 0
# endif
# ifndef WCHAR_MAX
# define WCHAR_MAX ((wchar_t)-1)
# endif
#endif
/*
* Whatever piecemeal, per compiler/platform thing we can do about the
* (u)intptr_t types and limits.
*/
#if (defined (_MSC_VER) && defined (_UINTPTR_T_DEFINED)) || defined (_UINTPTR_T)
# define STDINT_H_UINTPTR_T_DEFINED
#endif
#ifndef STDINT_H_UINTPTR_T_DEFINED
# if defined (__alpha__) || defined (__ia64__) || defined (__x86_64__) || defined (_WIN64) || defined (__ppc64__)
# define stdint_intptr_bits 64
# elif defined (__WATCOMC__) || defined (__TURBOC__)
# if defined(__TINY__) || defined(__SMALL__) || defined(__MEDIUM__)
# define stdint_intptr_bits 16
# else
# define stdint_intptr_bits 32
# endif
# elif defined (__i386__) || defined (_WIN32) || defined (WIN32) || defined (__ppc64__)
# define stdint_intptr_bits 32
# elif defined (__INTEL_COMPILER)
/* TODO -- what did Intel do about x86-64? */
# else
/* #error "This platform might not be supported yet" */
# endif
# ifdef stdint_intptr_bits
# define stdint_intptr_glue3_i(a,b,c) a##b##c
# define stdint_intptr_glue3(a,b,c) stdint_intptr_glue3_i(a,b,c)
# ifndef PRINTF_INTPTR_MODIFIER
# define PRINTF_INTPTR_MODIFIER stdint_intptr_glue3(PRINTF_INT,stdint_intptr_bits,_MODIFIER)
# endif
# ifndef PTRDIFF_MAX
# define PTRDIFF_MAX stdint_intptr_glue3(INT,stdint_intptr_bits,_MAX)
# endif
# ifndef PTRDIFF_MIN
# define PTRDIFF_MIN stdint_intptr_glue3(INT,stdint_intptr_bits,_MIN)
# endif
# ifndef UINTPTR_MAX
# define UINTPTR_MAX stdint_intptr_glue3(UINT,stdint_intptr_bits,_MAX)
# endif
# ifndef INTPTR_MAX
# define INTPTR_MAX stdint_intptr_glue3(INT,stdint_intptr_bits,_MAX)
# endif
# ifndef INTPTR_MIN
# define INTPTR_MIN stdint_intptr_glue3(INT,stdint_intptr_bits,_MIN)
# endif
# ifndef INTPTR_C
# define INTPTR_C(x) stdint_intptr_glue3(INT,stdint_intptr_bits,_C)(x)
# endif
# ifndef UINTPTR_C
# define UINTPTR_C(x) stdint_intptr_glue3(UINT,stdint_intptr_bits,_C)(x)
# endif
typedef stdint_intptr_glue3(uint,stdint_intptr_bits,_t) uintptr_t;
typedef stdint_intptr_glue3( int,stdint_intptr_bits,_t) intptr_t;
# else
/* TODO -- This following is likely wrong for some platforms, and does
nothing for the definition of uintptr_t. */
typedef ptrdiff_t intptr_t;
# endif
# define STDINT_H_UINTPTR_T_DEFINED
#endif
/*
* Assumes sig_atomic_t is signed and we have a 2s complement machine.
*/
#ifndef SIG_ATOMIC_MAX
# define SIG_ATOMIC_MAX ((((sig_atomic_t) 1) << (sizeof (sig_atomic_t)*CHAR_BIT-1)) - 1)
#endif
#endif
#if defined (__TEST_PSTDINT_FOR_CORRECTNESS)
/*
* Please compile with the maximum warning settings to make sure macros are
* not defined more than once.
*/
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#define glue3_aux(x,y,z) x ## y ## z
#define glue3(x,y,z) glue3_aux(x,y,z)
#define DECLU(bits) glue3(uint,bits,_t) glue3(u,bits,) = glue3(UINT,bits,_C) (0);
#define DECLI(bits) glue3(int,bits,_t) glue3(i,bits,) = glue3(INT,bits,_C) (0);
#define DECL(us,bits) glue3(DECL,us,) (bits)
#define TESTUMAX(bits) glue3(u,bits,) = ~glue3(u,bits,); if (glue3(UINT,bits,_MAX) != glue3(u,bits,)) printf ("Something wrong with UINT%d_MAX\n", bits)
#define REPORTERROR(msg) { err_n++; if (err_first <= 0) err_first = __LINE__; printf msg; }
int main () {
int err_n = 0;
int err_first = 0;
DECL(I,8)
DECL(U,8)
DECL(I,16)
DECL(U,16)
DECL(I,32)
DECL(U,32)
#ifdef INT64_MAX
DECL(I,64)
DECL(U,64)
#endif
intmax_t imax = INTMAX_C(0);
uintmax_t umax = UINTMAX_C(0);
char str0[256], str1[256];
sprintf (str0, "%" PRINTF_INT32_MODIFIER "d", INT32_C(2147483647));
if (0 != strcmp (str0, "2147483647")) REPORTERROR (("Something wrong with PRINTF_INT32_MODIFIER : %s\n", str0));
if (atoi(PRINTF_INT32_DEC_WIDTH) != (int) strlen(str0)) REPORTERROR (("Something wrong with PRINTF_INT32_DEC_WIDTH : %s\n", PRINTF_INT32_DEC_WIDTH));
sprintf (str0, "%" PRINTF_INT32_MODIFIER "u", UINT32_C(4294967295));
if (0 != strcmp (str0, "4294967295")) REPORTERROR (("Something wrong with PRINTF_INT32_MODIFIER : %s\n", str0));
if (atoi(PRINTF_UINT32_DEC_WIDTH) != (int) strlen(str0)) REPORTERROR (("Something wrong with PRINTF_UINT32_DEC_WIDTH : %s\n", PRINTF_UINT32_DEC_WIDTH));
#ifdef INT64_MAX
sprintf (str1, "%" PRINTF_INT64_MODIFIER "d", INT64_C(9223372036854775807));
if (0 != strcmp (str1, "9223372036854775807")) REPORTERROR (("Something wrong with PRINTF_INT32_MODIFIER : %s\n", str1));
if (atoi(PRINTF_INT64_DEC_WIDTH) != (int) strlen(str1)) REPORTERROR (("Something wrong with PRINTF_INT64_DEC_WIDTH : %s, %d\n", PRINTF_INT64_DEC_WIDTH, (int) strlen(str1)));
sprintf (str1, "%" PRINTF_INT64_MODIFIER "u", UINT64_C(18446744073709550591));
if (0 != strcmp (str1, "18446744073709550591")) REPORTERROR (("Something wrong with PRINTF_INT32_MODIFIER : %s\n", str1));
if (atoi(PRINTF_UINT64_DEC_WIDTH) != (int) strlen(str1)) REPORTERROR (("Something wrong with PRINTF_UINT64_DEC_WIDTH : %s, %d\n", PRINTF_UINT64_DEC_WIDTH, (int) strlen(str1)));
#endif
sprintf (str0, "%d %x\n", 0, ~0);
sprintf (str1, "%d %x\n", i8, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with i8 : %s\n", str1));
sprintf (str1, "%u %x\n", u8, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with u8 : %s\n", str1));
sprintf (str1, "%d %x\n", i16, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with i16 : %s\n", str1));
sprintf (str1, "%u %x\n", u16, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with u16 : %s\n", str1));
sprintf (str1, "%" PRINTF_INT32_MODIFIER "d %x\n", i32, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with i32 : %s\n", str1));
sprintf (str1, "%" PRINTF_INT32_MODIFIER "u %x\n", u32, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with u32 : %s\n", str1));
#ifdef INT64_MAX
sprintf (str1, "%" PRINTF_INT64_MODIFIER "d %x\n", i64, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with i64 : %s\n", str1));
#endif
sprintf (str1, "%" PRINTF_INTMAX_MODIFIER "d %x\n", imax, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with imax : %s\n", str1));
sprintf (str1, "%" PRINTF_INTMAX_MODIFIER "u %x\n", umax, ~0);
if (0 != strcmp (str0, str1)) REPORTERROR (("Something wrong with umax : %s\n", str1));
TESTUMAX(8);
TESTUMAX(16);
TESTUMAX(32);
#ifdef INT64_MAX
TESTUMAX(64);
#endif
#define STR(v) #v
#define Q(v) printf ("sizeof " STR(v) " = %u\n", (unsigned) sizeof (v));
if (err_n) {
printf ("pstdint.h is not correct. Please use sizes below to correct it:\n");
}
Q(int)
Q(unsigned)
Q(long int)
Q(short int)
Q(int8_t)
Q(int16_t)
Q(int32_t)
#ifdef INT64_MAX
Q(int64_t)
#endif
return EXIT_SUCCESS;
}
#endif

View File

@ -0,0 +1,43 @@
// ===============================================================================
// May be included multiple times - sets structure packing to 1
// for all supported compilers. #include <poppack1.h> reverts the changes.
//
// Currently this works on the following compilers:
// MSVC 7,8,9
// GCC
// BORLAND (complains about 'pack state changed but not reverted', but works)
// Clang
//
//
// USAGE:
//
// struct StructToBePacked {
// } PACK_STRUCT;
//
// ===============================================================================
#ifdef AI_PUSHPACK_IS_DEFINED
# error poppack1.h must be included after pushpack1.h
#endif
#if defined(_MSC_VER) || defined(__BORLANDC__) || defined (__BCPLUSPLUS__)
# pragma pack(push,1)
# define PACK_STRUCT
#elif defined( __GNUC__ ) || defined(__clang__)
# if !defined(HOST_MINGW)
# define PACK_STRUCT __attribute__((__packed__))
# else
# define PACK_STRUCT __attribute__((gcc_struct, __packed__))
# endif
#else
# error Compiler not supported
#endif
#if defined(_MSC_VER)
// C4103: Packing was changed after the inclusion of the header, probably missing #pragma pop
# pragma warning (disable : 4103)
#endif
#define AI_PUSHPACK_IS_DEFINED

View File

@ -0,0 +1,58 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file CreateAnimMesh.h
* Create AnimMesh from Mesh
*/
#ifndef INCLUDED_AI_CREATE_ANIM_MESH_H
#define INCLUDED_AI_CREATE_ANIM_MESH_H
#include <assimp/mesh.h>
namespace Assimp {
/** Create aiAnimMesh from aiMesh. */
ASSIMP_API aiAnimMesh *aiCreateAnimMesh(const aiMesh *mesh);
} // end of namespace Assimp
#endif // INCLUDED_AI_CREATE_ANIM_MESH_H

View File

@ -0,0 +1,140 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Default file I/O using fXXX()-family of functions */
#ifndef AI_DEFAULTIOSTREAM_H_INC
#define AI_DEFAULTIOSTREAM_H_INC
#include <stdio.h>
#include <assimp/IOStream.hpp>
#include <assimp/importerdesc.h>
#include <assimp/Defines.h>
namespace Assimp {
// ----------------------------------------------------------------------------------
//! @class DefaultIOStream
//! @brief Default IO implementation, use standard IO operations
//! @note An instance of this class can exist without a valid file handle
//! attached to it. All calls fail, but the instance can nevertheless be
//! used with no restrictions.
class ASSIMP_API DefaultIOStream : public IOStream
{
friend class DefaultIOSystem;
#if __ANDROID__
# if __ANDROID_API__ > 9
# if defined(AI_CONFIG_ANDROID_JNI_ASSIMP_MANAGER_SUPPORT)
friend class AndroidJNIIOSystem;
# endif // defined(AI_CONFIG_ANDROID_JNI_ASSIMP_MANAGER_SUPPORT)
# endif // __ANDROID_API__ > 9
#endif // __ANDROID__
protected:
DefaultIOStream() AI_NO_EXCEPT;
DefaultIOStream(FILE* pFile, const std::string &strFilename);
public:
/** Destructor public to allow simple deletion to close the file. */
~DefaultIOStream ();
// -------------------------------------------------------------------
/// Read from stream
size_t Read(void* pvBuffer,
size_t pSize,
size_t pCount);
// -------------------------------------------------------------------
/// Write to stream
size_t Write(const void* pvBuffer,
size_t pSize,
size_t pCount);
// -------------------------------------------------------------------
/// Seek specific position
aiReturn Seek(size_t pOffset,
aiOrigin pOrigin);
// -------------------------------------------------------------------
/// Get current seek position
size_t Tell() const;
// -------------------------------------------------------------------
/// Get size of file
size_t FileSize() const;
// -------------------------------------------------------------------
/// Flush file contents
void Flush();
private:
// File data-structure, using clib
FILE* mFile;
// Filename
std::string mFilename;
// Cached file size
mutable size_t mCachedSize;
};
// ----------------------------------------------------------------------------------
inline
DefaultIOStream::DefaultIOStream() AI_NO_EXCEPT
: mFile(nullptr)
, mFilename("")
, mCachedSize(SIZE_MAX) {
// empty
}
// ----------------------------------------------------------------------------------
inline
DefaultIOStream::DefaultIOStream (FILE* pFile, const std::string &strFilename)
: mFile(pFile)
, mFilename(strFilename)
, mCachedSize(SIZE_MAX) {
// empty
}
// ----------------------------------------------------------------------------------
} // ns assimp
#endif //!!AI_DEFAULTIOSTREAM_H_INC

View File

@ -0,0 +1,93 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Default implementation of IOSystem using the standard C file functions */
#ifndef AI_DEFAULTIOSYSTEM_H_INC
#define AI_DEFAULTIOSYSTEM_H_INC
#include <assimp/IOSystem.hpp>
namespace Assimp {
// ---------------------------------------------------------------------------
/** Default implementation of IOSystem using the standard C file functions */
class ASSIMP_API DefaultIOSystem : public IOSystem {
public:
// -------------------------------------------------------------------
/** Tests for the existence of a file at the given path. */
bool Exists( const char* pFile) const;
// -------------------------------------------------------------------
/** Returns the directory separator. */
char getOsSeparator() const;
// -------------------------------------------------------------------
/** Open a new file with a given path. */
IOStream* Open( const char* pFile, const char* pMode = "rb");
// -------------------------------------------------------------------
/** Closes the given file and releases all resources associated with it. */
void Close( IOStream* pFile);
// -------------------------------------------------------------------
/** Compare two paths */
bool ComparePaths (const char* one, const char* second) const;
/** @brief get the file name of a full filepath
* example: /tmp/archive.tar.gz -> archive.tar.gz
*/
static std::string fileName( const std::string &path );
/** @brief get the complete base name of a full filepath
* example: /tmp/archive.tar.gz -> archive.tar
*/
static std::string completeBaseName( const std::string &path);
/** @brief get the path of a full filepath
* example: /tmp/archive.tar.gz -> /tmp/
*/
static std::string absolutePath( const std::string &path);
};
} //!ns Assimp
#endif //AI_DEFAULTIOSYSTEM_H_INC

View File

@ -0,0 +1,188 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file DefaultLogger.hpp
*/
#ifndef INCLUDED_AI_DEFAULTLOGGER
#define INCLUDED_AI_DEFAULTLOGGER
#include "Logger.hpp"
#include "LogStream.hpp"
#include "NullLogger.hpp"
#include <vector>
namespace Assimp {
// ------------------------------------------------------------------------------------
class IOStream;
struct LogStreamInfo;
/** default name of logfile */
#define ASSIMP_DEFAULT_LOG_NAME "AssimpLog.txt"
// ------------------------------------------------------------------------------------
/** @brief CPP-API: Primary logging facility of Assimp.
*
* The library stores its primary #Logger as a static member of this class.
* #get() returns this primary logger. By default the underlying implementation is
* just a #NullLogger which rejects all log messages. By calling #create(), logging
* is turned on. To capture the log output multiple log streams (#LogStream) can be
* attach to the logger. Some default streams for common streaming locations (such as
* a file, std::cout, OutputDebugString()) are also provided.
*
* If you wish to customize the logging at an even deeper level supply your own
* implementation of #Logger to #set().
* @note The whole logging stuff causes a small extra overhead for all imports. */
class ASSIMP_API DefaultLogger :
public Logger {
public:
// ----------------------------------------------------------------------
/** @brief Creates a logging instance.
* @param name Name for log file. Only valid in combination
* with the aiDefaultLogStream_FILE flag.
* @param severity Log severity, VERBOSE turns on debug messages
* @param defStreams Default log streams to be attached. Any bitwise
* combination of the aiDefaultLogStream enumerated values.
* If #aiDefaultLogStream_FILE is specified but an empty string is
* passed for 'name', no log file is created at all.
* @param io IOSystem to be used to open external files (such as the
* log file). Pass NULL to rely on the default implementation.
* This replaces the default #NullLogger with a #DefaultLogger instance. */
static Logger *create(const char* name = ASSIMP_DEFAULT_LOG_NAME,
LogSeverity severity = NORMAL,
unsigned int defStreams = aiDefaultLogStream_DEBUGGER | aiDefaultLogStream_FILE,
IOSystem* io = NULL);
// ----------------------------------------------------------------------
/** @brief Setup a custom #Logger implementation.
*
* Use this if the provided #DefaultLogger class doesn't fit into
* your needs. If the provided message formatting is OK for you,
* it's much easier to use #create() and to attach your own custom
* output streams to it.
* @param logger Pass NULL to setup a default NullLogger*/
static void set (Logger *logger);
// ----------------------------------------------------------------------
/** @brief Getter for singleton instance
* @return Only instance. This is never null, but it could be a
* NullLogger. Use isNullLogger to check this.*/
static Logger *get();
// ----------------------------------------------------------------------
/** @brief Return whether a #NullLogger is currently active
* @return true if the current logger is a #NullLogger.
* Use create() or set() to setup a logger that does actually do
* something else than just rejecting all log messages. */
static bool isNullLogger();
// ----------------------------------------------------------------------
/** @brief Kills the current singleton logger and replaces it with a
* #NullLogger instance. */
static void kill();
// ----------------------------------------------------------------------
/** @copydoc Logger::attachStream */
bool attachStream(LogStream *pStream,
unsigned int severity);
// ----------------------------------------------------------------------
/** @copydoc Logger::detatchStream */
bool detatchStream(LogStream *pStream,
unsigned int severity);
private:
// ----------------------------------------------------------------------
/** @briefPrivate construction for internal use by create().
* @param severity Logging granularity */
explicit DefaultLogger(LogSeverity severity);
// ----------------------------------------------------------------------
/** @briefDestructor */
~DefaultLogger();
/** @brief Logs debug infos, only been written when severity level VERBOSE is set */
void OnDebug(const char* message);
/** @brief Logs an info message */
void OnInfo(const char* message);
/** @brief Logs a warning message */
void OnWarn(const char* message);
/** @brief Logs an error message */
void OnError(const char* message);
// ----------------------------------------------------------------------
/** @brief Writes a message to all streams */
void WriteToStreams(const char* message, ErrorSeverity ErrorSev );
// ----------------------------------------------------------------------
/** @brief Returns the thread id.
* @note This is an OS specific feature, if not supported, a
* zero will be returned.
*/
unsigned int GetThreadID();
private:
// Aliases for stream container
typedef std::vector<LogStreamInfo*> StreamArray;
typedef std::vector<LogStreamInfo*>::iterator StreamIt;
typedef std::vector<LogStreamInfo*>::const_iterator ConstStreamIt;
//! only logging instance
static Logger *m_pLogger;
static NullLogger s_pNullLogger;
//! Attached streams
StreamArray m_StreamArray;
bool noRepeatMsg;
char lastMsg[MAX_LOG_MESSAGE_LENGTH*2];
size_t lastLen;
};
// ------------------------------------------------------------------------------------
} // Namespace Assimp
#endif // !! INCLUDED_AI_DEFAULTLOGGER

View File

@ -0,0 +1,49 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2012, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
// We need those constants, workaround for any platforms where nobody defined them yet
#if (!defined SIZE_MAX)
# define SIZE_MAX (~((size_t)0))
#endif
#if (!defined UINT_MAX)
# define UINT_MAX (~((unsigned int)0))
#endif

View File

@ -0,0 +1,125 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2008, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
#ifndef INCLUDED_EXCEPTIONAL_H
#define INCLUDED_EXCEPTIONAL_H
#include <stdexcept>
#include <assimp/DefaultIOStream.h>
using std::runtime_error;
#ifdef _MSC_VER
# pragma warning(disable : 4275)
#endif
// ---------------------------------------------------------------------------
/** FOR IMPORTER PLUGINS ONLY: Simple exception class to be thrown if an
* unrecoverable error occurs while importing. Loading APIs return
* NULL instead of a valid aiScene then. */
class DeadlyImportError
: public runtime_error
{
public:
/** Constructor with arguments */
explicit DeadlyImportError( const std::string& errorText)
: runtime_error(errorText)
{
}
private:
};
typedef DeadlyImportError DeadlyExportError;
#ifdef _MSC_VER
# pragma warning(default : 4275)
#endif
// ---------------------------------------------------------------------------
template <typename T>
struct ExceptionSwallower {
T operator ()() const {
return T();
}
};
// ---------------------------------------------------------------------------
template <typename T>
struct ExceptionSwallower<T*> {
T* operator ()() const {
return NULL;
}
};
// ---------------------------------------------------------------------------
template <>
struct ExceptionSwallower<aiReturn> {
aiReturn operator ()() const {
try {
throw;
}
catch (std::bad_alloc&) {
return aiReturn_OUTOFMEMORY;
}
catch (...) {
return aiReturn_FAILURE;
}
}
};
// ---------------------------------------------------------------------------
template <>
struct ExceptionSwallower<void> {
void operator ()() const {
return;
}
};
#define ASSIMP_BEGIN_EXCEPTION_REGION()\
{\
try {
#define ASSIMP_END_EXCEPTION_REGION(type)\
} catch(...) {\
return ExceptionSwallower<type>()();\
}\
}
#endif // INCLUDED_EXCEPTIONAL_H

View File

@ -0,0 +1,505 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Exporter.hpp
* @brief Defines the CPP-API for the Assimp export interface
*/
#pragma once
#ifndef AI_EXPORT_HPP_INC
#define AI_EXPORT_HPP_INC
#ifndef ASSIMP_BUILD_NO_EXPORT
#include "cexport.h"
#include <map>
namespace Assimp {
class ExporterPimpl;
class IOSystem;
class ProgressHandler;
// ----------------------------------------------------------------------------------
/** CPP-API: The Exporter class forms an C++ interface to the export functionality
* of the Open Asset Import Library. Note that the export interface is available
* only if Assimp has been built with ASSIMP_BUILD_NO_EXPORT not defined.
*
* The interface is modeled after the importer interface and mostly
* symmetric. The same rules for threading etc. apply.
*
* In a nutshell, there are two export interfaces: #Export, which writes the
* output file(s) either to the regular file system or to a user-supplied
* #IOSystem, and #ExportToBlob which returns a linked list of memory
* buffers (blob), each referring to one output file (in most cases
* there will be only one output file of course, but this extra complexity is
* needed since Assimp aims at supporting a wide range of file formats).
*
* #ExportToBlob is especially useful if you intend to work
* with the data in-memory.
*/
class ASSIMP_API ExportProperties;
class ASSIMP_API Exporter {
public:
/** Function pointer type of a Export worker function */
typedef void (*fpExportFunc)(const char*, IOSystem*, const aiScene*, const ExportProperties*);
/** Internal description of an Assimp export format option */
struct ExportFormatEntry {
/// Public description structure to be returned by aiGetExportFormatDescription()
aiExportFormatDesc mDescription;
// Worker function to do the actual exporting
fpExportFunc mExportFunction;
// Post-processing steps to be executed PRIOR to invoking mExportFunction
unsigned int mEnforcePP;
// Constructor to fill all entries
ExportFormatEntry( const char* pId, const char* pDesc, const char* pExtension, fpExportFunc pFunction, unsigned int pEnforcePP = 0u)
{
mDescription.id = pId;
mDescription.description = pDesc;
mDescription.fileExtension = pExtension;
mExportFunction = pFunction;
mEnforcePP = pEnforcePP;
}
ExportFormatEntry() :
mExportFunction()
, mEnforcePP()
{
mDescription.id = NULL;
mDescription.description = NULL;
mDescription.fileExtension = NULL;
}
};
/**
* @brief The class constructor.
*/
Exporter();
/**
* @brief The class destructor.
*/
~Exporter();
// -------------------------------------------------------------------
/** Supplies a custom IO handler to the exporter to use to open and
* access files.
*
* If you need #Export to use custom IO logic to access the files,
* you need to supply a custom implementation of IOSystem and
* IOFile to the exporter.
*
* #Exporter takes ownership of the object and will destroy it
* afterwards. The previously assigned handler will be deleted.
* Pass NULL to take again ownership of your IOSystem and reset Assimp
* to use its default implementation, which uses plain file IO.
*
* @param pIOHandler The IO handler to be used in all file accesses
* of the Importer. */
void SetIOHandler( IOSystem* pIOHandler);
// -------------------------------------------------------------------
/** Retrieves the IO handler that is currently set.
* You can use #IsDefaultIOHandler() to check whether the returned
* interface is the default IO handler provided by ASSIMP. The default
* handler is active as long the application doesn't supply its own
* custom IO handler via #SetIOHandler().
* @return A valid IOSystem interface, never NULL. */
IOSystem* GetIOHandler() const;
// -------------------------------------------------------------------
/** Checks whether a default IO handler is active
* A default handler is active as long the application doesn't
* supply its own custom IO handler via #SetIOHandler().
* @return true by default */
bool IsDefaultIOHandler() const;
// -------------------------------------------------------------------
/** Supplies a custom progress handler to the exporter. This
* interface exposes an #Update() callback, which is called
* more or less periodically (please don't sue us if it
* isn't as periodically as you'd like it to have ...).
* This can be used to implement progress bars and loading
* timeouts.
* @param pHandler Progress callback interface. Pass nullptr to
* disable progress reporting.
* @note Progress handlers can be used to abort the loading
* at almost any time.*/
void SetProgressHandler(ProgressHandler* pHandler);
// -------------------------------------------------------------------
/** Exports the given scene to a chosen file format. Returns the exported
* data as a binary blob which you can write into a file or something.
* When you're done with the data, simply let the #Exporter instance go
* out of scope to have it released automatically.
* @param pScene The scene to export. Stays in possession of the caller,
* is not changed by the function.
* @param pFormatId ID string to specify to which format you want to
* export to. Use
* #GetExportFormatCount / #GetExportFormatDescription to learn which
* export formats are available.
* @param pPreprocessing See the documentation for #Export
* @return the exported data or NULL in case of error.
* @note If the Exporter instance did already hold a blob from
* a previous call to #ExportToBlob, it will be disposed.
* Any IO handlers set via #SetIOHandler are ignored here.
* @note Use aiCopyScene() to get a modifiable copy of a previously
* imported scene. */
const aiExportDataBlob* ExportToBlob(const aiScene* pScene, const char* pFormatId,
unsigned int pPreprocessing = 0u, const ExportProperties* pProperties = nullptr);
const aiExportDataBlob* ExportToBlob( const aiScene* pScene, const std::string& pFormatId,
unsigned int pPreprocessing = 0u, const ExportProperties* pProperties = nullptr);
// -------------------------------------------------------------------
/** Convenience function to export directly to a file. Use
* #SetIOSystem to supply a custom IOSystem to gain fine-grained control
* about the output data flow of the export process.
* @param pBlob A data blob obtained from a previous call to #aiExportScene. Must not be NULL.
* @param pPath Full target file name. Target must be accessible.
* @param pPreprocessing Accepts any choice of the #aiPostProcessSteps enumerated
* flags, but in reality only a subset of them makes sense here. Specifying
* 'preprocessing' flags is useful if the input scene does not conform to
* Assimp's default conventions as specified in the @link data Data Structures Page @endlink.
* In short, this means the geometry data should use a right-handed coordinate systems, face
* winding should be counter-clockwise and the UV coordinate origin is assumed to be in
* the upper left. The #aiProcess_MakeLeftHanded, #aiProcess_FlipUVs and
* #aiProcess_FlipWindingOrder flags are used in the import side to allow users
* to have those defaults automatically adapted to their conventions. Specifying those flags
* for exporting has the opposite effect, respectively. Some other of the
* #aiPostProcessSteps enumerated values may be useful as well, but you'll need
* to try out what their effect on the exported file is. Many formats impose
* their own restrictions on the structure of the geometry stored therein,
* so some preprocessing may have little or no effect at all, or may be
* redundant as exporters would apply them anyhow. A good example
* is triangulation - whilst you can enforce it by specifying
* the #aiProcess_Triangulate flag, most export formats support only
* triangulate data so they would run the step even if it wasn't requested.
*
* If assimp detects that the input scene was directly taken from the importer side of
* the library (i.e. not copied using aiCopyScene and potentially modified afterwards),
* any post-processing steps already applied to the scene will not be applied again, unless
* they show non-idempotent behavior (#aiProcess_MakeLeftHanded, #aiProcess_FlipUVs and
* #aiProcess_FlipWindingOrder).
* @return AI_SUCCESS if everything was fine.
* @note Use aiCopyScene() to get a modifiable copy of a previously
* imported scene.*/
aiReturn Export( const aiScene* pScene, const char* pFormatId, const char* pPath,
unsigned int pPreprocessing = 0u, const ExportProperties* pProperties = nullptr);
aiReturn Export( const aiScene* pScene, const std::string& pFormatId, const std::string& pPath,
unsigned int pPreprocessing = 0u, const ExportProperties* pProperties = nullptr);
// -------------------------------------------------------------------
/** Returns an error description of an error that occurred in #Export
* or #ExportToBlob
*
* Returns an empty string if no error occurred.
* @return A description of the last error, an empty string if no
* error occurred. The string is never NULL.
*
* @note The returned function remains valid until one of the
* following methods is called: #Export, #ExportToBlob, #FreeBlob */
const char* GetErrorString() const;
// -------------------------------------------------------------------
/** Return the blob obtained from the last call to #ExportToBlob */
const aiExportDataBlob* GetBlob() const;
// -------------------------------------------------------------------
/** Orphan the blob from the last call to #ExportToBlob. This means
* the caller takes ownership and is thus responsible for calling
* the C API function #aiReleaseExportBlob to release it. */
const aiExportDataBlob* GetOrphanedBlob() const;
// -------------------------------------------------------------------
/** Frees the current blob.
*
* The function does nothing if no blob has previously been
* previously produced via #ExportToBlob. #FreeBlob is called
* automatically by the destructor. The only reason to call
* it manually would be to reclaim as much storage as possible
* without giving up the #Exporter instance yet. */
void FreeBlob( );
// -------------------------------------------------------------------
/** Returns the number of export file formats available in the current
* Assimp build. Use #Exporter::GetExportFormatDescription to
* retrieve infos of a specific export format.
*
* This includes built-in exporters as well as exporters registered
* using #RegisterExporter.
**/
size_t GetExportFormatCount() const;
// -------------------------------------------------------------------
/** Returns a description of the nth export file format. Use #
* #Exporter::GetExportFormatCount to learn how many export
* formats are supported.
*
* The returned pointer is of static storage duration if the
* pIndex pertains to a built-in exporter (i.e. one not registered
* via #RegistrerExporter). It is restricted to the life-time of the
* #Exporter instance otherwise.
*
* @param pIndex Index of the export format to retrieve information
* for. Valid range is 0 to #Exporter::GetExportFormatCount
* @return A description of that specific export format.
* NULL if pIndex is out of range. */
const aiExportFormatDesc* GetExportFormatDescription( size_t pIndex ) const;
// -------------------------------------------------------------------
/** Register a custom exporter. Custom export formats are limited to
* to the current #Exporter instance and do not affect the
* library globally. The indexes under which the format's
* export format description can be queried are assigned
* monotonously.
* @param desc Exporter description.
* @return aiReturn_SUCCESS if the export format was successfully
* registered. A common cause that would prevent an exporter
* from being registered is that its format id is already
* occupied by another format. */
aiReturn RegisterExporter(const ExportFormatEntry& desc);
// -------------------------------------------------------------------
/** Remove an export format previously registered with #RegisterExporter
* from the #Exporter instance (this can also be used to drop
* built-in exporters because those are implicitly registered
* using #RegisterExporter).
* @param id Format id to be unregistered, this refers to the
* 'id' field of #aiExportFormatDesc.
* @note Calling this method on a format description not yet registered
* has no effect.*/
void UnregisterExporter(const char* id);
protected:
// Just because we don't want you to know how we're hacking around.
ExporterPimpl* pimpl;
};
class ASSIMP_API ExportProperties {
public:
// Data type to store the key hash
typedef unsigned int KeyType;
// typedefs for our four configuration maps.
// We don't need more, so there is no need for a generic solution
typedef std::map<KeyType, int> IntPropertyMap;
typedef std::map<KeyType, ai_real> FloatPropertyMap;
typedef std::map<KeyType, std::string> StringPropertyMap;
typedef std::map<KeyType, aiMatrix4x4> MatrixPropertyMap;
public:
/** Standard constructor
* @see ExportProperties()
*/
ExportProperties();
// -------------------------------------------------------------------
/** Copy constructor.
*
* This copies the configuration properties of another ExportProperties.
* @see ExportProperties(const ExportProperties& other)
*/
ExportProperties(const ExportProperties& other);
// -------------------------------------------------------------------
/** Set an integer configuration property.
* @param szName Name of the property. All supported properties
* are defined in the aiConfig.g header (all constants share the
* prefix AI_CONFIG_XXX and are simple strings).
* @param iValue New value of the property
* @return true if the property was set before. The new value replaces
* the previous value in this case.
* @note Property of different types (float, int, string ..) are kept
* on different stacks, so calling SetPropertyInteger() for a
* floating-point property has no effect - the loader will call
* GetPropertyFloat() to read the property, but it won't be there.
*/
bool SetPropertyInteger(const char* szName, int iValue);
// -------------------------------------------------------------------
/** Set a boolean configuration property. Boolean properties
* are stored on the integer stack internally so it's possible
* to set them via #SetPropertyBool and query them with
* #GetPropertyBool and vice versa.
* @see SetPropertyInteger()
*/
bool SetPropertyBool(const char* szName, bool value) {
return SetPropertyInteger(szName,value);
}
// -------------------------------------------------------------------
/** Set a floating-point configuration property.
* @see SetPropertyInteger()
*/
bool SetPropertyFloat(const char* szName, ai_real fValue);
// -------------------------------------------------------------------
/** Set a string configuration property.
* @see SetPropertyInteger()
*/
bool SetPropertyString(const char* szName, const std::string& sValue);
// -------------------------------------------------------------------
/** Set a matrix configuration property.
* @see SetPropertyInteger()
*/
bool SetPropertyMatrix(const char* szName, const aiMatrix4x4& sValue);
// -------------------------------------------------------------------
/** Get a configuration property.
* @param szName Name of the property. All supported properties
* are defined in the aiConfig.g header (all constants share the
* prefix AI_CONFIG_XXX).
* @param iErrorReturn Value that is returned if the property
* is not found.
* @return Current value of the property
* @note Property of different types (float, int, string ..) are kept
* on different lists, so calling SetPropertyInteger() for a
* floating-point property has no effect - the loader will call
* GetPropertyFloat() to read the property, but it won't be there.
*/
int GetPropertyInteger(const char* szName,
int iErrorReturn = 0xffffffff) const;
// -------------------------------------------------------------------
/** Get a boolean configuration property. Boolean properties
* are stored on the integer stack internally so it's possible
* to set them via #SetPropertyBool and query them with
* #GetPropertyBool and vice versa.
* @see GetPropertyInteger()
*/
bool GetPropertyBool(const char* szName, bool bErrorReturn = false) const {
return GetPropertyInteger(szName,bErrorReturn)!=0;
}
// -------------------------------------------------------------------
/** Get a floating-point configuration property
* @see GetPropertyInteger()
*/
ai_real GetPropertyFloat(const char* szName,
ai_real fErrorReturn = 10e10f) const;
// -------------------------------------------------------------------
/** Get a string configuration property
*
* The return value remains valid until the property is modified.
* @see GetPropertyInteger()
*/
const std::string GetPropertyString(const char* szName,
const std::string& sErrorReturn = "") const;
// -------------------------------------------------------------------
/** Get a matrix configuration property
*
* The return value remains valid until the property is modified.
* @see GetPropertyInteger()
*/
const aiMatrix4x4 GetPropertyMatrix(const char* szName,
const aiMatrix4x4& sErrorReturn = aiMatrix4x4()) const;
// -------------------------------------------------------------------
/** Determine a integer configuration property has been set.
* @see HasPropertyInteger()
*/
bool HasPropertyInteger(const char* szName) const;
/** Determine a boolean configuration property has been set.
* @see HasPropertyBool()
*/
bool HasPropertyBool(const char* szName) const;
/** Determine a boolean configuration property has been set.
* @see HasPropertyFloat()
*/
bool HasPropertyFloat(const char* szName) const;
/** Determine a String configuration property has been set.
* @see HasPropertyString()
*/
bool HasPropertyString(const char* szName) const;
/** Determine a Matrix configuration property has been set.
* @see HasPropertyMatrix()
*/
bool HasPropertyMatrix(const char* szName) const;
protected:
/** List of integer properties */
IntPropertyMap mIntProperties;
/** List of floating-point properties */
FloatPropertyMap mFloatProperties;
/** List of string properties */
StringPropertyMap mStringProperties;
/** List of Matrix properties */
MatrixPropertyMap mMatrixProperties;
};
// ----------------------------------------------------------------------------------
inline
const aiExportDataBlob* Exporter::ExportToBlob( const aiScene* pScene, const std::string& pFormatId,
unsigned int pPreprocessing, const ExportProperties* pProperties)
{
return ExportToBlob(pScene,pFormatId.c_str(),pPreprocessing, pProperties);
}
// ----------------------------------------------------------------------------------
inline
aiReturn Exporter :: Export( const aiScene* pScene, const std::string& pFormatId,
const std::string& pPath, unsigned int pPreprocessing,
const ExportProperties* pProperties)
{
return Export(pScene,pFormatId.c_str(),pPath.c_str(),pPreprocessing, pProperties);
}
} // namespace Assimp
#endif // ASSIMP_BUILD_NO_EXPORT
#endif // AI_EXPORT_HPP_INC

View File

@ -0,0 +1,133 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
#ifndef AI_GENERIC_PROPERTY_H_INCLUDED
#define AI_GENERIC_PROPERTY_H_INCLUDED
#include <assimp/Importer.hpp>
#include <assimp/ai_assert.h>
#include "Hash.h"
#include <map>
// ------------------------------------------------------------------------------------------------
template <class T>
inline
bool SetGenericProperty(std::map< unsigned int, T >& list,
const char* szName, const T& value) {
ai_assert(nullptr != szName);
const uint32_t hash = SuperFastHash(szName);
typename std::map<unsigned int, T>::iterator it = list.find(hash);
if (it == list.end()) {
list.insert(std::pair<unsigned int, T>( hash, value ));
return false;
}
(*it).second = value;
return true;
}
// ------------------------------------------------------------------------------------------------
template <class T>
inline
const T& GetGenericProperty(const std::map< unsigned int, T >& list,
const char* szName, const T& errorReturn) {
ai_assert(nullptr != szName);
const uint32_t hash = SuperFastHash(szName);
typename std::map<unsigned int, T>::const_iterator it = list.find(hash);
if (it == list.end()) {
return errorReturn;
}
return (*it).second;
}
// ------------------------------------------------------------------------------------------------
// Special version for pointer types - they will be deleted when replaced with another value
// passing NULL removes the whole property
template <class T>
inline
void SetGenericPropertyPtr(std::map< unsigned int, T* >& list,
const char* szName, T* value, bool* bWasExisting = nullptr ) {
ai_assert(nullptr != szName);
const uint32_t hash = SuperFastHash(szName);
typename std::map<unsigned int, T*>::iterator it = list.find(hash);
if (it == list.end()) {
if (bWasExisting) {
*bWasExisting = false;
}
list.insert(std::pair<unsigned int,T*>( hash, value ));
return;
}
if ((*it).second != value) {
delete (*it).second;
(*it).second = value;
}
if (!value) {
list.erase(it);
}
if (bWasExisting) {
*bWasExisting = true;
}
}
// ------------------------------------------------------------------------------------------------
template <class T>
inline
bool HasGenericProperty(const std::map< unsigned int, T >& list,
const char* szName) {
ai_assert(nullptr != szName);
const uint32_t hash = SuperFastHash(szName);
typename std::map<unsigned int, T>::const_iterator it = list.find(hash);
if (it == list.end()) {
return false;
}
return true;
}
#endif // !! AI_GENERIC_PROPERTY_H_INCLUDED

View File

@ -0,0 +1,118 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
#ifndef AI_HASH_H_INCLUDED
#define AI_HASH_H_INCLUDED
#include <stdint.h>
#include <string.h>
// ------------------------------------------------------------------------------------------------
// Hashing function taken from
// http://www.azillionmonkeys.com/qed/hash.html
// (incremental version)
//
// This code is Copyright 2004-2008 by Paul Hsieh. It is used here in the belief that
// Assimp's license is considered compatible with Pauls's derivative license as specified
// on his web page.
//
// (stdint.h should have been been included here)
// ------------------------------------------------------------------------------------------------
#undef get16bits
#if (defined(__GNUC__) && defined(__i386__)) || defined(__WATCOMC__) \
|| defined(_MSC_VER) || defined (__BORLANDC__) || defined (__TURBOC__)
#define get16bits(d) (*((const uint16_t *) (d)))
#endif
#if !defined (get16bits)
#define get16bits(d) ((((uint32_t)(((const uint8_t *)(d))[1])) << 8)\
+(uint32_t)(((const uint8_t *)(d))[0]) )
#endif
// ------------------------------------------------------------------------------------------------
inline uint32_t SuperFastHash (const char * data, uint32_t len = 0, uint32_t hash = 0) {
uint32_t tmp;
int rem;
if (!data) return 0;
if (!len)len = (uint32_t)::strlen(data);
rem = len & 3;
len >>= 2;
/* Main loop */
for (;len > 0; len--) {
hash += get16bits (data);
tmp = (get16bits (data+2) << 11) ^ hash;
hash = (hash << 16) ^ tmp;
data += 2*sizeof (uint16_t);
hash += hash >> 11;
}
/* Handle end cases */
switch (rem) {
case 3: hash += get16bits (data);
hash ^= hash << 16;
hash ^= data[sizeof (uint16_t)] << 18;
hash += hash >> 11;
break;
case 2: hash += get16bits (data);
hash ^= hash << 11;
hash += hash >> 17;
break;
case 1: hash += *data;
hash ^= hash << 10;
hash += hash >> 1;
}
/* Force "avalanching" of final 127 bits */
hash ^= hash << 3;
hash += hash >> 5;
hash ^= hash << 4;
hash += hash >> 17;
hash ^= hash << 25;
hash += hash >> 6;
return hash;
}
#endif // !! AI_HASH_H_INCLUDED

View File

@ -0,0 +1,142 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file IOStream.hpp
* @brief File I/O wrappers for C++.
*/
#pragma once
#ifndef AI_IOSTREAM_H_INC
#define AI_IOSTREAM_H_INC
#include "types.h"
#ifndef __cplusplus
# error This header requires C++ to be used. aiFileIO.h is the \
corresponding C interface.
#endif
namespace Assimp {
// ----------------------------------------------------------------------------------
/** @brief CPP-API: Class to handle file I/O for C++
*
* Derive an own implementation from this interface to provide custom IO handling
* to the Importer. If you implement this interface, be sure to also provide an
* implementation for IOSystem that creates instances of your custom IO class.
*/
class ASSIMP_API IOStream
#ifndef SWIG
: public Intern::AllocateFromAssimpHeap
#endif
{
protected:
/** Constructor protected, use IOSystem::Open() to create an instance. */
IOStream() AI_NO_EXCEPT;
public:
// -------------------------------------------------------------------
/** @brief Destructor. Deleting the object closes the underlying file,
* alternatively you may use IOSystem::Close() to release the file.
*/
virtual ~IOStream();
// -------------------------------------------------------------------
/** @brief Read from the file
*
* See fread() for more details
* This fails for write-only files */
virtual size_t Read(void* pvBuffer,
size_t pSize,
size_t pCount) = 0;
// -------------------------------------------------------------------
/** @brief Write to the file
*
* See fwrite() for more details
* This fails for read-only files */
virtual size_t Write(const void* pvBuffer,
size_t pSize,
size_t pCount) = 0;
// -------------------------------------------------------------------
/** @brief Set the read/write cursor of the file
*
* Note that the offset is _negative_ for aiOrigin_END.
* See fseek() for more details */
virtual aiReturn Seek(size_t pOffset,
aiOrigin pOrigin) = 0;
// -------------------------------------------------------------------
/** @brief Get the current position of the read/write cursor
*
* See ftell() for more details */
virtual size_t Tell() const = 0;
// -------------------------------------------------------------------
/** @brief Returns filesize
* Returns the filesize. */
virtual size_t FileSize() const = 0;
// -------------------------------------------------------------------
/** @brief Flush the contents of the file buffer (for writers)
* See fflush() for more details.
*/
virtual void Flush() = 0;
}; //! class IOStream
// ----------------------------------------------------------------------------------
inline
IOStream::IOStream() AI_NO_EXCEPT {
// empty
}
// ----------------------------------------------------------------------------------
inline
IOStream::~IOStream() {
// empty
}
// ----------------------------------------------------------------------------------
} //!namespace Assimp
#endif //!!AI_IOSTREAM_H_INC

View File

@ -0,0 +1,355 @@
#pragma once
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
#include <assimp/types.h>
#include <assimp/IOStream.hpp>
#include "ParsingUtils.h"
#include <vector>
namespace Assimp {
// ---------------------------------------------------------------------------
/**
* Implementation of a cached stream buffer.
*/
template<class T>
class IOStreamBuffer {
public:
/// @brief The class constructor.
IOStreamBuffer( size_t cache = 4096 * 4096 );
/// @brief The class destructor.
~IOStreamBuffer();
/// @brief Will open the cached access for a given stream.
/// @param stream The stream to cache.
/// @return true if successful.
bool open( IOStream *stream );
/// @brief Will close the cached access.
/// @return true if successful.
bool close();
/// @brief Returns the file-size.
/// @return The file-size.
size_t size() const;
/// @brief Returns the cache size.
/// @return The cache size.
size_t cacheSize() const;
/// @brief Will read the next block.
/// @return true if successful.
bool readNextBlock();
/// @brief Returns the number of blocks to read.
/// @return The number of blocks.
size_t getNumBlocks() const;
/// @brief Returns the current block index.
/// @return The current block index.
size_t getCurrentBlockIndex() const;
/// @brief Returns the current file pos.
/// @return The current file pos.
size_t getFilePos() const;
/// @brief Will read the next line.
/// @param buffer The buffer for the next line.
/// @return true if successful.
bool getNextDataLine( std::vector<T> &buffer, T continuationToken );
/// @brief Will read the next line ascii or binary end line char.
/// @param buffer The buffer for the next line.
/// @return true if successful.
bool getNextLine(std::vector<T> &buffer);
/// @brief Will read the next block.
/// @param buffer The buffer for the next block.
/// @return true if successful.
bool getNextBlock( std::vector<T> &buffer );
private:
IOStream *m_stream;
size_t m_filesize;
size_t m_cacheSize;
size_t m_numBlocks;
size_t m_blockIdx;
std::vector<T> m_cache;
size_t m_cachePos;
size_t m_filePos;
};
template<class T>
inline
IOStreamBuffer<T>::IOStreamBuffer( size_t cache )
: m_stream( nullptr )
, m_filesize( 0 )
, m_cacheSize( cache )
, m_numBlocks( 0 )
, m_blockIdx( 0 )
, m_cachePos( 0 )
, m_filePos( 0 ) {
m_cache.resize( cache );
std::fill( m_cache.begin(), m_cache.end(), '\n' );
}
template<class T>
inline
IOStreamBuffer<T>::~IOStreamBuffer() {
// empty
}
template<class T>
inline
bool IOStreamBuffer<T>::open( IOStream *stream ) {
// file still opened!
if ( nullptr != m_stream ) {
return false;
}
// Invalid stream pointer
if ( nullptr == stream ) {
return false;
}
m_stream = stream;
m_filesize = m_stream->FileSize();
if ( m_filesize == 0 ) {
return false;
}
if ( m_filesize < m_cacheSize ) {
m_cacheSize = m_filesize;
}
m_numBlocks = m_filesize / m_cacheSize;
if ( ( m_filesize % m_cacheSize ) > 0 ) {
m_numBlocks++;
}
return true;
}
template<class T>
inline
bool IOStreamBuffer<T>::close() {
if ( nullptr == m_stream ) {
return false;
}
// init counters and state vars
m_stream = nullptr;
m_filesize = 0;
m_numBlocks = 0;
m_blockIdx = 0;
m_cachePos = 0;
m_filePos = 0;
return true;
}
template<class T>
inline
size_t IOStreamBuffer<T>::size() const {
return m_filesize;
}
template<class T>
inline
size_t IOStreamBuffer<T>::cacheSize() const {
return m_cacheSize;
}
template<class T>
inline
bool IOStreamBuffer<T>::readNextBlock() {
m_stream->Seek( m_filePos, aiOrigin_SET );
size_t readLen = m_stream->Read( &m_cache[ 0 ], sizeof( T ), m_cacheSize );
if ( readLen == 0 ) {
return false;
}
if ( readLen < m_cacheSize ) {
m_cacheSize = readLen;
}
m_filePos += m_cacheSize;
m_cachePos = 0;
m_blockIdx++;
return true;
}
template<class T>
inline
size_t IOStreamBuffer<T>::getNumBlocks() const {
return m_numBlocks;
}
template<class T>
inline
size_t IOStreamBuffer<T>::getCurrentBlockIndex() const {
return m_blockIdx;
}
template<class T>
inline
size_t IOStreamBuffer<T>::getFilePos() const {
return m_filePos;
}
template<class T>
inline
bool IOStreamBuffer<T>::getNextDataLine( std::vector<T> &buffer, T continuationToken ) {
buffer.resize( m_cacheSize );
if ( m_cachePos >= m_cacheSize || 0 == m_filePos ) {
if ( !readNextBlock() ) {
return false;
}
}
bool continuationFound( false );
size_t i = 0;
for( ;; ) {
if ( continuationToken == m_cache[ m_cachePos ] ) {
continuationFound = true;
++m_cachePos;
}
if ( IsLineEnd( m_cache[ m_cachePos ] ) ) {
if ( !continuationFound ) {
// the end of the data line
break;
} else {
// skip line end
while ( m_cache[m_cachePos] != '\n') {
++m_cachePos;
}
++m_cachePos;
continuationFound = false;
}
}
buffer[ i ] = m_cache[ m_cachePos ];
++m_cachePos;
++i;
if (m_cachePos >= size()) {
break;
}
if ( m_cachePos >= m_cacheSize ) {
if ( !readNextBlock() ) {
return false;
}
}
}
buffer[ i ] = '\n';
++m_cachePos;
return true;
}
static inline
bool isEndOfCache( size_t pos, size_t cacheSize ) {
return ( pos == cacheSize );
}
template<class T>
inline
bool IOStreamBuffer<T>::getNextLine(std::vector<T> &buffer) {
buffer.resize(m_cacheSize);
if ( isEndOfCache( m_cachePos, m_cacheSize ) || 0 == m_filePos) {
if (!readNextBlock()) {
return false;
}
}
if (IsLineEnd(m_cache[m_cachePos])) {
// skip line end
while (m_cache[m_cachePos] != '\n') {
++m_cachePos;
}
++m_cachePos;
if ( isEndOfCache( m_cachePos, m_cacheSize ) ) {
if ( !readNextBlock() ) {
return false;
}
}
}
size_t i( 0 );
while (!IsLineEnd(m_cache[ m_cachePos ])) {
buffer[i] = m_cache[ m_cachePos ];
++m_cachePos;
++i;
if (m_cachePos >= m_cacheSize) {
if (!readNextBlock()) {
return false;
}
}
}
buffer[i] = '\n';
++m_cachePos;
return true;
}
template<class T>
inline
bool IOStreamBuffer<T>::getNextBlock( std::vector<T> &buffer) {
// Return the last block-value if getNextLine was used before
if ( 0 != m_cachePos ) {
buffer = std::vector<T>( m_cache.begin() + m_cachePos, m_cache.end() );
m_cachePos = 0;
} else {
if ( !readNextBlock() ) {
return false;
}
buffer = std::vector<T>(m_cache.begin(), m_cache.end());
}
return true;
}
} // !ns Assimp

View File

@ -0,0 +1,357 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file IOSystem.hpp
* @brief File system wrapper for C++. Inherit this class to supply
* custom file handling logic to the Import library.
*/
#pragma once
#ifndef AI_IOSYSTEM_H_INC
#define AI_IOSYSTEM_H_INC
#ifndef __cplusplus
# error This header requires C++ to be used. aiFileIO.h is the \
corresponding C interface.
#endif
#include "types.h"
#ifdef _WIN32
# include <direct.h>
# include <stdlib.h>
# include <stdio.h>
#else
# include <sys/stat.h>
# include <sys/types.h>
# include <unistd.h>
#endif // _WIN32
#include <vector>
namespace Assimp {
class IOStream;
// ---------------------------------------------------------------------------
/** @brief CPP-API: Interface to the file system.
*
* Derive an own implementation from this interface to supply custom file handling
* to the importer library. If you implement this interface, you also want to
* supply a custom implementation for IOStream.
*
* @see Importer::SetIOHandler()
*/
class ASSIMP_API IOSystem
#ifndef SWIG
: public Intern::AllocateFromAssimpHeap
#endif
{
public:
// -------------------------------------------------------------------
/** @brief Default constructor.
*
* Create an instance of your derived class and assign it to an
* #Assimp::Importer instance by calling Importer::SetIOHandler().
*/
IOSystem() AI_NO_EXCEPT;
// -------------------------------------------------------------------
/** @brief Virtual destructor.
*
* It is safe to be called from within DLL Assimp, we're constructed
* on Assimp's heap.
*/
virtual ~IOSystem();
// -------------------------------------------------------------------
/** @brief For backward compatibility
* @see Exists(const char*)
*/
AI_FORCE_INLINE bool Exists( const std::string& pFile) const;
// -------------------------------------------------------------------
/** @brief Tests for the existence of a file at the given path.
*
* @param pFile Path to the file
* @return true if there is a file with this path, else false.
*/
virtual bool Exists( const char* pFile) const = 0;
// -------------------------------------------------------------------
/** @brief Returns the system specific directory separator
* @return System specific directory separator
*/
virtual char getOsSeparator() const = 0;
// -------------------------------------------------------------------
/** @brief Open a new file with a given path.
*
* When the access to the file is finished, call Close() to release
* all associated resources (or the virtual dtor of the IOStream).
*
* @param pFile Path to the file
* @param pMode Desired file I/O mode. Required are: "wb", "w", "wt",
* "rb", "r", "rt".
*
* @return New IOStream interface allowing the lib to access
* the underlying file.
* @note When implementing this class to provide custom IO handling,
* you probably have to supply an own implementation of IOStream as well.
*/
virtual IOStream* Open(const char* pFile,
const char* pMode = "rb") = 0;
// -------------------------------------------------------------------
/** @brief For backward compatibility
* @see Open(const char*, const char*)
*/
inline IOStream* Open(const std::string& pFile,
const std::string& pMode = std::string("rb"));
// -------------------------------------------------------------------
/** @brief Closes the given file and releases all resources
* associated with it.
* @param pFile The file instance previously created by Open().
*/
virtual void Close( IOStream* pFile) = 0;
// -------------------------------------------------------------------
/** @brief Compares two paths and check whether the point to
* identical files.
*
* The dummy implementation of this virtual member performs a
* case-insensitive comparison of the given strings. The default IO
* system implementation uses OS mechanisms to convert relative into
* absolute paths, so the result can be trusted.
* @param one First file
* @param second Second file
* @return true if the paths point to the same file. The file needn't
* be existing, however.
*/
virtual bool ComparePaths (const char* one,
const char* second) const;
// -------------------------------------------------------------------
/** @brief For backward compatibility
* @see ComparePaths(const char*, const char*)
*/
inline bool ComparePaths (const std::string& one,
const std::string& second) const;
// -------------------------------------------------------------------
/** @brief Pushes a new directory onto the directory stack.
* @param path Path to push onto the stack.
* @return True, when push was successful, false if path is empty.
*/
virtual bool PushDirectory( const std::string &path );
// -------------------------------------------------------------------
/** @brief Returns the top directory from the stack.
* @return The directory on the top of the stack.
* Returns empty when no directory was pushed to the stack.
*/
virtual const std::string &CurrentDirectory() const;
// -------------------------------------------------------------------
/** @brief Returns the number of directories stored on the stack.
* @return The number of directories of the stack.
*/
virtual size_t StackSize() const;
// -------------------------------------------------------------------
/** @brief Pops the top directory from the stack.
* @return True, when a directory was on the stack. False if no
* directory was on the stack.
*/
virtual bool PopDirectory();
// -------------------------------------------------------------------
/** @brief CReates an new directory at the given path.
* @param path [in] The path to create.
* @return True, when a directory was created. False if the directory
* cannot be created.
*/
virtual bool CreateDirectory( const std::string &path );
// -------------------------------------------------------------------
/** @brief Will change the current directory to the given path.
* @param path [in] The path to change to.
* @return True, when the directory has changed successfully.
*/
virtual bool ChangeDirectory( const std::string &path );
virtual bool DeleteFile( const std::string &file );
private:
std::vector<std::string> m_pathStack;
};
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
IOSystem::IOSystem() AI_NO_EXCEPT
: m_pathStack() {
// empty
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
IOSystem::~IOSystem() {
// empty
}
// ----------------------------------------------------------------------------
// For compatibility, the interface of some functions taking a std::string was
// changed to const char* to avoid crashes between binary incompatible STL
// versions. This code her is inlined, so it shouldn't cause any problems.
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
IOStream* IOSystem::Open(const std::string& pFile, const std::string& pMode) {
// NOTE:
// For compatibility, interface was changed to const char* to
// avoid crashes between binary incompatible STL versions
return Open(pFile.c_str(),pMode.c_str());
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
bool IOSystem::Exists( const std::string& pFile) const {
// NOTE:
// For compatibility, interface was changed to const char* to
// avoid crashes between binary incompatible STL versions
return Exists(pFile.c_str());
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
bool IOSystem::ComparePaths (const std::string& one, const std::string& second) const {
// NOTE:
// For compatibility, interface was changed to const char* to
// avoid crashes between binary incompatible STL versions
return ComparePaths(one.c_str(),second.c_str());
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
bool IOSystem::PushDirectory( const std::string &path ) {
if ( path.empty() ) {
return false;
}
m_pathStack.push_back( path );
return true;
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
const std::string &IOSystem::CurrentDirectory() const {
if ( m_pathStack.empty() ) {
static const std::string Dummy("");
return Dummy;
}
return m_pathStack[ m_pathStack.size()-1 ];
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
size_t IOSystem::StackSize() const {
return m_pathStack.size();
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
bool IOSystem::PopDirectory() {
if ( m_pathStack.empty() ) {
return false;
}
m_pathStack.pop_back();
return true;
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
bool IOSystem::CreateDirectory( const std::string &path ) {
if ( path.empty() ) {
return false;
}
#ifdef _WIN32
return 0 != ::_mkdir( path.c_str() );
#else
return 0 != ::mkdir( path.c_str(), 0777 );
#endif // _WIN32
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
bool IOSystem::ChangeDirectory( const std::string &path ) {
if ( path.empty() ) {
return false;
}
#ifdef _WIN32
return 0 != ::_chdir( path.c_str() );
#else
return 0 != ::chdir( path.c_str() );
#endif // _WIN32
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE
bool IOSystem::DeleteFile( const std::string &file ) {
if ( file.empty() ) {
return false;
}
const int retCode( ::remove( file.c_str() ) );
return ( 0 == retCode );
}
} //!ns Assimp
#endif //AI_IOSYSTEM_H_INC

View File

@ -0,0 +1,659 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Importer.hpp
* @brief Defines the C++-API to the Open Asset Import Library.
*/
#pragma once
#ifndef AI_ASSIMP_HPP_INC
#define AI_ASSIMP_HPP_INC
#ifndef __cplusplus
# error This header requires C++ to be used. Use assimp.h for plain C.
#endif // __cplusplus
// Public ASSIMP data structures
#include <assimp/types.h>
namespace Assimp {
// =======================================================================
// Public interface to Assimp
class Importer;
class IOStream;
class IOSystem;
class ProgressHandler;
// =======================================================================
// Plugin development
//
// Include the following headers for the declarations:
// BaseImporter.h
// BaseProcess.h
class BaseImporter;
class BaseProcess;
class SharedPostProcessInfo;
class BatchLoader;
// =======================================================================
// Holy stuff, only for members of the high council of the Jedi.
class ImporterPimpl;
} //! namespace Assimp
#define AI_PROPERTY_WAS_NOT_EXISTING 0xffffffff
struct aiScene;
// importerdesc.h
struct aiImporterDesc;
/** @namespace Assimp Assimp's CPP-API and all internal APIs */
namespace Assimp {
// ----------------------------------------------------------------------------------
/** CPP-API: The Importer class forms an C++ interface to the functionality of the
* Open Asset Import Library.
*
* Create an object of this class and call ReadFile() to import a file.
* If the import succeeds, the function returns a pointer to the imported data.
* The data remains property of the object, it is intended to be accessed
* read-only. The imported data will be destroyed along with the Importer
* object. If the import fails, ReadFile() returns a NULL pointer. In this
* case you can retrieve a human-readable error description be calling
* GetErrorString(). You can call ReadFile() multiple times with a single Importer
* instance. Actually, constructing Importer objects involves quite many
* allocations and may take some time, so it's better to reuse them as often as
* possible.
*
* If you need the Importer to do custom file handling to access the files,
* implement IOSystem and IOStream and supply an instance of your custom
* IOSystem implementation by calling SetIOHandler() before calling ReadFile().
* If you do not assign a custion IO handler, a default handler using the
* standard C++ IO logic will be used.
*
* @note One Importer instance is not thread-safe. If you use multiple
* threads for loading, each thread should maintain its own Importer instance.
*/
class ASSIMP_API Importer {
public:
/**
* @brief The upper limit for hints.
*/
static const unsigned int MaxLenHint = 200;
public:
// -------------------------------------------------------------------
/** Constructor. Creates an empty importer object.
*
* Call ReadFile() to start the import process. The configuration
* property table is initially empty.
*/
Importer();
// -------------------------------------------------------------------
/** Copy constructor.
*
* This copies the configuration properties of another Importer.
* If this Importer owns a scene it won't be copied.
* Call ReadFile() to start the import process.
*/
Importer(const Importer& other)=delete;
// -------------------------------------------------------------------
/** Assignment operator has been deleted
*/
Importer &operator=(const Importer &) = delete;
// -------------------------------------------------------------------
/** Destructor. The object kept ownership of the imported data,
* which now will be destroyed along with the object.
*/
~Importer();
// -------------------------------------------------------------------
/** Registers a new loader.
*
* @param pImp Importer to be added. The Importer instance takes
* ownership of the pointer, so it will be automatically deleted
* with the Importer instance.
* @return AI_SUCCESS if the loader has been added. The registration
* fails if there is already a loader for a specific file extension.
*/
aiReturn RegisterLoader(BaseImporter* pImp);
// -------------------------------------------------------------------
/** Unregisters a loader.
*
* @param pImp Importer to be unregistered.
* @return AI_SUCCESS if the loader has been removed. The function
* fails if the loader is currently in use (this could happen
* if the #Importer instance is used by more than one thread) or
* if it has not yet been registered.
*/
aiReturn UnregisterLoader(BaseImporter* pImp);
// -------------------------------------------------------------------
/** Registers a new post-process step.
*
* At the moment, there's a small limitation: new post processing
* steps are added to end of the list, or in other words, executed
* last, after all built-in steps.
* @param pImp Post-process step to be added. The Importer instance
* takes ownership of the pointer, so it will be automatically
* deleted with the Importer instance.
* @return AI_SUCCESS if the step has been added correctly.
*/
aiReturn RegisterPPStep(BaseProcess* pImp);
// -------------------------------------------------------------------
/** Unregisters a post-process step.
*
* @param pImp Step to be unregistered.
* @return AI_SUCCESS if the step has been removed. The function
* fails if the step is currently in use (this could happen
* if the #Importer instance is used by more than one thread) or
* if it has not yet been registered.
*/
aiReturn UnregisterPPStep(BaseProcess* pImp);
// -------------------------------------------------------------------
/** Set an integer configuration property.
* @param szName Name of the property. All supported properties
* are defined in the aiConfig.g header (all constants share the
* prefix AI_CONFIG_XXX and are simple strings).
* @param iValue New value of the property
* @return true if the property was set before. The new value replaces
* the previous value in this case.
* @note Property of different types (float, int, string ..) are kept
* on different stacks, so calling SetPropertyInteger() for a
* floating-point property has no effect - the loader will call
* GetPropertyFloat() to read the property, but it won't be there.
*/
bool SetPropertyInteger(const char* szName, int iValue);
// -------------------------------------------------------------------
/** Set a boolean configuration property. Boolean properties
* are stored on the integer stack internally so it's possible
* to set them via #SetPropertyBool and query them with
* #GetPropertyBool and vice versa.
* @see SetPropertyInteger()
*/
bool SetPropertyBool(const char* szName, bool value) {
return SetPropertyInteger(szName,value);
}
// -------------------------------------------------------------------
/** Set a floating-point configuration property.
* @see SetPropertyInteger()
*/
bool SetPropertyFloat(const char* szName, ai_real fValue);
// -------------------------------------------------------------------
/** Set a string configuration property.
* @see SetPropertyInteger()
*/
bool SetPropertyString(const char* szName, const std::string& sValue);
// -------------------------------------------------------------------
/** Set a matrix configuration property.
* @see SetPropertyInteger()
*/
bool SetPropertyMatrix(const char* szName, const aiMatrix4x4& sValue);
// -------------------------------------------------------------------
/** Get a configuration property.
* @param szName Name of the property. All supported properties
* are defined in the aiConfig.g header (all constants share the
* prefix AI_CONFIG_XXX).
* @param iErrorReturn Value that is returned if the property
* is not found.
* @return Current value of the property
* @note Property of different types (float, int, string ..) are kept
* on different lists, so calling SetPropertyInteger() for a
* floating-point property has no effect - the loader will call
* GetPropertyFloat() to read the property, but it won't be there.
*/
int GetPropertyInteger(const char* szName,
int iErrorReturn = 0xffffffff) const;
// -------------------------------------------------------------------
/** Get a boolean configuration property. Boolean properties
* are stored on the integer stack internally so it's possible
* to set them via #SetPropertyBool and query them with
* #GetPropertyBool and vice versa.
* @see GetPropertyInteger()
*/
bool GetPropertyBool(const char* szName, bool bErrorReturn = false) const {
return GetPropertyInteger(szName,bErrorReturn)!=0;
}
// -------------------------------------------------------------------
/** Get a floating-point configuration property
* @see GetPropertyInteger()
*/
ai_real GetPropertyFloat(const char* szName,
ai_real fErrorReturn = 10e10) const;
// -------------------------------------------------------------------
/** Get a string configuration property
*
* The return value remains valid until the property is modified.
* @see GetPropertyInteger()
*/
const std::string GetPropertyString(const char* szName,
const std::string& sErrorReturn = "") const;
// -------------------------------------------------------------------
/** Get a matrix configuration property
*
* The return value remains valid until the property is modified.
* @see GetPropertyInteger()
*/
const aiMatrix4x4 GetPropertyMatrix(const char* szName,
const aiMatrix4x4& sErrorReturn = aiMatrix4x4()) const;
// -------------------------------------------------------------------
/** Supplies a custom IO handler to the importer to use to open and
* access files. If you need the importer to use custom IO logic to
* access the files, you need to provide a custom implementation of
* IOSystem and IOFile to the importer. Then create an instance of
* your custom IOSystem implementation and supply it by this function.
*
* The Importer takes ownership of the object and will destroy it
* afterwards. The previously assigned handler will be deleted.
* Pass NULL to take again ownership of your IOSystem and reset Assimp
* to use its default implementation.
*
* @param pIOHandler The IO handler to be used in all file accesses
* of the Importer.
*/
void SetIOHandler( IOSystem* pIOHandler);
// -------------------------------------------------------------------
/** Retrieves the IO handler that is currently set.
* You can use #IsDefaultIOHandler() to check whether the returned
* interface is the default IO handler provided by ASSIMP. The default
* handler is active as long the application doesn't supply its own
* custom IO handler via #SetIOHandler().
* @return A valid IOSystem interface, never NULL.
*/
IOSystem* GetIOHandler() const;
// -------------------------------------------------------------------
/** Checks whether a default IO handler is active
* A default handler is active as long the application doesn't
* supply its own custom IO handler via #SetIOHandler().
* @return true by default
*/
bool IsDefaultIOHandler() const;
// -------------------------------------------------------------------
/** Supplies a custom progress handler to the importer. This
* interface exposes an #Update() callback, which is called
* more or less periodically (please don't sue us if it
* isn't as periodically as you'd like it to have ...).
* This can be used to implement progress bars and loading
* timeouts.
* @param pHandler Progress callback interface. Pass NULL to
* disable progress reporting.
* @note Progress handlers can be used to abort the loading
* at almost any time.*/
void SetProgressHandler ( ProgressHandler* pHandler );
// -------------------------------------------------------------------
/** Retrieves the progress handler that is currently set.
* You can use #IsDefaultProgressHandler() to check whether the returned
* interface is the default handler provided by ASSIMP. The default
* handler is active as long the application doesn't supply its own
* custom handler via #SetProgressHandler().
* @return A valid ProgressHandler interface, never NULL.
*/
ProgressHandler* GetProgressHandler() const;
// -------------------------------------------------------------------
/** Checks whether a default progress handler is active
* A default handler is active as long the application doesn't
* supply its own custom progress handler via #SetProgressHandler().
* @return true by default
*/
bool IsDefaultProgressHandler() const;
// -------------------------------------------------------------------
/** @brief Check whether a given set of post-processing flags
* is supported.
*
* Some flags are mutually exclusive, others are probably
* not available because your excluded them from your
* Assimp builds. Calling this function is recommended if
* you're unsure.
*
* @param pFlags Bitwise combination of the aiPostProcess flags.
* @return true if this flag combination is fine.
*/
bool ValidateFlags(unsigned int pFlags) const;
// -------------------------------------------------------------------
/** Reads the given file and returns its contents if successful.
*
* If the call succeeds, the contents of the file are returned as a
* pointer to an aiScene object. The returned data is intended to be
* read-only, the importer object keeps ownership of the data and will
* destroy it upon destruction. If the import fails, NULL is returned.
* A human-readable error description can be retrieved by calling
* GetErrorString(). The previous scene will be deleted during this call.
* @param pFile Path and filename to the file to be imported.
* @param pFlags Optional post processing steps to be executed after
* a successful import. Provide a bitwise combination of the
* #aiPostProcessSteps flags. If you wish to inspect the imported
* scene first in order to fine-tune your post-processing setup,
* consider to use #ApplyPostProcessing().
* @return A pointer to the imported data, NULL if the import failed.
* The pointer to the scene remains in possession of the Importer
* instance. Use GetOrphanedScene() to take ownership of it.
*
* @note Assimp is able to determine the file format of a file
* automatically.
*/
const aiScene* ReadFile(
const char* pFile,
unsigned int pFlags);
// -------------------------------------------------------------------
/** Reads the given file from a memory buffer and returns its
* contents if successful.
*
* If the call succeeds, the contents of the file are returned as a
* pointer to an aiScene object. The returned data is intended to be
* read-only, the importer object keeps ownership of the data and will
* destroy it upon destruction. If the import fails, NULL is returned.
* A human-readable error description can be retrieved by calling
* GetErrorString(). The previous scene will be deleted during this call.
* Calling this method doesn't affect the active IOSystem.
* @param pBuffer Pointer to the file data
* @param pLength Length of pBuffer, in bytes
* @param pFlags Optional post processing steps to be executed after
* a successful import. Provide a bitwise combination of the
* #aiPostProcessSteps flags. If you wish to inspect the imported
* scene first in order to fine-tune your post-processing setup,
* consider to use #ApplyPostProcessing().
* @param pHint An additional hint to the library. If this is a non
* empty string, the library looks for a loader to support
* the file extension specified by pHint and passes the file to
* the first matching loader. If this loader is unable to completely
* the request, the library continues and tries to determine the
* file format on its own, a task that may or may not be successful.
* Check the return value, and you'll know ...
* @return A pointer to the imported data, NULL if the import failed.
* The pointer to the scene remains in possession of the Importer
* instance. Use GetOrphanedScene() to take ownership of it.
*
* @note This is a straightforward way to decode models from memory
* buffers, but it doesn't handle model formats that spread their
* data across multiple files or even directories. Examples include
* OBJ or MD3, which outsource parts of their material info into
* external scripts. If you need full functionality, provide
* a custom IOSystem to make Assimp find these files and use
* the regular ReadFile() API.
*/
const aiScene* ReadFileFromMemory(
const void* pBuffer,
size_t pLength,
unsigned int pFlags,
const char* pHint = "");
// -------------------------------------------------------------------
/** Apply post-processing to an already-imported scene.
*
* This is strictly equivalent to calling #ReadFile() with the same
* flags. However, you can use this separate function to inspect
* the imported scene first to fine-tune your post-processing setup.
* @param pFlags Provide a bitwise combination of the
* #aiPostProcessSteps flags.
* @return A pointer to the post-processed data. This is still the
* same as the pointer returned by #ReadFile(). However, if
* post-processing fails, the scene could now be NULL.
* That's quite a rare case, post processing steps are not really
* designed to 'fail'. To be exact, the #aiProcess_ValidateDS
* flag is currently the only post processing step which can actually
* cause the scene to be reset to NULL.
*
* @note The method does nothing if no scene is currently bound
* to the #Importer instance. */
const aiScene* ApplyPostProcessing(unsigned int pFlags);
const aiScene* ApplyCustomizedPostProcessing( BaseProcess *rootProcess, bool requestValidation );
// -------------------------------------------------------------------
/** @brief Reads the given file and returns its contents if successful.
*
* This function is provided for backward compatibility.
* See the const char* version for detailed docs.
* @see ReadFile(const char*, pFlags) */
const aiScene* ReadFile(
const std::string& pFile,
unsigned int pFlags);
// -------------------------------------------------------------------
/** Frees the current scene.
*
* The function does nothing if no scene has previously been
* read via ReadFile(). FreeScene() is called automatically by the
* destructor and ReadFile() itself. */
void FreeScene( );
// -------------------------------------------------------------------
/** Returns an error description of an error that occurred in ReadFile().
*
* Returns an empty string if no error occurred.
* @return A description of the last error, an empty string if no
* error occurred. The string is never NULL.
*
* @note The returned function remains valid until one of the
* following methods is called: #ReadFile(), #FreeScene(). */
const char* GetErrorString() const;
// -------------------------------------------------------------------
/** Returns the scene loaded by the last successful call to ReadFile()
*
* @return Current scene or NULL if there is currently no scene loaded */
const aiScene* GetScene() const;
// -------------------------------------------------------------------
/** Returns the scene loaded by the last successful call to ReadFile()
* and releases the scene from the ownership of the Importer
* instance. The application is now responsible for deleting the
* scene. Any further calls to GetScene() or GetOrphanedScene()
* will return NULL - until a new scene has been loaded via ReadFile().
*
* @return Current scene or NULL if there is currently no scene loaded
* @note Use this method with maximal caution, and only if you have to.
* By design, aiScene's are exclusively maintained, allocated and
* deallocated by Assimp and no one else. The reasoning behind this
* is the golden rule that deallocations should always be done
* by the module that did the original allocation because heaps
* are not necessarily shared. GetOrphanedScene() enforces you
* to delete the returned scene by yourself, but this will only
* be fine if and only if you're using the same heap as assimp.
* On Windows, it's typically fine provided everything is linked
* against the multithreaded-dll version of the runtime library.
* It will work as well for static linkage with Assimp.*/
aiScene* GetOrphanedScene();
// -------------------------------------------------------------------
/** Returns whether a given file extension is supported by ASSIMP.
*
* @param szExtension Extension to be checked.
* Must include a trailing dot '.'. Example: ".3ds", ".md3".
* Cases-insensitive.
* @return true if the extension is supported, false otherwise */
bool IsExtensionSupported(const char* szExtension) const;
// -------------------------------------------------------------------
/** @brief Returns whether a given file extension is supported by ASSIMP.
*
* This function is provided for backward compatibility.
* See the const char* version for detailed and up-to-date docs.
* @see IsExtensionSupported(const char*) */
inline bool IsExtensionSupported(const std::string& szExtension) const;
// -------------------------------------------------------------------
/** Get a full list of all file extensions supported by ASSIMP.
*
* If a file extension is contained in the list this does of course not
* mean that ASSIMP is able to load all files with this extension ---
* it simply means there is an importer loaded which claims to handle
* files with this file extension.
* @param szOut String to receive the extension list.
* Format of the list: "*.3ds;*.obj;*.dae". This is useful for
* use with the WinAPI call GetOpenFileName(Ex). */
void GetExtensionList(aiString& szOut) const;
// -------------------------------------------------------------------
/** @brief Get a full list of all file extensions supported by ASSIMP.
*
* This function is provided for backward compatibility.
* See the aiString version for detailed and up-to-date docs.
* @see GetExtensionList(aiString&)*/
inline void GetExtensionList(std::string& szOut) const;
// -------------------------------------------------------------------
/** Get the number of importers currently registered with Assimp. */
size_t GetImporterCount() const;
// -------------------------------------------------------------------
/** Get meta data for the importer corresponding to a specific index..
*
* For the declaration of #aiImporterDesc, include <assimp/importerdesc.h>.
* @param index Index to query, must be within [0,GetImporterCount())
* @return Importer meta data structure, NULL if the index does not
* exist or if the importer doesn't offer meta information (
* importers may do this at the cost of being hated by their peers).*/
const aiImporterDesc* GetImporterInfo(size_t index) const;
// -------------------------------------------------------------------
/** Find the importer corresponding to a specific index.
*
* @param index Index to query, must be within [0,GetImporterCount())
* @return Importer instance. NULL if the index does not
* exist. */
BaseImporter* GetImporter(size_t index) const;
// -------------------------------------------------------------------
/** Find the importer corresponding to a specific file extension.
*
* This is quite similar to #IsExtensionSupported except a
* BaseImporter instance is returned.
* @param szExtension Extension to check for. The following formats
* are recognized (BAH being the file extension): "BAH" (comparison
* is case-insensitive), ".bah", "*.bah" (wild card and dot
* characters at the beginning of the extension are skipped).
* @return NULL if no importer is found*/
BaseImporter* GetImporter (const char* szExtension) const;
// -------------------------------------------------------------------
/** Find the importer index corresponding to a specific file extension.
*
* @param szExtension Extension to check for. The following formats
* are recognized (BAH being the file extension): "BAH" (comparison
* is case-insensitive), ".bah", "*.bah" (wild card and dot
* characters at the beginning of the extension are skipped).
* @return (size_t)-1 if no importer is found */
size_t GetImporterIndex (const char* szExtension) const;
// -------------------------------------------------------------------
/** Returns the storage allocated by ASSIMP to hold the scene data
* in memory.
*
* This refers to the currently loaded file, see #ReadFile().
* @param in Data structure to be filled.
* @note The returned memory statistics refer to the actual
* size of the use data of the aiScene. Heap-related overhead
* is (naturally) not included.*/
void GetMemoryRequirements(aiMemoryInfo& in) const;
// -------------------------------------------------------------------
/** Enables "extra verbose" mode.
*
* 'Extra verbose' means the data structure is validated after *every*
* single post processing step to make sure everyone modifies the data
* structure in a well-defined manner. This is a debug feature and not
* intended for use in production environments. */
void SetExtraVerbose(bool bDo);
// -------------------------------------------------------------------
/** Private, do not use. */
ImporterPimpl* Pimpl() { return pimpl; }
const ImporterPimpl* Pimpl() const { return pimpl; }
protected:
// Just because we don't want you to know how we're hacking around.
ImporterPimpl* pimpl;
}; //! class Importer
// ----------------------------------------------------------------------------
// For compatibility, the interface of some functions taking a std::string was
// changed to const char* to avoid crashes between binary incompatible STL
// versions. This code her is inlined, so it shouldn't cause any problems.
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
AI_FORCE_INLINE const aiScene* Importer::ReadFile( const std::string& pFile,unsigned int pFlags){
return ReadFile(pFile.c_str(),pFlags);
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE void Importer::GetExtensionList(std::string& szOut) const {
aiString s;
GetExtensionList(s);
szOut = s.data;
}
// ----------------------------------------------------------------------------
AI_FORCE_INLINE bool Importer::IsExtensionSupported(const std::string& szExtension) const {
return IsExtensionSupported(szExtension.c_str());
}
} // !namespace Assimp
#endif // AI_ASSIMP_HPP_INC

View File

@ -0,0 +1,285 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file LineSplitter.h
* @brief LineSplitter, a helper class to iterate through all lines
* of a file easily. Works with StreamReader.
*/
#pragma once
#ifndef INCLUDED_LINE_SPLITTER_H
#define INCLUDED_LINE_SPLITTER_H
#include <stdexcept>
#include "StreamReader.h"
#include "ParsingUtils.h"
namespace Assimp {
// ------------------------------------------------------------------------------------------------
/** Usage:
@code
for(LineSplitter splitter(stream);splitter;++splitter) {
if (*splitter == "hi!") {
...
}
else if (splitter->substr(0,5) == "hello") {
...
// access the third token in the line (tokens are space-separated)
if (strtol(splitter[2]) > 5) { .. }
}
std::cout << "Current line is: " << splitter.get_index() << std::endl;
}
@endcode
*/
// ------------------------------------------------------------------------------------------------
class LineSplitter {
public:
typedef size_t line_idx;
// -----------------------------------------
/** construct from existing stream reader
note: trim is *always* assumed true if skyp_empty_lines==true
*/
LineSplitter(StreamReaderLE& stream, bool skip_empty_lines = true, bool trim = true);
~LineSplitter();
// -----------------------------------------
/** pseudo-iterator increment */
LineSplitter& operator++();
// -----------------------------------------
LineSplitter& operator++(int);
// -----------------------------------------
/** get a pointer to the beginning of a particular token */
const char* operator[] (size_t idx) const;
// -----------------------------------------
/** extract the start positions of N tokens from the current line*/
template <size_t N>
void get_tokens(const char* (&tokens)[N]) const;
// -----------------------------------------
/** member access */
const std::string* operator -> () const;
std::string operator* () const;
// -----------------------------------------
/** boolean context */
operator bool() const;
// -----------------------------------------
/** line indices are zero-based, empty lines are included */
operator line_idx() const;
line_idx get_index() const;
// -----------------------------------------
/** access the underlying stream object */
StreamReaderLE& get_stream();
// -----------------------------------------
/** !strcmp((*this)->substr(0,strlen(check)),check) */
bool match_start(const char* check);
// -----------------------------------------
/** swallow the next call to ++, return the previous value. */
void swallow_next_increment();
LineSplitter( const LineSplitter & ) = delete;
LineSplitter(LineSplitter &&) = delete;
LineSplitter &operator = ( const LineSplitter & ) = delete;
private:
line_idx mIdx;
std::string mCur;
StreamReaderLE& mStream;
bool mSwallow, mSkip_empty_lines, mTrim;
};
inline
LineSplitter::LineSplitter(StreamReaderLE& stream, bool skip_empty_lines, bool trim )
: mIdx(0)
, mCur()
, mStream(stream)
, mSwallow()
, mSkip_empty_lines(skip_empty_lines)
, mTrim(trim) {
mCur.reserve(1024);
operator++();
mIdx = 0;
}
inline
LineSplitter::~LineSplitter() {
// empty
}
inline
LineSplitter& LineSplitter::operator++() {
if (mSwallow) {
mSwallow = false;
return *this;
}
if (!*this) {
throw std::logic_error("End of file, no more lines to be retrieved.");
}
char s;
mCur.clear();
while (mStream.GetRemainingSize() && (s = mStream.GetI1(), 1)) {
if (s == '\n' || s == '\r') {
if (mSkip_empty_lines) {
while (mStream.GetRemainingSize() && ((s = mStream.GetI1()) == ' ' || s == '\r' || s == '\n'));
if (mStream.GetRemainingSize()) {
mStream.IncPtr(-1);
}
} else {
// skip both potential line terminators but don't read past this line.
if (mStream.GetRemainingSize() && (s == '\r' && mStream.GetI1() != '\n')) {
mStream.IncPtr(-1);
}
if (mTrim) {
while (mStream.GetRemainingSize() && ((s = mStream.GetI1()) == ' ' || s == '\t'));
if (mStream.GetRemainingSize()) {
mStream.IncPtr(-1);
}
}
}
break;
}
mCur += s;
}
++mIdx;
return *this;
}
inline
LineSplitter &LineSplitter::operator++(int) {
return ++(*this);
}
inline
const char *LineSplitter::operator[] (size_t idx) const {
const char* s = operator->()->c_str();
SkipSpaces(&s);
for (size_t i = 0; i < idx; ++i) {
for (; !IsSpace(*s); ++s) {
if (IsLineEnd(*s)) {
throw std::range_error("Token index out of range, EOL reached");
}
}
SkipSpaces(&s);
}
return s;
}
template <size_t N>
inline
void LineSplitter::get_tokens(const char* (&tokens)[N]) const {
const char* s = operator->()->c_str();
SkipSpaces(&s);
for (size_t i = 0; i < N; ++i) {
if (IsLineEnd(*s)) {
throw std::range_error("Token count out of range, EOL reached");
}
tokens[i] = s;
for (; *s && !IsSpace(*s); ++s);
SkipSpaces(&s);
}
}
inline
const std::string* LineSplitter::operator -> () const {
return &mCur;
}
inline
std::string LineSplitter::operator* () const {
return mCur;
}
inline
LineSplitter::operator bool() const {
return mStream.GetRemainingSize() > 0;
}
inline
LineSplitter::operator line_idx() const {
return mIdx;
}
inline
LineSplitter::line_idx LineSplitter::get_index() const {
return mIdx;
}
inline
StreamReaderLE &LineSplitter::get_stream() {
return mStream;
}
inline
bool LineSplitter::match_start(const char* check) {
const size_t len = ::strlen(check);
return len <= mCur.length() && std::equal(check, check + len, mCur.begin());
}
inline
void LineSplitter::swallow_next_increment() {
mSwallow = true;
}
} // Namespace Assimp
#endif // INCLUDED_LINE_SPLITTER_H

View File

@ -0,0 +1,131 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file LogAux.h
* @brief Common logging usage patterns for importer implementations
*/
#ifndef INCLUDED_AI_LOGAUX_H
#define INCLUDED_AI_LOGAUX_H
#include <assimp/TinyFormatter.h>
#include <assimp/Exceptional.h>
#include <assimp/DefaultLogger.hpp>
namespace Assimp {
template<class TDeriving>
class LogFunctions {
public:
// ------------------------------------------------------------------------------------------------
static void ThrowException(const std::string& msg)
{
throw DeadlyImportError(Prefix()+msg);
}
// ------------------------------------------------------------------------------------------------
static void LogWarn(const Formatter::format& message) {
if (!DefaultLogger::isNullLogger()) {
ASSIMP_LOG_WARN(Prefix()+(std::string)message);
}
}
// ------------------------------------------------------------------------------------------------
static void LogError(const Formatter::format& message) {
if (!DefaultLogger::isNullLogger()) {
ASSIMP_LOG_ERROR(Prefix()+(std::string)message);
}
}
// ------------------------------------------------------------------------------------------------
static void LogInfo(const Formatter::format& message) {
if (!DefaultLogger::isNullLogger()) {
ASSIMP_LOG_INFO(Prefix()+(std::string)message);
}
}
// ------------------------------------------------------------------------------------------------
static void LogDebug(const Formatter::format& message) {
if (!DefaultLogger::isNullLogger()) {
ASSIMP_LOG_DEBUG(Prefix()+(std::string)message);
}
}
// https://sourceforge.net/tracker/?func=detail&atid=1067632&aid=3358562&group_id=226462
#if !defined(__GNUC__) || !defined(__APPLE__) || __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)
// ------------------------------------------------------------------------------------------------
static void LogWarn (const char* message) {
if (!DefaultLogger::isNullLogger()) {
LogWarn(Formatter::format(message));
}
}
// ------------------------------------------------------------------------------------------------
static void LogError (const char* message) {
if (!DefaultLogger::isNullLogger()) {
LogError(Formatter::format(message));
}
}
// ------------------------------------------------------------------------------------------------
static void LogInfo (const char* message) {
if (!DefaultLogger::isNullLogger()) {
LogInfo(Formatter::format(message));
}
}
// ------------------------------------------------------------------------------------------------
static void LogDebug (const char* message) {
if (!DefaultLogger::isNullLogger()) {
LogDebug(Formatter::format(message));
}
}
#endif
private:
static const char* Prefix();
};
} // ! Assimp
#endif

View File

@ -0,0 +1,111 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file LogStream.hpp
* @brief Abstract base class 'LogStream', representing an output log stream.
*/
#ifndef INCLUDED_AI_LOGSTREAM_H
#define INCLUDED_AI_LOGSTREAM_H
#include "types.h"
namespace Assimp {
class IOSystem;
// ------------------------------------------------------------------------------------
/** @brief CPP-API: Abstract interface for log stream implementations.
*
* Several default implementations are provided, see #aiDefaultLogStream for more
* details. Writing your own implementation of LogStream is just necessary if these
* are not enough for your purpose. */
class ASSIMP_API LogStream
#ifndef SWIG
: public Intern::AllocateFromAssimpHeap
#endif
{
protected:
/** @brief Default constructor */
LogStream() AI_NO_EXCEPT;
public:
/** @brief Virtual destructor */
virtual ~LogStream();
// -------------------------------------------------------------------
/** @brief Overwrite this for your own output methods
*
* Log messages *may* consist of multiple lines and you shouldn't
* expect a consistent formatting. If you want custom formatting
* (e.g. generate HTML), supply a custom instance of Logger to
* #DefaultLogger:set(). Usually you can *expect* that a log message
* is exactly one line and terminated with a single \n character.
* @param message Message to be written */
virtual void write(const char* message) = 0;
// -------------------------------------------------------------------
/** @brief Creates a default log stream
* @param streams Type of the default stream
* @param name For aiDefaultLogStream_FILE: name of the output file
* @param io For aiDefaultLogStream_FILE: IOSystem to be used to open the output
* file. Pass NULL for the default implementation.
* @return New LogStream instance. */
static LogStream* createDefaultStream(aiDefaultLogStream stream,
const char* name = "AssimpLog.txt",
IOSystem* io = nullptr );
}; // !class LogStream
inline
LogStream::LogStream() AI_NO_EXCEPT {
// empty
}
inline
LogStream::~LogStream() {
// empty
}
// ------------------------------------------------------------------------------------
} // Namespace Assimp
#endif

View File

@ -0,0 +1,305 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Logger.hpp
* @brief Abstract base class 'Logger', base of the logging system.
*/
#ifndef INCLUDED_AI_LOGGER_H
#define INCLUDED_AI_LOGGER_H
#include <assimp/types.h>
#include <assimp/TinyFormatter.h>
namespace Assimp {
class LogStream;
// Maximum length of a log message. Longer messages are rejected.
#define MAX_LOG_MESSAGE_LENGTH 1024u
// ----------------------------------------------------------------------------------
/** @brief CPP-API: Abstract interface for logger implementations.
* Assimp provides a default implementation and uses it for almost all
* logging stuff ('DefaultLogger'). This class defines just basic logging
* behavior and is not of interest for you. Instead, take a look at #DefaultLogger. */
class ASSIMP_API Logger
#ifndef SWIG
: public Intern::AllocateFromAssimpHeap
#endif
{
public:
// ----------------------------------------------------------------------
/** @enum LogSeverity
* @brief Log severity to describe the granularity of logging.
*/
enum LogSeverity {
NORMAL, //!< Normal granularity of logging
VERBOSE //!< Debug infos will be logged, too
};
// ----------------------------------------------------------------------
/** @enum ErrorSeverity
* @brief Description for severity of a log message.
*
* Every LogStream has a bitwise combination of these flags.
* A LogStream doesn't receive any messages of a specific type
* if it doesn't specify the corresponding ErrorSeverity flag.
*/
enum ErrorSeverity {
Debugging = 1, //!< Debug log message
Info = 2, //!< Info log message
Warn = 4, //!< Warn log message
Err = 8 //!< Error log message
};
public:
/** @brief Virtual destructor */
virtual ~Logger();
// ----------------------------------------------------------------------
/** @brief Writes a debug message
* @param message Debug message*/
void debug(const char* message);
void debug(const std::string &message);
// ----------------------------------------------------------------------
/** @brief Writes a info message
* @param message Info message*/
void info(const char* message);
void info(const std::string &message);
// ----------------------------------------------------------------------
/** @brief Writes a warning message
* @param message Warn message*/
void warn(const char* message);
void warn(const std::string &message);
// ----------------------------------------------------------------------
/** @brief Writes an error message
* @param message Error message*/
void error(const char* message);
void error(const std::string &message);
// ----------------------------------------------------------------------
/** @brief Set a new log severity.
* @param log_severity New severity for logging*/
void setLogSeverity(LogSeverity log_severity);
// ----------------------------------------------------------------------
/** @brief Get the current log severity*/
LogSeverity getLogSeverity() const;
// ----------------------------------------------------------------------
/** @brief Attach a new log-stream
*
* The logger takes ownership of the stream and is responsible
* for its destruction (which is done using ::delete when the logger
* itself is destroyed). Call detachStream to detach a stream and to
* gain ownership of it again.
* @param pStream Log-stream to attach
* @param severity Message filter, specified which types of log
* messages are dispatched to the stream. Provide a bitwise
* combination of the ErrorSeverity flags.
* @return true if the stream has been attached, false otherwise.*/
virtual bool attachStream(LogStream *pStream,
unsigned int severity = Debugging | Err | Warn | Info) = 0;
// ----------------------------------------------------------------------
/** @brief Detach a still attached stream from the logger (or
* modify the filter flags bits)
* @param pStream Log-stream instance for detaching
* @param severity Provide a bitwise combination of the ErrorSeverity
* flags. This value is &~ed with the current flags of the stream,
* if the result is 0 the stream is detached from the Logger and
* the caller retakes the possession of the stream.
* @return true if the stream has been detached, false otherwise.*/
virtual bool detatchStream(LogStream *pStream,
unsigned int severity = Debugging | Err | Warn | Info) = 0;
protected:
/**
* Default constructor
*/
Logger() AI_NO_EXCEPT;
/**
* Construction with a given log severity
*/
explicit Logger(LogSeverity severity);
// ----------------------------------------------------------------------
/**
* @brief Called as a request to write a specific debug message
* @param message Debug message. Never longer than
* MAX_LOG_MESSAGE_LENGTH characters (excluding the '0').
* @note The message string is only valid until the scope of
* the function is left.
*/
virtual void OnDebug(const char* message)= 0;
// ----------------------------------------------------------------------
/**
* @brief Called as a request to write a specific info message
* @param message Info message. Never longer than
* MAX_LOG_MESSAGE_LENGTH characters (ecxluding the '0').
* @note The message string is only valid until the scope of
* the function is left.
*/
virtual void OnInfo(const char* message) = 0;
// ----------------------------------------------------------------------
/**
* @brief Called as a request to write a specific warn message
* @param message Warn message. Never longer than
* MAX_LOG_MESSAGE_LENGTH characters (exluding the '0').
* @note The message string is only valid until the scope of
* the function is left.
*/
virtual void OnWarn(const char* essage) = 0;
// ----------------------------------------------------------------------
/**
* @brief Called as a request to write a specific error message
* @param message Error message. Never longer than
* MAX_LOG_MESSAGE_LENGTH characters (exluding the '0').
* @note The message string is only valid until the scope of
* the function is left.
*/
virtual void OnError(const char* message) = 0;
protected:
LogSeverity m_Severity;
};
// ----------------------------------------------------------------------------------
// Default constructor
inline
Logger::Logger() AI_NO_EXCEPT
: m_Severity(NORMAL) {
// empty
}
// ----------------------------------------------------------------------------------
// Virtual destructor
inline
Logger::~Logger() {
// empty
}
// ----------------------------------------------------------------------------------
// Construction with given logging severity
inline
Logger::Logger(LogSeverity severity)
: m_Severity(severity) {
// empty
}
// ----------------------------------------------------------------------------------
// Log severity setter
inline
void Logger::setLogSeverity(LogSeverity log_severity){
m_Severity = log_severity;
}
// ----------------------------------------------------------------------------------
// Log severity getter
inline
Logger::LogSeverity Logger::getLogSeverity() const {
return m_Severity;
}
// ----------------------------------------------------------------------------------
inline
void Logger::debug(const std::string &message) {
return debug(message.c_str());
}
// ----------------------------------------------------------------------------------
inline
void Logger::error(const std::string &message) {
return error(message.c_str());
}
// ----------------------------------------------------------------------------------
inline
void Logger::warn(const std::string &message) {
return warn(message.c_str());
}
// ----------------------------------------------------------------------------------
inline
void Logger::info(const std::string &message) {
return info(message.c_str());
}
// ------------------------------------------------------------------------------------------------
#define ASSIMP_LOG_WARN_F(string,...)\
DefaultLogger::get()->warn((Formatter::format(string),__VA_ARGS__))
#define ASSIMP_LOG_ERROR_F(string,...)\
DefaultLogger::get()->error((Formatter::format(string),__VA_ARGS__))
#define ASSIMP_LOG_DEBUG_F(string,...)\
DefaultLogger::get()->debug((Formatter::format(string),__VA_ARGS__))
#define ASSIMP_LOG_INFO_F(string,...)\
DefaultLogger::get()->info((Formatter::format(string),__VA_ARGS__))
#define ASSIMP_LOG_WARN(string)\
DefaultLogger::get()->warn(string)
#define ASSIMP_LOG_ERROR(string)\
DefaultLogger::get()->error(string)
#define ASSIMP_LOG_DEBUG(string)\
DefaultLogger::get()->debug(string)
#define ASSIMP_LOG_INFO(string)\
DefaultLogger::get()->info(string)
} // Namespace Assimp
#endif // !! INCLUDED_AI_LOGGER_H

View File

@ -0,0 +1,49 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/* Helper macro to set a pointer to NULL in debug builds
*/
#if (defined ASSIMP_BUILD_DEBUG)
# define AI_DEBUG_INVALIDATE_PTR(x) x = NULL;
#else
# define AI_DEBUG_INVALIDATE_PTR(x)
#endif

View File

@ -0,0 +1,86 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2016, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
#pragma once
/** @file MathFunctions.h
* @brief Implementation of math utility functions.
*
*/
#include <limits>
namespace Assimp {
namespace Math {
// TODO: use binary GCD for unsigned integers ....
template < typename IntegerType >
inline
IntegerType gcd( IntegerType a, IntegerType b ) {
const IntegerType zero = (IntegerType)0;
while ( true ) {
if ( a == zero )
return b;
b %= a;
if ( b == zero )
return a;
a %= b;
}
}
template < typename IntegerType >
inline
IntegerType lcm( IntegerType a, IntegerType b ) {
const IntegerType t = gcd (a,b);
if (!t)
return t;
return a / t * b;
}
template<class T>
inline
T getEpsilon() {
return std::numeric_limits<T>::epsilon();
}
}
}

View File

@ -0,0 +1,244 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file MemoryIOWrapper.h
* Handy IOStream/IOSystem implemetation to read directly from a memory buffer */
#ifndef AI_MEMORYIOSTREAM_H_INC
#define AI_MEMORYIOSTREAM_H_INC
#include <assimp/IOStream.hpp>
#include <assimp/IOSystem.hpp>
#include <assimp/ai_assert.h>
#include <stdint.h>
namespace Assimp {
#define AI_MEMORYIO_MAGIC_FILENAME "$$$___magic___$$$"
#define AI_MEMORYIO_MAGIC_FILENAME_LENGTH 17
// ----------------------------------------------------------------------------------
/** Implementation of IOStream to read directly from a memory buffer */
// ----------------------------------------------------------------------------------
class MemoryIOStream : public IOStream {
public:
MemoryIOStream (const uint8_t* buff, size_t len, bool own = false)
: buffer (buff)
, length(len)
, pos((size_t)0)
, own(own) {
// empty
}
~MemoryIOStream () {
if(own) {
delete[] buffer;
}
}
// -------------------------------------------------------------------
// Read from stream
size_t Read(void* pvBuffer, size_t pSize, size_t pCount) {
ai_assert(nullptr != pvBuffer);
ai_assert(0 != pSize);
const size_t cnt = std::min( pCount, (length-pos) / pSize);
const size_t ofs = pSize * cnt;
::memcpy(pvBuffer,buffer+pos,ofs);
pos += ofs;
return cnt;
}
// -------------------------------------------------------------------
// Write to stream
size_t Write(const void* /*pvBuffer*/, size_t /*pSize*/,size_t /*pCount*/) {
ai_assert(false); // won't be needed
return 0;
}
// -------------------------------------------------------------------
// Seek specific position
aiReturn Seek(size_t pOffset, aiOrigin pOrigin) {
if (aiOrigin_SET == pOrigin) {
if (pOffset > length) {
return AI_FAILURE;
}
pos = pOffset;
} else if (aiOrigin_END == pOrigin) {
if (pOffset > length) {
return AI_FAILURE;
}
pos = length-pOffset;
} else {
if (pOffset+pos > length) {
return AI_FAILURE;
}
pos += pOffset;
}
return AI_SUCCESS;
}
// -------------------------------------------------------------------
// Get current seek position
size_t Tell() const {
return pos;
}
// -------------------------------------------------------------------
// Get size of file
size_t FileSize() const {
return length;
}
// -------------------------------------------------------------------
// Flush file contents
void Flush() {
ai_assert(false); // won't be needed
}
private:
const uint8_t* buffer;
size_t length,pos;
bool own;
};
// ---------------------------------------------------------------------------
/** Dummy IO system to read from a memory buffer */
class MemoryIOSystem : public IOSystem {
public:
/** Constructor. */
MemoryIOSystem(const uint8_t* buff, size_t len, IOSystem* io)
: buffer(buff)
, length(len)
, existing_io(io)
, created_streams() {
// empty
}
/** Destructor. */
~MemoryIOSystem() {
}
// -------------------------------------------------------------------
/** Tests for the existence of a file at the given path. */
bool Exists(const char* pFile) const override {
if (0 == strncmp( pFile, AI_MEMORYIO_MAGIC_FILENAME, AI_MEMORYIO_MAGIC_FILENAME_LENGTH ) ) {
return true;
}
return existing_io ? existing_io->Exists(pFile) : false;
}
// -------------------------------------------------------------------
/** Returns the directory separator. */
char getOsSeparator() const override {
return existing_io ? existing_io->getOsSeparator()
: '/'; // why not? it doesn't care
}
// -------------------------------------------------------------------
/** Open a new file with a given path. */
IOStream* Open(const char* pFile, const char* pMode = "rb") override {
if ( 0 == strncmp( pFile, AI_MEMORYIO_MAGIC_FILENAME, AI_MEMORYIO_MAGIC_FILENAME_LENGTH ) ) {
created_streams.emplace_back(new MemoryIOStream(buffer, length));
return created_streams.back();
}
return existing_io ? existing_io->Open(pFile, pMode) : NULL;
}
// -------------------------------------------------------------------
/** Closes the given file and releases all resources associated with it. */
void Close( IOStream* pFile) override {
auto it = std::find(created_streams.begin(), created_streams.end(), pFile);
if (it != created_streams.end()) {
delete pFile;
created_streams.erase(it);
} else if (existing_io) {
existing_io->Close(pFile);
}
}
// -------------------------------------------------------------------
/** Compare two paths */
bool ComparePaths(const char* one, const char* second) const override {
return existing_io ? existing_io->ComparePaths(one, second) : false;
}
bool PushDirectory( const std::string &path ) override {
return existing_io ? existing_io->PushDirectory(path) : false;
}
const std::string &CurrentDirectory() const override {
static std::string empty;
return existing_io ? existing_io->CurrentDirectory() : empty;
}
size_t StackSize() const override {
return existing_io ? existing_io->StackSize() : 0;
}
bool PopDirectory() override {
return existing_io ? existing_io->PopDirectory() : false;
}
bool CreateDirectory( const std::string &path ) override {
return existing_io ? existing_io->CreateDirectory(path) : false;
}
bool ChangeDirectory( const std::string &path ) override {
return existing_io ? existing_io->ChangeDirectory(path) : false;
}
bool DeleteFile( const std::string &file ) override {
return existing_io ? existing_io->DeleteFile(file) : false;
}
private:
const uint8_t* buffer;
size_t length;
IOSystem* existing_io;
std::vector<IOStream*> created_streams;
};
} // end namespace Assimp
#endif

View File

@ -0,0 +1,99 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file NullLogger.hpp
* @brief Dummy logger
*/
#ifndef INCLUDED_AI_NULLLOGGER_H
#define INCLUDED_AI_NULLLOGGER_H
#include "Logger.hpp"
namespace Assimp {
// ---------------------------------------------------------------------------
/** @brief CPP-API: Empty logging implementation.
*
* Does nothing! Used by default if the application hasn't requested a
* custom logger via #DefaultLogger::set() or #DefaultLogger::create(); */
class ASSIMP_API NullLogger
: public Logger {
public:
/** @brief Logs a debug message */
void OnDebug(const char* message) {
(void)message; //this avoids compiler warnings
}
/** @brief Logs an info message */
void OnInfo(const char* message) {
(void)message; //this avoids compiler warnings
}
/** @brief Logs a warning message */
void OnWarn(const char* message) {
(void)message; //this avoids compiler warnings
}
/** @brief Logs an error message */
void OnError(const char* message) {
(void)message; //this avoids compiler warnings
}
/** @brief Detach a still attached stream from logger */
bool attachStream(LogStream *pStream, unsigned int severity) {
(void)pStream; (void)severity; //this avoids compiler warnings
return false;
}
/** @brief Detach a still attached stream from logger */
bool detatchStream(LogStream *pStream, unsigned int severity) {
(void)pStream; (void)severity; //this avoids compiler warnings
return false;
}
private:
};
}
#endif // !! AI_NULLLOGGER_H_INCLUDED

View File

@ -0,0 +1,259 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file ParsingUtils.h
* @brief Defines helper functions for text parsing
*/
#ifndef AI_PARSING_UTILS_H_INC
#define AI_PARSING_UTILS_H_INC
#include "StringComparison.h"
#include "StringUtils.h"
#include <assimp/defs.h>
namespace Assimp {
// NOTE: the functions below are mostly intended as replacement for
// std::upper, std::lower, std::isupper, std::islower, std::isspace.
// we don't bother of locales. We don't want them. We want reliable
// (i.e. identical) results across all locales.
// The functions below accept any character type, but know only
// about ASCII. However, UTF-32 is the only safe ASCII superset to
// use since it doesn't have multi-byte sequences.
static const unsigned int BufferSize = 4096;
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
char_t ToLower( char_t in ) {
return (in >= (char_t)'A' && in <= (char_t)'Z') ? (char_t)(in+0x20) : in;
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
char_t ToUpper( char_t in) {
return (in >= (char_t)'a' && in <= (char_t)'z') ? (char_t)(in-0x20) : in;
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool IsUpper( char_t in) {
return (in >= (char_t)'A' && in <= (char_t)'Z');
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool IsLower( char_t in) {
return (in >= (char_t)'a' && in <= (char_t)'z');
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool IsSpace( char_t in) {
return (in == (char_t)' ' || in == (char_t)'\t');
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool IsLineEnd( char_t in) {
return (in==(char_t)'\r'||in==(char_t)'\n'||in==(char_t)'\0'||in==(char_t)'\f');
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool IsSpaceOrNewLine( char_t in) {
return IsSpace<char_t>(in) || IsLineEnd<char_t>(in);
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool SkipSpaces( const char_t* in, const char_t** out) {
while( *in == ( char_t )' ' || *in == ( char_t )'\t' ) {
++in;
}
*out = in;
return !IsLineEnd<char_t>(*in);
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool SkipSpaces( const char_t** inout) {
return SkipSpaces<char_t>(*inout,inout);
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool SkipLine( const char_t* in, const char_t** out) {
while( *in != ( char_t )'\r' && *in != ( char_t )'\n' && *in != ( char_t )'\0' ) {
++in;
}
// files are opened in binary mode. Ergo there are both NL and CR
while( *in == ( char_t )'\r' || *in == ( char_t )'\n' ) {
++in;
}
*out = in;
return *in != (char_t)'\0';
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool SkipLine( const char_t** inout) {
return SkipLine<char_t>(*inout,inout);
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool SkipSpacesAndLineEnd( const char_t* in, const char_t** out) {
while( *in == ( char_t )' ' || *in == ( char_t )'\t' || *in == ( char_t )'\r' || *in == ( char_t )'\n' ) {
++in;
}
*out = in;
return *in != '\0';
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool SkipSpacesAndLineEnd( const char_t** inout) {
return SkipSpacesAndLineEnd<char_t>(*inout,inout);
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool GetNextLine( const char_t*& buffer, char_t out[ BufferSize ] ) {
if( ( char_t )'\0' == *buffer ) {
return false;
}
char* _out = out;
char* const end = _out + BufferSize;
while( !IsLineEnd( *buffer ) && _out < end ) {
*_out++ = *buffer++;
}
*_out = (char_t)'\0';
while( IsLineEnd( *buffer ) && '\0' != *buffer ) {
++buffer;
}
return true;
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE bool IsNumeric( char_t in) {
return ( in >= '0' && in <= '9' ) || '-' == in || '+' == in;
}
// ---------------------------------------------------------------------------------
template <class char_t>
AI_FORCE_INLINE
bool TokenMatch(char_t*& in, const char* token, unsigned int len)
{
if (!::strncmp(token,in,len) && IsSpaceOrNewLine(in[len])) {
if (in[len] != '\0') {
in += len+1;
} else {
// If EOF after the token make sure we don't go past end of buffer
in += len;
}
return true;
}
return false;
}
// ---------------------------------------------------------------------------------
/** @brief Case-ignoring version of TokenMatch
* @param in Input
* @param token Token to check for
* @param len Number of characters to check
*/
AI_FORCE_INLINE
bool TokenMatchI(const char*& in, const char* token, unsigned int len) {
if (!ASSIMP_strincmp(token,in,len) && IsSpaceOrNewLine(in[len])) {
in += len+1;
return true;
}
return false;
}
// ---------------------------------------------------------------------------------
AI_FORCE_INLINE
void SkipToken(const char*& in) {
SkipSpaces(&in);
while ( !IsSpaceOrNewLine( *in ) ) {
++in;
}
}
// ---------------------------------------------------------------------------------
AI_FORCE_INLINE
std::string GetNextToken(const char*& in) {
SkipSpacesAndLineEnd(&in);
const char* cur = in;
while ( !IsSpaceOrNewLine( *in ) ) {
++in;
}
return std::string(cur,(size_t)(in-cur));
}
// ---------------------------------------------------------------------------------
} // ! namespace Assimp
#endif // ! AI_PARSING_UTILS_H_INC

View File

@ -0,0 +1,99 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Profiler.h
* @brief Utility to measure the respective runtime of each import step
*/
#ifndef INCLUDED_PROFILER_H
#define INCLUDED_PROFILER_H
#include <chrono>
#include <assimp/DefaultLogger.hpp>
#include "TinyFormatter.h"
#include <map>
namespace Assimp {
namespace Profiling {
using namespace Formatter;
// ------------------------------------------------------------------------------------------------
/** Simple wrapper around boost::timer to simplify reporting. Timings are automatically
* dumped to the log file.
*/
class Profiler {
public:
Profiler() {
// empty
}
public:
/** Start a named timer */
void BeginRegion(const std::string& region) {
regions[region] = std::chrono::system_clock::now();
ASSIMP_LOG_DEBUG((format("START `"),region,"`"));
}
/** End a specific named timer and write its end time to the log */
void EndRegion(const std::string& region) {
RegionMap::const_iterator it = regions.find(region);
if (it == regions.end()) {
return;
}
std::chrono::duration<double> elapsedSeconds = std::chrono::system_clock::now() - regions[region];
ASSIMP_LOG_DEBUG((format("END `"),region,"`, dt= ", elapsedSeconds.count()," s"));
}
private:
typedef std::map<std::string,std::chrono::time_point<std::chrono::system_clock>> RegionMap;
RegionMap regions;
};
}
}
#endif

View File

@ -0,0 +1,145 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file ProgressHandler.hpp
* @brief Abstract base class 'ProgressHandler'.
*/
#pragma once
#ifndef AI_PROGRESSHANDLER_H_INC
#define AI_PROGRESSHANDLER_H_INC
#include "types.h"
namespace Assimp {
// ------------------------------------------------------------------------------------
/** @brief CPP-API: Abstract interface for custom progress report receivers.
*
* Each #Importer instance maintains its own #ProgressHandler. The default
* implementation provided by Assimp doesn't do anything at all. */
class ASSIMP_API ProgressHandler
#ifndef SWIG
: public Intern::AllocateFromAssimpHeap
#endif
{
protected:
/// @brief Default constructor
ProgressHandler () AI_NO_EXCEPT {
// empty
}
public:
/// @brief Virtual destructor.
virtual ~ProgressHandler () {
}
// -------------------------------------------------------------------
/** @brief Progress callback.
* @param percentage An estimate of the current loading progress,
* in percent. Or -1.f if such an estimate is not available.
*
* There are restriction on what you may do from within your
* implementation of this method: no exceptions may be thrown and no
* non-const #Importer methods may be called. It is
* not generally possible to predict the number of callbacks
* fired during a single import.
*
* @return Return false to abort loading at the next possible
* occasion (loaders and Assimp are generally allowed to perform
* all needed cleanup tasks prior to returning control to the
* caller). If the loading is aborted, #Importer::ReadFile()
* returns always NULL.
* */
virtual bool Update(float percentage = -1.f) = 0;
// -------------------------------------------------------------------
/** @brief Progress callback for file loading steps
* @param numberOfSteps The number of total post-processing
* steps
* @param currentStep The index of the current post-processing
* step that will run, or equal to numberOfSteps if all of
* them has finished. This number is always strictly monotone
* increasing, although not necessarily linearly.
*
* @note This is currently only used at the start and the end
* of the file parsing.
* */
virtual void UpdateFileRead(int currentStep /*= 0*/, int numberOfSteps /*= 0*/) {
float f = numberOfSteps ? currentStep / (float)numberOfSteps : 1.0f;
Update( f * 0.5f );
}
// -------------------------------------------------------------------
/** @brief Progress callback for post-processing steps
* @param numberOfSteps The number of total post-processing
* steps
* @param currentStep The index of the current post-processing
* step that will run, or equal to numberOfSteps if all of
* them has finished. This number is always strictly monotone
* increasing, although not necessarily linearly.
* */
virtual void UpdatePostProcess(int currentStep /*= 0*/, int numberOfSteps /*= 0*/) {
float f = numberOfSteps ? currentStep / (float)numberOfSteps : 1.0f;
Update( f * 0.5f + 0.5f );
}
// -------------------------------------------------------------------
/** @brief Progress callback for export steps.
* @param numberOfSteps The number of total processing
* steps
* @param currentStep The index of the current post-processing
* step that will run, or equal to numberOfSteps if all of
* them has finished. This number is always strictly monotone
* increasing, although not necessarily linearly.
* */
virtual void UpdateFileWrite(int currentStep /*= 0*/, int numberOfSteps /*= 0*/) {
float f = numberOfSteps ? currentStep / (float)numberOfSteps : 1.0f;
Update(f * 0.5f);
}
}; // !class ProgressHandler
// ------------------------------------------------------------------------------------
} // Namespace Assimp
#endif // AI_PROGRESSHANDLER_H_INC

View File

@ -0,0 +1,91 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Declares a helper class, "CommentRemover", which can be
* used to remove comments (single and multi line) from a text file.
*/
#ifndef AI_REMOVE_COMMENTS_H_INC
#define AI_REMOVE_COMMENTS_H_INC
#include <assimp/defs.h>
namespace Assimp {
// ---------------------------------------------------------------------------
/** \brief Helper class to remove single and multi line comments from a file
*
* Some mesh formats like MD5 have comments that are quite similar
* to those in C or C++ so this code has been moved to a separate
* module.
*/
class ASSIMP_API CommentRemover
{
// class cannot be instanced
CommentRemover() {}
public:
//! Remove single-line comments. The end of a line is
//! expected to be either NL or CR or NLCR.
//! \param szComment The start sequence of the comment, e.g. "//"
//! \param szBuffer Buffer to work with
//! \param chReplacement Character to be used as replacement
//! for commented lines. By default this is ' '
static void RemoveLineComments(const char* szComment,
char* szBuffer, char chReplacement = ' ');
//! Remove multi-line comments. The end of a line is
//! expected to be either NL or CR or NLCR. Multi-line comments
//! may not be nested (as in C).
//! \param szCommentStart The start sequence of the comment, e.g. "/*"
//! \param szCommentEnd The end sequence of the comment, e.g. "*/"
//! \param szBuffer Buffer to work with
//! \param chReplacement Character to be used as replacement
//! for commented lines. By default this is ' '
static void RemoveMultiLineComments(const char* szCommentStart,
const char* szCommentEnd,char* szBuffer,
char chReplacement = ' ');
};
} // ! Assimp
#endif // !! AI_REMOVE_COMMENTS_H_INC

View File

@ -0,0 +1,150 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** Small helper classes to optimize finding vertices close to a given location
*/
#ifndef AI_D3DSSPATIALSORT_H_INC
#define AI_D3DSSPATIALSORT_H_INC
#include <assimp/types.h>
#include <vector>
#include <stdint.h>
namespace Assimp {
// ----------------------------------------------------------------------------------
/** Specialized version of SpatialSort to support smoothing groups
* This is used in by the 3DS, ASE and LWO loaders. 3DS and ASE share their
* normal computation code in SmoothingGroups.inl, the LWO loader has its own
* implementation to handle all details of its file format correctly.
*/
// ----------------------------------------------------------------------------------
class ASSIMP_API SGSpatialSort
{
public:
SGSpatialSort();
// -------------------------------------------------------------------
/** Construction from a given face array, handling smoothing groups
* properly
*/
explicit SGSpatialSort(const std::vector<aiVector3D>& vPositions);
// -------------------------------------------------------------------
/** Add a vertex to the spatial sort
* @param vPosition Vertex position to be added
* @param index Index of the vrtex
* @param smoothingGroup SmoothingGroup for this vertex
*/
void Add(const aiVector3D& vPosition, unsigned int index,
unsigned int smoothingGroup);
// -------------------------------------------------------------------
/** Prepare the spatial sorter for use. This step runs in O(logn)
*/
void Prepare();
/** Destructor */
~SGSpatialSort();
// -------------------------------------------------------------------
/** Returns an iterator for all positions close to the given position.
* @param pPosition The position to look for vertices.
* @param pSG Only included vertices with at least one shared smooth group
* @param pRadius Maximal distance from the position a vertex may have
* to be counted in.
* @param poResults The container to store the indices of the found
* positions. Will be emptied by the call so it may contain anything.
* @param exactMatch Specifies whether smoothing groups are bit masks
* (false) or integral values (true). In the latter case, a vertex
* cannot belong to more than one smoothing group.
* @return An iterator to iterate over all vertices in the given area.
*/
// -------------------------------------------------------------------
void FindPositions( const aiVector3D& pPosition, uint32_t pSG,
float pRadius, std::vector<unsigned int>& poResults,
bool exactMatch = false) const;
protected:
/** Normal of the sorting plane, normalized. The center is always at (0, 0, 0) */
aiVector3D mPlaneNormal;
// -------------------------------------------------------------------
/** An entry in a spatially sorted position array. Consists of a
* vertex index, its position and its pre-calculated distance from
* the reference plane */
// -------------------------------------------------------------------
struct Entry {
unsigned int mIndex; ///< The vertex referred by this entry
aiVector3D mPosition; ///< Position
uint32_t mSmoothGroups;
float mDistance; ///< Distance of this vertex to the sorting plane
Entry() AI_NO_EXCEPT
: mIndex(0)
, mPosition()
, mSmoothGroups(0)
, mDistance(0.0f) {
// empty
}
Entry( unsigned int pIndex, const aiVector3D& pPosition, float pDistance,uint32_t pSG)
: mIndex( pIndex)
, mPosition( pPosition)
, mSmoothGroups(pSG)
, mDistance( pDistance) {
// empty
}
bool operator < (const Entry& e) const {
return mDistance < e.mDistance;
}
};
// all positions, sorted by distance to the sorting plane
std::vector<Entry> mPositions;
};
} // end of namespace Assimp
#endif // AI_SPATIALSORT_H_INC

View File

@ -0,0 +1,403 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Declares a helper class, "SceneCombiner" providing various
* utilities to merge scenes.
*/
#ifndef AI_SCENE_COMBINER_H_INC
#define AI_SCENE_COMBINER_H_INC
#include <assimp/ai_assert.h>
#include <assimp/types.h>
#include <assimp/Defines.h>
#include <stddef.h>
#include <set>
#include <list>
#include <stdint.h>
#include <vector>
struct aiScene;
struct aiNode;
struct aiMaterial;
struct aiTexture;
struct aiCamera;
struct aiLight;
struct aiMetadata;
struct aiBone;
struct aiMesh;
struct aiAnimMesh;
struct aiAnimation;
struct aiNodeAnim;
namespace Assimp {
// ---------------------------------------------------------------------------
/** \brief Helper data structure for SceneCombiner.
*
* Describes to which node a scene must be attached to.
*/
struct AttachmentInfo
{
AttachmentInfo()
: scene (NULL)
, attachToNode (NULL)
{}
AttachmentInfo(aiScene* _scene, aiNode* _attachToNode)
: scene (_scene)
, attachToNode (_attachToNode)
{}
aiScene* scene;
aiNode* attachToNode;
};
// ---------------------------------------------------------------------------
struct NodeAttachmentInfo
{
NodeAttachmentInfo()
: node (NULL)
, attachToNode (NULL)
, resolved (false)
, src_idx (SIZE_MAX)
{}
NodeAttachmentInfo(aiNode* _scene, aiNode* _attachToNode,size_t idx)
: node (_scene)
, attachToNode (_attachToNode)
, resolved (false)
, src_idx (idx)
{}
aiNode* node;
aiNode* attachToNode;
bool resolved;
size_t src_idx;
};
// ---------------------------------------------------------------------------
/** @def AI_INT_MERGE_SCENE_GEN_UNIQUE_NAMES
* Generate unique names for all named scene items
*/
#define AI_INT_MERGE_SCENE_GEN_UNIQUE_NAMES 0x1
/** @def AI_INT_MERGE_SCENE_GEN_UNIQUE_MATNAMES
* Generate unique names for materials, too.
* This is not absolutely required to pass the validation.
*/
#define AI_INT_MERGE_SCENE_GEN_UNIQUE_MATNAMES 0x2
/** @def AI_INT_MERGE_SCENE_DUPLICATES_DEEP_CPY
* Use deep copies of duplicate scenes
*/
#define AI_INT_MERGE_SCENE_DUPLICATES_DEEP_CPY 0x4
/** @def AI_INT_MERGE_SCENE_RESOLVE_CROSS_ATTACHMENTS
* If attachment nodes are not found in the given master scene,
* search the other imported scenes for them in an any order.
*/
#define AI_INT_MERGE_SCENE_RESOLVE_CROSS_ATTACHMENTS 0x8
/** @def AI_INT_MERGE_SCENE_GEN_UNIQUE_NAMES_IF_NECESSARY
* Can be combined with AI_INT_MERGE_SCENE_GEN_UNIQUE_NAMES.
* Unique names are generated, but only if this is absolutely
* required to avoid name conflicts.
*/
#define AI_INT_MERGE_SCENE_GEN_UNIQUE_NAMES_IF_NECESSARY 0x10
typedef std::pair<aiBone*,unsigned int> BoneSrcIndex;
// ---------------------------------------------------------------------------
/** @brief Helper data structure for SceneCombiner::MergeBones.
*/
struct BoneWithHash : public std::pair<uint32_t,aiString*> {
std::vector<BoneSrcIndex> pSrcBones;
};
// ---------------------------------------------------------------------------
/** @brief Utility for SceneCombiner
*/
struct SceneHelper
{
SceneHelper ()
: scene (NULL)
, idlen (0)
{
id[0] = 0;
}
explicit SceneHelper (aiScene* _scene)
: scene (_scene)
, idlen (0)
{
id[0] = 0;
}
AI_FORCE_INLINE aiScene* operator-> () const
{
return scene;
}
// scene we're working on
aiScene* scene;
// prefix to be added to all identifiers in the scene ...
char id [32];
// and its strlen()
unsigned int idlen;
// hash table to quickly check whether a name is contained in the scene
std::set<unsigned int> hashes;
};
// ---------------------------------------------------------------------------
/** \brief Static helper class providing various utilities to merge two
* scenes. It is intended as internal utility and NOT for use by
* applications.
*
* The class is currently being used by various postprocessing steps
* and loaders (ie. LWS).
*/
class ASSIMP_API SceneCombiner {
// class cannot be instanced
SceneCombiner() {
// empty
}
~SceneCombiner() {
// empty
}
public:
// -------------------------------------------------------------------
/** Merges two or more scenes.
*
* @param dest Receives a pointer to the destination scene. If the
* pointer doesn't point to NULL when the function is called, the
* existing scene is cleared and refilled.
* @param src Non-empty list of scenes to be merged. The function
* deletes the input scenes afterwards. There may be duplicate scenes.
* @param flags Combination of the AI_INT_MERGE_SCENE flags defined above
*/
static void MergeScenes(aiScene** dest,std::vector<aiScene*>& src,
unsigned int flags = 0);
// -------------------------------------------------------------------
/** Merges two or more scenes and attaches all scenes to a specific
* position in the node graph of the master scene.
*
* @param dest Receives a pointer to the destination scene. If the
* pointer doesn't point to NULL when the function is called, the
* existing scene is cleared and refilled.
* @param master Master scene. It will be deleted afterwards. All
* other scenes will be inserted in its node graph.
* @param src Non-empty list of scenes to be merged along with their
* corresponding attachment points in the master scene. The function
* deletes the input scenes afterwards. There may be duplicate scenes.
* @param flags Combination of the AI_INT_MERGE_SCENE flags defined above
*/
static void MergeScenes(aiScene** dest, aiScene* master,
std::vector<AttachmentInfo>& src,
unsigned int flags = 0);
// -------------------------------------------------------------------
/** Merges two or more meshes
*
* The meshes should have equal vertex formats. Only components
* that are provided by ALL meshes will be present in the output mesh.
* An exception is made for VColors - they are set to black. The
* meshes should have the same material indices, too. The output
* material index is always the material index of the first mesh.
*
* @param dest Destination mesh. Must be empty.
* @param flags Currently no parameters
* @param begin First mesh to be processed
* @param end Points to the mesh after the last mesh to be processed
*/
static void MergeMeshes(aiMesh** dest,unsigned int flags,
std::vector<aiMesh*>::const_iterator begin,
std::vector<aiMesh*>::const_iterator end);
// -------------------------------------------------------------------
/** Merges two or more bones
*
* @param out Mesh to receive the output bone list
* @param flags Currently no parameters
* @param begin First mesh to be processed
* @param end Points to the mesh after the last mesh to be processed
*/
static void MergeBones(aiMesh* out,std::vector<aiMesh*>::const_iterator it,
std::vector<aiMesh*>::const_iterator end);
// -------------------------------------------------------------------
/** Merges two or more materials
*
* The materials should be complementary as much as possible. In case
* of a property present in different materials, the first occurrence
* is used.
*
* @param dest Destination material. Must be empty.
* @param begin First material to be processed
* @param end Points to the material after the last material to be processed
*/
static void MergeMaterials(aiMaterial** dest,
std::vector<aiMaterial*>::const_iterator begin,
std::vector<aiMaterial*>::const_iterator end);
// -------------------------------------------------------------------
/** Builds a list of uniquely named bones in a mesh list
*
* @param asBones Receives the output list
* @param it First mesh to be processed
* @param end Last mesh to be processed
*/
static void BuildUniqueBoneList(std::list<BoneWithHash>& asBones,
std::vector<aiMesh*>::const_iterator it,
std::vector<aiMesh*>::const_iterator end);
// -------------------------------------------------------------------
/** Add a name prefix to all nodes in a scene.
*
* @param Current node. This function is called recursively.
* @param prefix Prefix to be added to all nodes
* @param len STring length
*/
static void AddNodePrefixes(aiNode* node, const char* prefix,
unsigned int len);
// -------------------------------------------------------------------
/** Add an offset to all mesh indices in a node graph
*
* @param Current node. This function is called recursively.
* @param offset Offset to be added to all mesh indices
*/
static void OffsetNodeMeshIndices (aiNode* node, unsigned int offset);
// -------------------------------------------------------------------
/** Attach a list of node graphs to well-defined nodes in a master
* graph. This is a helper for MergeScenes()
*
* @param master Master scene
* @param srcList List of source scenes along with their attachment
* points. If an attachment point is NULL (or does not exist in
* the master graph), a scene is attached to the root of the master
* graph (as an additional child node)
* @duplicates List of duplicates. If elem[n] == n the scene is not
* a duplicate. Otherwise elem[n] links scene n to its first occurrence.
*/
static void AttachToGraph ( aiScene* master,
std::vector<NodeAttachmentInfo>& srcList);
static void AttachToGraph (aiNode* attach,
std::vector<NodeAttachmentInfo>& srcList);
// -------------------------------------------------------------------
/** Get a deep copy of a scene
*
* @param dest Receives a pointer to the destination scene
* @param src Source scene - remains unmodified.
*/
static void CopyScene(aiScene** dest,const aiScene* source,bool allocate = true);
// -------------------------------------------------------------------
/** Get a flat copy of a scene
*
* Only the first hierarchy layer is copied. All pointer members of
* aiScene are shared by source and destination scene. If the
* pointer doesn't point to NULL when the function is called, the
* existing scene is cleared and refilled.
* @param dest Receives a pointer to the destination scene
* @param src Source scene - remains unmodified.
*/
static void CopySceneFlat(aiScene** dest,const aiScene* source);
// -------------------------------------------------------------------
/** Get a deep copy of a mesh
*
* @param dest Receives a pointer to the destination mesh
* @param src Source mesh - remains unmodified.
*/
static void Copy (aiMesh** dest, const aiMesh* src);
// similar to Copy():
static void Copy (aiAnimMesh** dest, const aiAnimMesh* src);
static void Copy (aiMaterial** dest, const aiMaterial* src);
static void Copy (aiTexture** dest, const aiTexture* src);
static void Copy (aiAnimation** dest, const aiAnimation* src);
static void Copy (aiCamera** dest, const aiCamera* src);
static void Copy (aiBone** dest, const aiBone* src);
static void Copy (aiLight** dest, const aiLight* src);
static void Copy (aiNodeAnim** dest, const aiNodeAnim* src);
static void Copy (aiMetadata** dest, const aiMetadata* src);
// recursive, of course
static void Copy (aiNode** dest, const aiNode* src);
private:
// -------------------------------------------------------------------
// Same as AddNodePrefixes, but with an additional check
static void AddNodePrefixesChecked(aiNode* node, const char* prefix,
unsigned int len,
std::vector<SceneHelper>& input,
unsigned int cur);
// -------------------------------------------------------------------
// Add node identifiers to a hashing set
static void AddNodeHashes(aiNode* node, std::set<unsigned int>& hashes);
// -------------------------------------------------------------------
// Search for duplicate names
static bool FindNameMatch(const aiString& name,
std::vector<SceneHelper>& input, unsigned int cur);
};
}
#endif // !! AI_SCENE_COMBINER_H_INC

View File

@ -0,0 +1,125 @@
/** Helper class to construct a dummy mesh for file formats containing only motion data */
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file SkeletonMeshBuilder.h
* Declares SkeletonMeshBuilder, a tiny utility to build dummy meshes
* for animation skeletons.
*/
#ifndef AI_SKELETONMESHBUILDER_H_INC
#define AI_SKELETONMESHBUILDER_H_INC
#include <vector>
#include <assimp/mesh.h>
struct aiMaterial;
struct aiScene;
struct aiNode;
namespace Assimp {
// ---------------------------------------------------------------------------
/**
* This little helper class constructs a dummy mesh for a given scene
* the resembles the node hierarchy. This is useful for file formats
* that don't carry any mesh data but only animation data.
*/
class ASSIMP_API SkeletonMeshBuilder
{
public:
// -------------------------------------------------------------------
/** The constructor processes the given scene and adds a mesh there.
*
* Does nothing if the scene already has mesh data.
* @param pScene The scene for which a skeleton mesh should be constructed.
* @param root The node to start with. NULL is the scene root
* @param bKnobsOnly Set this to true if you don't want the connectors
* between the knobs representing the nodes.
*/
SkeletonMeshBuilder( aiScene* pScene, aiNode* root = NULL,
bool bKnobsOnly = false);
protected:
// -------------------------------------------------------------------
/** Recursively builds a simple mesh representation for the given node
* and also creates a joint for the node that affects this part of
* the mesh.
* @param pNode The node to build geometry for.
*/
void CreateGeometry( const aiNode* pNode);
// -------------------------------------------------------------------
/** Creates the mesh from the internally accumulated stuff and returns it.
*/
aiMesh* CreateMesh();
// -------------------------------------------------------------------
/** Creates a dummy material and returns it. */
aiMaterial* CreateMaterial();
protected:
/** space to assemble the mesh data: points */
std::vector<aiVector3D> mVertices;
/** faces */
struct Face
{
unsigned int mIndices[3];
Face();
Face( unsigned int p0, unsigned int p1, unsigned int p2)
{ mIndices[0] = p0; mIndices[1] = p1; mIndices[2] = p2; }
};
std::vector<Face> mFaces;
/** bones */
std::vector<aiBone*> mBones;
bool mKnobsOnly;
};
} // end of namespace Assimp
#endif // AI_SKELETONMESHBUILDER_H_INC

View File

@ -0,0 +1,108 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Defines the helper data structures for importing 3DS files.
http://www.jalix.org/ressources/graphics/3DS/_unofficials/3ds-unofficial.txt */
#ifndef AI_SMOOTHINGGROUPS_H_INC
#define AI_SMOOTHINGGROUPS_H_INC
#include <assimp/vector3.h>
#include <stdint.h>
#include <vector>
// ---------------------------------------------------------------------------
/** Helper structure representing a face with smoothing groups assigned */
struct FaceWithSmoothingGroup {
FaceWithSmoothingGroup() AI_NO_EXCEPT
: mIndices()
, iSmoothGroup(0) {
// in debug builds set all indices to a common magic value
#ifdef ASSIMP_BUILD_DEBUG
this->mIndices[0] = 0xffffffff;
this->mIndices[1] = 0xffffffff;
this->mIndices[2] = 0xffffffff;
#endif
}
//! Indices. .3ds is using uint16. However, after
//! an unique vertex set has been generated,
//! individual index values might exceed 2^16
uint32_t mIndices[3];
//! specifies to which smoothing group the face belongs to
uint32_t iSmoothGroup;
};
// ---------------------------------------------------------------------------
/** Helper structure representing a mesh whose faces have smoothing
groups assigned. This allows us to reuse the code for normal computations
from smoothings groups for several loaders (3DS, ASE). All of them
use face structures which inherit from #FaceWithSmoothingGroup,
but as they add extra members and need to be copied by value we
need to use a template here.
*/
template <class T>
struct MeshWithSmoothingGroups
{
//! Vertex positions
std::vector<aiVector3D> mPositions;
//! Face lists
std::vector<T> mFaces;
//! List of normal vectors
std::vector<aiVector3D> mNormals;
};
// ---------------------------------------------------------------------------
/** Computes normal vectors for the mesh
*/
template <class T>
void ComputeNormalsWithSmoothingsGroups(MeshWithSmoothingGroups<T>& sMesh);
// include implementations
#include "SmoothingGroups.inl"
#endif // !! AI_SMOOTHINGGROUPS_H_INC

View File

@ -0,0 +1,138 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2012, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Generation of normal vectors basing on smoothing groups */
#ifndef AI_SMOOTHINGGROUPS_INL_INCLUDED
#define AI_SMOOTHINGGROUPS_INL_INCLUDED
// internal headers
#include <assimp/SGSpatialSort.h>
// CRT header
#include <algorithm>
using namespace Assimp;
// ------------------------------------------------------------------------------------------------
template <class T>
void ComputeNormalsWithSmoothingsGroups(MeshWithSmoothingGroups<T>& sMesh)
{
// First generate face normals
sMesh.mNormals.resize(sMesh.mPositions.size(),aiVector3D());
for( unsigned int a = 0; a < sMesh.mFaces.size(); a++)
{
T& face = sMesh.mFaces[a];
aiVector3D* pV1 = &sMesh.mPositions[face.mIndices[0]];
aiVector3D* pV2 = &sMesh.mPositions[face.mIndices[1]];
aiVector3D* pV3 = &sMesh.mPositions[face.mIndices[2]];
aiVector3D pDelta1 = *pV2 - *pV1;
aiVector3D pDelta2 = *pV3 - *pV1;
aiVector3D vNor = pDelta1 ^ pDelta2;
for (unsigned int c = 0; c < 3;++c)
sMesh.mNormals[face.mIndices[c]] = vNor;
}
// calculate the position bounds so we have a reliable epsilon to check position differences against
aiVector3D minVec( 1e10f, 1e10f, 1e10f), maxVec( -1e10f, -1e10f, -1e10f);
for( unsigned int a = 0; a < sMesh.mPositions.size(); a++)
{
minVec.x = std::min( minVec.x, sMesh.mPositions[a].x);
minVec.y = std::min( minVec.y, sMesh.mPositions[a].y);
minVec.z = std::min( minVec.z, sMesh.mPositions[a].z);
maxVec.x = std::max( maxVec.x, sMesh.mPositions[a].x);
maxVec.y = std::max( maxVec.y, sMesh.mPositions[a].y);
maxVec.z = std::max( maxVec.z, sMesh.mPositions[a].z);
}
const float posEpsilon = (maxVec - minVec).Length() * 1e-5f;
std::vector<aiVector3D> avNormals;
avNormals.resize(sMesh.mNormals.size());
// now generate the spatial sort tree
SGSpatialSort sSort;
for( typename std::vector<T>::iterator i = sMesh.mFaces.begin();
i != sMesh.mFaces.end();++i)
{
for (unsigned int c = 0; c < 3;++c)
sSort.Add(sMesh.mPositions[(*i).mIndices[c]],(*i).mIndices[c],(*i).iSmoothGroup);
}
sSort.Prepare();
std::vector<bool> vertexDone(sMesh.mPositions.size(),false);
for( typename std::vector<T>::iterator i = sMesh.mFaces.begin();
i != sMesh.mFaces.end();++i)
{
std::vector<unsigned int> poResult;
for (unsigned int c = 0; c < 3;++c)
{
unsigned int idx = (*i).mIndices[c];
if (vertexDone[idx])continue;
sSort.FindPositions(sMesh.mPositions[idx],(*i).iSmoothGroup,
posEpsilon,poResult);
aiVector3D vNormals;
for (std::vector<unsigned int>::const_iterator
a = poResult.begin();
a != poResult.end();++a)
{
vNormals += sMesh.mNormals[(*a)];
}
vNormals.NormalizeSafe();
// write back into all affected normals
for (std::vector<unsigned int>::const_iterator
a = poResult.begin();
a != poResult.end();++a)
{
idx = *a;
avNormals [idx] = vNormals;
vertexDone[idx] = true;
}
}
}
sMesh.mNormals = avNormals;
}
#endif // !! AI_SMOOTHINGGROUPS_INL_INCLUDED

View File

@ -0,0 +1,174 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** Small helper classes to optimise finding vertizes close to a given location */
#ifndef AI_SPATIALSORT_H_INC
#define AI_SPATIALSORT_H_INC
#include <vector>
#include <assimp/types.h>
namespace Assimp {
// ------------------------------------------------------------------------------------------------
/** A little helper class to quickly find all vertices in the epsilon environment of a given
* position. Construct an instance with an array of positions. The class stores the given positions
* by their indices and sorts them by their distance to an arbitrary chosen plane.
* You can then query the instance for all vertices close to a given position in an average O(log n)
* time, with O(n) worst case complexity when all vertices lay on the plane. The plane is chosen
* so that it avoids common planes in usual data sets. */
// ------------------------------------------------------------------------------------------------
class ASSIMP_API SpatialSort
{
public:
SpatialSort();
// ------------------------------------------------------------------------------------
/** Constructs a spatially sorted representation from the given position array.
* Supply the positions in its layout in memory, the class will only refer to them
* by index.
* @param pPositions Pointer to the first position vector of the array.
* @param pNumPositions Number of vectors to expect in that array.
* @param pElementOffset Offset in bytes from the beginning of one vector in memory
* to the beginning of the next vector. */
SpatialSort( const aiVector3D* pPositions, unsigned int pNumPositions,
unsigned int pElementOffset);
/** Destructor */
~SpatialSort();
public:
// ------------------------------------------------------------------------------------
/** Sets the input data for the SpatialSort. This replaces existing data, if any.
* The new data receives new indices in ascending order.
*
* @param pPositions Pointer to the first position vector of the array.
* @param pNumPositions Number of vectors to expect in that array.
* @param pElementOffset Offset in bytes from the beginning of one vector in memory
* to the beginning of the next vector.
* @param pFinalize Specifies whether the SpatialSort's internal representation
* is finalized after the new data has been added. Finalization is
* required in order to use #FindPosition() or #GenerateMappingTable().
* If you don't finalize yet, you can use #Append() to add data from
* other sources.*/
void Fill( const aiVector3D* pPositions, unsigned int pNumPositions,
unsigned int pElementOffset,
bool pFinalize = true);
// ------------------------------------------------------------------------------------
/** Same as #Fill(), except the method appends to existing data in the #SpatialSort. */
void Append( const aiVector3D* pPositions, unsigned int pNumPositions,
unsigned int pElementOffset,
bool pFinalize = true);
// ------------------------------------------------------------------------------------
/** Finalize the spatial hash data structure. This can be useful after
* multiple calls to #Append() with the pFinalize parameter set to false.
* This is finally required before one of #FindPositions() and #GenerateMappingTable()
* can be called to query the spatial sort.*/
void Finalize();
// ------------------------------------------------------------------------------------
/** Returns an iterator for all positions close to the given position.
* @param pPosition The position to look for vertices.
* @param pRadius Maximal distance from the position a vertex may have to be counted in.
* @param poResults The container to store the indices of the found positions.
* Will be emptied by the call so it may contain anything.
* @return An iterator to iterate over all vertices in the given area.*/
void FindPositions( const aiVector3D& pPosition, ai_real pRadius,
std::vector<unsigned int>& poResults) const;
// ------------------------------------------------------------------------------------
/** Fills an array with indices of all positions identical to the given position. In
* opposite to FindPositions(), not an epsilon is used but a (very low) tolerance of
* four floating-point units.
* @param pPosition The position to look for vertices.
* @param poResults The container to store the indices of the found positions.
* Will be emptied by the call so it may contain anything.*/
void FindIdenticalPositions( const aiVector3D& pPosition,
std::vector<unsigned int>& poResults) const;
// ------------------------------------------------------------------------------------
/** Compute a table that maps each vertex ID referring to a spatially close
* enough position to the same output ID. Output IDs are assigned in ascending order
* from 0...n.
* @param fill Will be filled with numPositions entries.
* @param pRadius Maximal distance from the position a vertex may have to
* be counted in.
* @return Number of unique vertices (n). */
unsigned int GenerateMappingTable(std::vector<unsigned int>& fill,
ai_real pRadius) const;
protected:
/** Normal of the sorting plane, normalized. The center is always at (0, 0, 0) */
aiVector3D mPlaneNormal;
/** An entry in a spatially sorted position array. Consists of a vertex index,
* its position and its pre-calculated distance from the reference plane */
struct Entry {
unsigned int mIndex; ///< The vertex referred by this entry
aiVector3D mPosition; ///< Position
ai_real mDistance; ///< Distance of this vertex to the sorting plane
Entry() AI_NO_EXCEPT
: mIndex( 999999999 ), mPosition(), mDistance( 99999. ) {
// empty
}
Entry( unsigned int pIndex, const aiVector3D& pPosition, ai_real pDistance)
: mIndex( pIndex), mPosition( pPosition), mDistance( pDistance) {
// empty
}
bool operator < (const Entry& e) const { return mDistance < e.mDistance; }
};
// all positions, sorted by distance to the sorting plane
std::vector<Entry> mPositions;
};
} // end of namespace Assimp
#endif // AI_SPATIALSORT_H_INC

View File

@ -0,0 +1,200 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Declares a helper class, "StandardShapes" which generates
* vertices for standard shapes, such as cylnders, cones, spheres ..
*/
#ifndef AI_STANDARD_SHAPES_H_INC
#define AI_STANDARD_SHAPES_H_INC
#include <assimp/vector3.h>
#include <vector>
struct aiMesh;
namespace Assimp {
// ---------------------------------------------------------------------------
/** \brief Helper class to generate vertex buffers for standard geometric
* shapes, such as cylinders, cones, boxes, spheres, elipsoids ... .
*/
class ASSIMP_API StandardShapes
{
// class cannot be instanced
StandardShapes() {}
public:
// ----------------------------------------------------------------
/** Generates a mesh from an array of vertex positions.
*
* @param positions List of vertex positions
* @param numIndices Number of indices per primitive
* @return Output mesh
*/
static aiMesh* MakeMesh(const std::vector<aiVector3D>& positions,
unsigned int numIndices);
static aiMesh* MakeMesh ( unsigned int (*GenerateFunc)
(std::vector<aiVector3D>&));
static aiMesh* MakeMesh ( unsigned int (*GenerateFunc)
(std::vector<aiVector3D>&, bool));
static aiMesh* MakeMesh ( unsigned int n, void (*GenerateFunc)
(unsigned int,std::vector<aiVector3D>&));
// ----------------------------------------------------------------
/** @brief Generates a hexahedron (cube)
*
* Hexahedrons can be scaled on all axes.
* @param positions Receives output triangles.
* @param polygons If you pass true here quads will be returned
* @return Number of vertices per face
*/
static unsigned int MakeHexahedron(
std::vector<aiVector3D>& positions,
bool polygons = false);
// ----------------------------------------------------------------
/** @brief Generates an icosahedron
*
* @param positions Receives output triangles.
* @return Number of vertices per face
*/
static unsigned int MakeIcosahedron(
std::vector<aiVector3D>& positions);
// ----------------------------------------------------------------
/** @brief Generates a dodecahedron
*
* @param positions Receives output triangles
* @param polygons If you pass true here pentagons will be returned
* @return Number of vertices per face
*/
static unsigned int MakeDodecahedron(
std::vector<aiVector3D>& positions,
bool polygons = false);
// ----------------------------------------------------------------
/** @brief Generates an octahedron
*
* @param positions Receives output triangles.
* @return Number of vertices per face
*/
static unsigned int MakeOctahedron(
std::vector<aiVector3D>& positions);
// ----------------------------------------------------------------
/** @brief Generates a tetrahedron
*
* @param positions Receives output triangles.
* @return Number of vertices per face
*/
static unsigned int MakeTetrahedron(
std::vector<aiVector3D>& positions);
// ----------------------------------------------------------------
/** @brief Generates a sphere
*
* @param tess Number of subdivions - 0 generates a octahedron
* @param positions Receives output triangles.
*/
static void MakeSphere(unsigned int tess,
std::vector<aiVector3D>& positions);
// ----------------------------------------------------------------
/** @brief Generates a cone or a cylinder, either open or closed.
*
* @code
*
* |-----| <- radius 1
*
* __x__ <- ] ^
* / \ | height |
* / \ | Y
* / \ |
* / \ |
* /______x______\ <- ] <- end cap
*
* |-------------| <- radius 2
*
* @endcode
*
* @param height Height of the cone
* @param radius1 First radius
* @param radius2 Second radius
* @param tess Number of triangles.
* @param bOpened true for an open cone/cylinder. An open shape has
* no 'end caps'
* @param positions Receives output triangles
*/
static void MakeCone(ai_real height,ai_real radius1,
ai_real radius2,unsigned int tess,
std::vector<aiVector3D>& positions,bool bOpen= false);
// ----------------------------------------------------------------
/** @brief Generates a flat circle
*
* The circle is constructed in the planned formed by the x,z
* axes of the cartesian coordinate system.
*
* @param radius Radius of the circle
* @param tess Number of segments.
* @param positions Receives output triangles.
*/
static void MakeCircle(ai_real radius, unsigned int tess,
std::vector<aiVector3D>& positions);
};
} // ! Assimp
#endif // !! AI_STANDARD_SHAPES_H_INC

View File

@ -0,0 +1,343 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Defines the StreamReader class which reads data from
* a binary stream with a well-defined endianness.
*/
#ifndef AI_STREAMREADER_H_INCLUDED
#define AI_STREAMREADER_H_INCLUDED
#include <assimp/IOStream.hpp>
#include <assimp/Defines.h>
#include "ByteSwapper.h"
#include "Exceptional.h"
#include <memory>
namespace Assimp {
// --------------------------------------------------------------------------------------------
/** Wrapper class around IOStream to allow for consistent reading of binary data in both
* little and big endian format. Don't attempt to instance the template directly. Use
* StreamReaderLE to read from a little-endian stream and StreamReaderBE to read from a
* BE stream. The class expects that the endianness of any input data is known at
* compile-time, which should usually be true (#BaseImporter::ConvertToUTF8 implements
* runtime endianness conversions for text files).
*
* XXX switch from unsigned int for size types to size_t? or ptrdiff_t?*/
// --------------------------------------------------------------------------------------------
template <bool SwapEndianess = false, bool RuntimeSwitch = false>
class StreamReader {
public:
// FIXME: use these data types throughout the whole library,
// then change them to 64 bit values :-)
using diff = int;
using pos = unsigned int;
// ---------------------------------------------------------------------
/** Construction from a given stream with a well-defined endianness.
*
* The StreamReader holds a permanent strong reference to the
* stream, which is released upon destruction.
* @param stream Input stream. The stream is not restarted if
* its file pointer is not at 0. Instead, the stream reader
* reads from the current position to the end of the stream.
* @param le If @c RuntimeSwitch is true: specifies whether the
* stream is in little endian byte order. Otherwise the
* endianness information is contained in the @c SwapEndianess
* template parameter and this parameter is meaningless. */
StreamReader(std::shared_ptr<IOStream> stream, bool le = false)
: stream(stream)
, le(le)
{
ai_assert(stream);
InternBegin();
}
// ---------------------------------------------------------------------
StreamReader(IOStream* stream, bool le = false)
: stream(std::shared_ptr<IOStream>(stream))
, le(le)
{
ai_assert(stream);
InternBegin();
}
// ---------------------------------------------------------------------
~StreamReader() {
delete[] buffer;
}
// deprecated, use overloaded operator>> instead
// ---------------------------------------------------------------------
/** Read a float from the stream */
float GetF4()
{
return Get<float>();
}
// ---------------------------------------------------------------------
/** Read a double from the stream */
double GetF8() {
return Get<double>();
}
// ---------------------------------------------------------------------
/** Read a signed 16 bit integer from the stream */
int16_t GetI2() {
return Get<int16_t>();
}
// ---------------------------------------------------------------------
/** Read a signed 8 bit integer from the stream */
int8_t GetI1() {
return Get<int8_t>();
}
// ---------------------------------------------------------------------
/** Read an signed 32 bit integer from the stream */
int32_t GetI4() {
return Get<int32_t>();
}
// ---------------------------------------------------------------------
/** Read a signed 64 bit integer from the stream */
int64_t GetI8() {
return Get<int64_t>();
}
// ---------------------------------------------------------------------
/** Read a unsigned 16 bit integer from the stream */
uint16_t GetU2() {
return Get<uint16_t>();
}
// ---------------------------------------------------------------------
/** Read a unsigned 8 bit integer from the stream */
uint8_t GetU1() {
return Get<uint8_t>();
}
// ---------------------------------------------------------------------
/** Read an unsigned 32 bit integer from the stream */
uint32_t GetU4() {
return Get<uint32_t>();
}
// ---------------------------------------------------------------------
/** Read a unsigned 64 bit integer from the stream */
uint64_t GetU8() {
return Get<uint64_t>();
}
// ---------------------------------------------------------------------
/** Get the remaining stream size (to the end of the stream) */
unsigned int GetRemainingSize() const {
return (unsigned int)(end - current);
}
// ---------------------------------------------------------------------
/** Get the remaining stream size (to the current read limit). The
* return value is the remaining size of the stream if no custom
* read limit has been set. */
unsigned int GetRemainingSizeToLimit() const {
return (unsigned int)(limit - current);
}
// ---------------------------------------------------------------------
/** Increase the file pointer (relative seeking) */
void IncPtr(intptr_t plus) {
current += plus;
if (current > limit) {
throw DeadlyImportError("End of file or read limit was reached");
}
}
// ---------------------------------------------------------------------
/** Get the current file pointer */
int8_t* GetPtr() const {
return current;
}
// ---------------------------------------------------------------------
/** Set current file pointer (Get it from #GetPtr). This is if you
* prefer to do pointer arithmetics on your own or want to copy
* large chunks of data at once.
* @param p The new pointer, which is validated against the size
* limit and buffer boundaries. */
void SetPtr(int8_t* p) {
current = p;
if (current > limit || current < buffer) {
throw DeadlyImportError("End of file or read limit was reached");
}
}
// ---------------------------------------------------------------------
/** Copy n bytes to an external buffer
* @param out Destination for copying
* @param bytes Number of bytes to copy */
void CopyAndAdvance(void* out, size_t bytes) {
int8_t* ur = GetPtr();
SetPtr(ur+bytes); // fire exception if eof
::memcpy(out,ur,bytes);
}
// ---------------------------------------------------------------------
/** Get the current offset from the beginning of the file */
int GetCurrentPos() const {
return (unsigned int)(current - buffer);
}
void SetCurrentPos(size_t pos) {
SetPtr(buffer + pos);
}
// ---------------------------------------------------------------------
/** Setup a temporary read limit
*
* @param limit Maximum number of bytes to be read from
* the beginning of the file. Specifying UINT_MAX
* resets the limit to the original end of the stream.
* Returns the previously set limit. */
unsigned int SetReadLimit(unsigned int _limit) {
unsigned int prev = GetReadLimit();
if (UINT_MAX == _limit) {
limit = end;
return prev;
}
limit = buffer + _limit;
if (limit > end) {
throw DeadlyImportError("StreamReader: Invalid read limit");
}
return prev;
}
// ---------------------------------------------------------------------
/** Get the current read limit in bytes. Reading over this limit
* accidentally raises an exception. */
unsigned int GetReadLimit() const {
return (unsigned int)(limit - buffer);
}
// ---------------------------------------------------------------------
/** Skip to the read limit in bytes. Reading over this limit
* accidentally raises an exception. */
void SkipToReadLimit() {
current = limit;
}
// ---------------------------------------------------------------------
/** overload operator>> and allow chaining of >> ops. */
template <typename T>
StreamReader& operator >> (T& f) {
f = Get<T>();
return *this;
}
// ---------------------------------------------------------------------
/** Generic read method. ByteSwap::Swap(T*) *must* be defined */
template <typename T>
T Get() {
if ( current + sizeof(T) > limit) {
throw DeadlyImportError("End of file or stream limit was reached");
}
T f;
::memcpy (&f, current, sizeof(T));
Intern::Getter<SwapEndianess,T,RuntimeSwitch>() (&f,le);
current += sizeof(T);
return f;
}
private:
// ---------------------------------------------------------------------
void InternBegin() {
if (!stream) {
// in case someone wonders: StreamReader is frequently invoked with
// no prior validation whether the input stream is valid. Since
// no one bothers changing the error message, this message here
// is passed down to the caller and 'unable to open file'
// simply describes best what happened.
throw DeadlyImportError("StreamReader: Unable to open file");
}
const size_t s = stream->FileSize() - stream->Tell();
if (!s) {
throw DeadlyImportError("StreamReader: File is empty or EOF is already reached");
}
current = buffer = new int8_t[s];
const size_t read = stream->Read(current,1,s);
// (read < s) can only happen if the stream was opened in text mode, in which case FileSize() is not reliable
ai_assert(read <= s);
end = limit = &buffer[read-1] + 1;
}
private:
std::shared_ptr<IOStream> stream;
int8_t *buffer, *current, *end, *limit;
bool le;
};
// --------------------------------------------------------------------------------------------
// `static` StreamReaders. Their byte order is fixed and they might be a little bit faster.
#ifdef AI_BUILD_BIG_ENDIAN
typedef StreamReader<true> StreamReaderLE;
typedef StreamReader<false> StreamReaderBE;
#else
typedef StreamReader<true> StreamReaderBE;
typedef StreamReader<false> StreamReaderLE;
#endif
// `dynamic` StreamReader. The byte order of the input data is specified in the
// c'tor. This involves runtime branching and might be a little bit slower.
typedef StreamReader<true,true> StreamReaderAny;
} // end namespace Assimp
#endif // !! AI_STREAMREADER_H_INCLUDED

View File

@ -0,0 +1,303 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Defines the StreamWriter class which writes data to
* a binary stream with a well-defined endianness. */
#ifndef AI_STREAMWRITER_H_INCLUDED
#define AI_STREAMWRITER_H_INCLUDED
#include "ByteSwapper.h"
#include <assimp/IOStream.hpp>
#include <memory>
#include <vector>
namespace Assimp {
// --------------------------------------------------------------------------------------------
/** Wrapper class around IOStream to allow for consistent writing of binary data in both
* little and big endian format. Don't attempt to instance the template directly. Use
* StreamWriterLE to write to a little-endian stream and StreamWriterBE to write to a
* BE stream. Alternatively, there is StreamWriterAny if the endianness of the output
* stream is to be determined at runtime.
*/
// --------------------------------------------------------------------------------------------
template <bool SwapEndianess = false, bool RuntimeSwitch = false>
class StreamWriter
{
enum {
INITIAL_CAPACITY = 1024
};
public:
// ---------------------------------------------------------------------
/** Construction from a given stream with a well-defined endianness.
*
* The StreamReader holds a permanent strong reference to the
* stream, which is released upon destruction.
* @param stream Input stream. The stream is not re-seeked and writing
continues at the current position of the stream cursor.
* @param le If @c RuntimeSwitch is true: specifies whether the
* stream is in little endian byte order. Otherwise the
* endianness information is defined by the @c SwapEndianess
* template parameter and this parameter is meaningless. */
StreamWriter(std::shared_ptr<IOStream> stream, bool le = false)
: stream(stream)
, le(le)
, cursor()
{
ai_assert(stream);
buffer.reserve(INITIAL_CAPACITY);
}
// ---------------------------------------------------------------------
StreamWriter(IOStream* stream, bool le = false)
: stream(std::shared_ptr<IOStream>(stream))
, le(le)
, cursor()
{
ai_assert(stream);
buffer.reserve(INITIAL_CAPACITY);
}
// ---------------------------------------------------------------------
~StreamWriter() {
stream->Write(buffer.data(), 1, buffer.size());
stream->Flush();
}
public:
// ---------------------------------------------------------------------
/** Flush the contents of the internal buffer, and the output IOStream */
void Flush()
{
stream->Write(buffer.data(), 1, buffer.size());
stream->Flush();
buffer.clear();
cursor = 0;
}
// ---------------------------------------------------------------------
/** Seek to the given offset / origin in the output IOStream.
*
* Flushes the internal buffer and the output IOStream prior to seeking. */
aiReturn Seek(size_t pOffset, aiOrigin pOrigin=aiOrigin_SET)
{
Flush();
return stream->Seek(pOffset, pOrigin);
}
// ---------------------------------------------------------------------
/** Tell the current position in the output IOStream.
*
* First flushes the internal buffer and the output IOStream. */
size_t Tell()
{
Flush();
return stream->Tell();
}
public:
// ---------------------------------------------------------------------
/** Write a float to the stream */
void PutF4(float f)
{
Put(f);
}
// ---------------------------------------------------------------------
/** Write a double to the stream */
void PutF8(double d) {
Put(d);
}
// ---------------------------------------------------------------------
/** Write a signed 16 bit integer to the stream */
void PutI2(int16_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write a signed 8 bit integer to the stream */
void PutI1(int8_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write an signed 32 bit integer to the stream */
void PutI4(int32_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write a signed 64 bit integer to the stream */
void PutI8(int64_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write a unsigned 16 bit integer to the stream */
void PutU2(uint16_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write a unsigned 8 bit integer to the stream */
void PutU1(uint8_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write an unsigned 32 bit integer to the stream */
void PutU4(uint32_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write a unsigned 64 bit integer to the stream */
void PutU8(uint64_t n) {
Put(n);
}
// ---------------------------------------------------------------------
/** Write a single character to the stream */
void PutChar(char c) {
Put(c);
}
// ---------------------------------------------------------------------
/** Write an aiString to the stream */
void PutString(const aiString& s)
{
// as Put(T f) below
if (cursor + s.length >= buffer.size()) {
buffer.resize(cursor + s.length);
}
void* dest = &buffer[cursor];
::memcpy(dest, s.C_Str(), s.length);
cursor += s.length;
}
// ---------------------------------------------------------------------
/** Write a std::string to the stream */
void PutString(const std::string& s)
{
// as Put(T f) below
if (cursor + s.size() >= buffer.size()) {
buffer.resize(cursor + s.size());
}
void* dest = &buffer[cursor];
::memcpy(dest, s.c_str(), s.size());
cursor += s.size();
}
public:
// ---------------------------------------------------------------------
/** overload operator<< and allow chaining of MM ops. */
template <typename T>
StreamWriter& operator << (T f) {
Put(f);
return *this;
}
// ---------------------------------------------------------------------
std::size_t GetCurrentPos() const {
return cursor;
}
// ---------------------------------------------------------------------
void SetCurrentPos(std::size_t new_cursor) {
cursor = new_cursor;
}
// ---------------------------------------------------------------------
/** Generic write method. ByteSwap::Swap(T*) *must* be defined */
template <typename T>
void Put(T f) {
Intern :: Getter<SwapEndianess,T,RuntimeSwitch>() (&f, le);
if (cursor + sizeof(T) >= buffer.size()) {
buffer.resize(cursor + sizeof(T));
}
void* dest = &buffer[cursor];
// reinterpret_cast + assignment breaks strict aliasing rules
// and generally causes trouble on platforms such as ARM that
// do not silently ignore alignment faults.
::memcpy(dest, &f, sizeof(T));
cursor += sizeof(T);
}
private:
std::shared_ptr<IOStream> stream;
bool le;
std::vector<uint8_t> buffer;
std::size_t cursor;
};
// --------------------------------------------------------------------------------------------
// `static` StreamWriter. Their byte order is fixed and they might be a little bit faster.
#ifdef AI_BUILD_BIG_ENDIAN
typedef StreamWriter<true> StreamWriterLE;
typedef StreamWriter<false> StreamWriterBE;
#else
typedef StreamWriter<true> StreamWriterBE;
typedef StreamWriter<false> StreamWriterLE;
#endif
// `dynamic` StreamWriter. The byte order of the input data is specified in the
// c'tor. This involves runtime branching and might be a little bit slower.
typedef StreamWriter<true,true> StreamWriterAny;
} // end namespace Assimp
#endif // !! AI_STREAMWriter_H_INCLUDED

View File

@ -0,0 +1,233 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Definition of platform independent string workers:
ASSIMP_itoa10
ASSIMP_stricmp
ASSIMP_strincmp
These functions are not consistently available on all platforms,
or the provided implementations behave too differently.
*/
#ifndef INCLUDED_AI_STRING_WORKERS_H
#define INCLUDED_AI_STRING_WORKERS_H
#include <assimp/ai_assert.h>
#include <assimp/defs.h>
#include "StringComparison.h"
#include <string.h>
#include <stdint.h>
#include <string>
namespace Assimp {
// -------------------------------------------------------------------------------
/** @brief itoa with a fixed base 10
* 'itoa' is not consistently available on all platforms so it is quite useful
* to have a small replacement function here. No need to use a full sprintf()
* if we just want to print a number ...
* @param out Output buffer
* @param max Maximum number of characters to be written, including '\0'.
* This parameter may not be 0.
* @param number Number to be written
* @return Length of the output string, excluding the '\0'
*/
AI_FORCE_INLINE
unsigned int ASSIMP_itoa10( char* out, unsigned int max, int32_t number) {
ai_assert(NULL != out);
// write the unary minus to indicate we have a negative number
unsigned int written = 1u;
if (number < 0 && written < max) {
*out++ = '-';
++written;
number = -number;
}
// We begin with the largest number that is not zero.
int32_t cur = 1000000000; // 2147483648
bool mustPrint = false;
while (written < max) {
const unsigned int digit = number / cur;
if (mustPrint || digit > 0 || 1 == cur) {
// print all future zeroe's from now
mustPrint = true;
*out++ = '0'+static_cast<char>(digit);
++written;
number -= digit*cur;
if (1 == cur) {
break;
}
}
cur /= 10;
}
// append a terminal zero
*out++ = '\0';
return written-1;
}
// -------------------------------------------------------------------------------
/** @brief itoa with a fixed base 10 (Secure template overload)
* The compiler should choose this function if he or she is able to determine the
* size of the array automatically.
*/
template <size_t length>
AI_FORCE_INLINE
unsigned int ASSIMP_itoa10( char(& out)[length], int32_t number) {
return ASSIMP_itoa10(out,length,number);
}
// -------------------------------------------------------------------------------
/** @brief Helper function to do platform independent string comparison.
*
* This is required since stricmp() is not consistently available on
* all platforms. Some platforms use the '_' prefix, others don't even
* have such a function.
*
* @param s1 First input string
* @param s2 Second input string
* @return 0 if the given strings are identical
*/
AI_FORCE_INLINE
int ASSIMP_stricmp(const char *s1, const char *s2) {
ai_assert( NULL != s1 );
ai_assert( NULL != s2 );
#if (defined _MSC_VER)
return ::_stricmp(s1,s2);
#elif defined( __GNUC__ )
return ::strcasecmp(s1,s2);
#else
char c1, c2;
do {
c1 = tolower(*s1++);
c2 = tolower(*s2++);
}
while ( c1 && (c1 == c2) );
return c1 - c2;
#endif
}
// -------------------------------------------------------------------------------
/** @brief Case independent comparison of two std::strings
*
* @param a First string
* @param b Second string
* @return 0 if a == b
*/
AI_FORCE_INLINE
int ASSIMP_stricmp(const std::string& a, const std::string& b) {
int i = (int)b.length()-(int)a.length();
return (i ? i : ASSIMP_stricmp(a.c_str(),b.c_str()));
}
// -------------------------------------------------------------------------------
/** @brief Helper function to do platform independent string comparison.
*
* This is required since strincmp() is not consistently available on
* all platforms. Some platforms use the '_' prefix, others don't even
* have such a function.
*
* @param s1 First input string
* @param s2 Second input string
* @param n Macimum number of characters to compare
* @return 0 if the given strings are identical
*/
AI_FORCE_INLINE
int ASSIMP_strincmp(const char *s1, const char *s2, unsigned int n) {
ai_assert( NULL != s1 );
ai_assert( NULL != s2 );
if ( !n ) {
return 0;
}
#if (defined _MSC_VER)
return ::_strnicmp(s1,s2,n);
#elif defined( __GNUC__ )
return ::strncasecmp(s1,s2, n);
#else
char c1, c2;
unsigned int p = 0;
do
{
if (p++ >= n)return 0;
c1 = tolower(*s1++);
c2 = tolower(*s2++);
}
while ( c1 && (c1 == c2) );
return c1 - c2;
#endif
}
// -------------------------------------------------------------------------------
/** @brief Evaluates an integer power
*
* todo: move somewhere where it fits better in than here
*/
AI_FORCE_INLINE
unsigned int integer_pow( unsigned int base, unsigned int power ) {
unsigned int res = 1;
for ( unsigned int i = 0; i < power; ++i ) {
res *= base;
}
return res;
}
} // end of namespace
#endif // ! AI_STRINGCOMPARISON_H_INC

View File

@ -0,0 +1,143 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
#ifndef INCLUDED_AI_STRINGUTILS_H
#define INCLUDED_AI_STRINGUTILS_H
#include <assimp/defs.h>
#include <sstream>
#include <stdarg.h>
#include <cstdlib>
/// @fn ai_snprintf
/// @brief The portable version of the function snprintf ( C99 standard ), which works on visual studio compilers 2013 and earlier.
/// @param outBuf The buffer to write in
/// @param size The buffer size
/// @param format The format string
/// @param ap The additional arguments.
/// @return The number of written characters if the buffer size was big enough. If an encoding error occurs, a negative number is returned.
#if defined(_MSC_VER) && _MSC_VER < 1900
AI_FORCE_INLINE
int c99_ai_vsnprintf(char *outBuf, size_t size, const char *format, va_list ap) {
int count(-1);
if (0 != size) {
count = _vsnprintf_s(outBuf, size, _TRUNCATE, format, ap);
}
if (count == -1) {
count = _vscprintf(format, ap);
}
return count;
}
AI_FORCE_INLINE
int ai_snprintf(char *outBuf, size_t size, const char *format, ...) {
int count;
va_list ap;
va_start(ap, format);
count = c99_ai_vsnprintf(outBuf, size, format, ap);
va_end(ap);
return count;
}
#else
# define ai_snprintf snprintf
#endif
/// @fn to_string
/// @brief The portable version of to_string ( some gcc-versions on embedded devices are not supporting this).
/// @param value The value to write into the std::string.
/// @return The value as a std::string
template <typename T>
AI_FORCE_INLINE
std::string to_string( T value ) {
std::ostringstream os;
os << value;
return os.str();
}
/// @fn ai_strtof
/// @brief The portable version of strtof.
/// @param begin The first character of the string.
/// @param end The last character
/// @return The float value, 0.0f in cas of an error.
AI_FORCE_INLINE
float ai_strtof( const char *begin, const char *end ) {
if ( nullptr == begin ) {
return 0.0f;
}
float val( 0.0f );
if ( nullptr == end ) {
val = static_cast< float >( ::atof( begin ) );
} else {
std::string::size_type len( end - begin );
std::string token( begin, len );
val = static_cast< float >( ::atof( token.c_str() ) );
}
return val;
}
/// @fn DecimalToHexa
/// @brief The portable to convert a decimal value into a hexadecimal string.
/// @param toConvert Value to convert
/// @return The hexadecimal string, is empty in case of an error.
template<class T>
AI_FORCE_INLINE
std::string DecimalToHexa( T toConvert ) {
std::string result;
std::stringstream ss;
ss << std::hex << toConvert;
ss >> result;
for ( size_t i = 0; i < result.size(); ++i ) {
result[ i ] = toupper( result[ i ] );
}
return result;
}
#endif // INCLUDED_AI_STRINGUTILS_H

View File

@ -0,0 +1,131 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Defines a helper class to evaluate subdivision surfaces.*/
#pragma once
#ifndef AI_SUBDISIVION_H_INC
#define AI_SUBDISIVION_H_INC
#include <cstddef>
#include <assimp/types.h>
struct aiMesh;
namespace Assimp {
// ------------------------------------------------------------------------------
/** Helper class to evaluate subdivision surfaces. Different algorithms
* are provided for choice. */
// ------------------------------------------------------------------------------
class ASSIMP_API Subdivider {
public:
/** Enumerates all supported subvidision algorithms */
enum Algorithm {
CATMULL_CLARKE = 0x1
};
virtual ~Subdivider();
// ---------------------------------------------------------------
/** Create a subdivider of a specific type
*
* @param algo Algorithm to be used for subdivision
* @return Subdivider instance. */
static Subdivider* Create (Algorithm algo);
// ---------------------------------------------------------------
/** Subdivide a mesh using the selected algorithm
*
* @param mesh First mesh to be subdivided. Must be in verbose
* format.
* @param out Receives the output mesh, allocated by me.
* @param num Number of subdivisions to perform.
* @param discard_input If true is passed, the input mesh is
* deleted after the subdivision is complete. This can
* improve performance because it allows the optimization
* to reuse the existing mesh for intermediate results.
* @pre out!=mesh*/
virtual void Subdivide ( aiMesh* mesh,
aiMesh*& out, unsigned int num,
bool discard_input = false) = 0;
// ---------------------------------------------------------------
/** Subdivide multiple meshes using the selected algorithm. This
* avoids erroneous smoothing on objects consisting of multiple
* per-material meshes. Usually, most 3d modellers smooth on a
* per-object base, regardless the materials assigned to the
* meshes.
*
* @param smesh Array of meshes to be subdivided. Must be in
* verbose format.
* @param nmesh Number of meshes in smesh.
* @param out Receives the output meshes. The array must be
* sufficiently large (at least @c nmesh elements) and may not
* overlap the input array. Output meshes map one-to-one to
* their corresponding input meshes. The meshes are allocated
* by the function.
* @param discard_input If true is passed, input meshes are
* deleted after the subdivision is complete. This can
* improve performance because it allows the optimization
* of reusing existing meshes for intermediate results.
* @param num Number of subdivisions to perform.
* @pre nmesh != 0, smesh and out may not overlap*/
virtual void Subdivide (
aiMesh** smesh,
size_t nmesh,
aiMesh** out,
unsigned int num,
bool discard_input = false) = 0;
};
inline
Subdivider::~Subdivider() {
// empty
}
} // end namespace Assimp
#endif // !! AI_SUBDISIVION_H_INC

View File

@ -0,0 +1,166 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file TinyFormatter.h
* @brief Utility to format log messages more easily. Introduced
* to get rid of the boost::format dependency. Much slinker,
* basically just extends stringstream.
*/
#ifndef INCLUDED_TINY_FORMATTER_H
#define INCLUDED_TINY_FORMATTER_H
#include <sstream>
namespace Assimp {
namespace Formatter {
// ------------------------------------------------------------------------------------------------
/** stringstream utility. Usage:
* @code
* void writelog(const std::string&s);
* void writelog(const std::wstring&s);
* ...
* writelog(format()<< "hi! this is a number: " << 4);
* writelog(wformat()<< L"hi! this is a number: " << 4);
*
* @endcode */
template < typename T,
typename CharTraits = std::char_traits<T>,
typename Allocator = std::allocator<T>
>
class basic_formatter
{
public:
typedef class std::basic_string<
T,CharTraits,Allocator
> string;
typedef class std::basic_ostringstream<
T,CharTraits,Allocator
> stringstream;
public:
basic_formatter() {}
/* Allow basic_formatter<T>'s to be used almost interchangeably
* with std::(w)string or const (w)char* arguments because the
* conversion c'tor is called implicitly. */
template <typename TT>
basic_formatter(const TT& sin) {
underlying << sin;
}
// The problem described here:
// https://sourceforge.net/tracker/?func=detail&atid=1067632&aid=3358562&group_id=226462
// can also cause trouble here. Apparently, older gcc versions sometimes copy temporaries
// being bound to const ref& function parameters. Copying streams is not permitted, though.
// This workaround avoids this by manually specifying a copy ctor.
#if !defined(__GNUC__) || !defined(__APPLE__) || __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)
explicit basic_formatter(const basic_formatter& other) {
underlying << (string)other;
}
#endif
public:
operator string () const {
return underlying.str();
}
/* note - this is declared const because binding temporaries does only
* work for const references, so many function prototypes will
* include const basic_formatter<T>& s but might still want to
* modify the formatted string without the need for a full copy.*/
template <typename TToken>
const basic_formatter& operator << (const TToken& s) const {
underlying << s;
return *this;
}
template <typename TToken>
basic_formatter& operator << (const TToken& s) {
underlying << s;
return *this;
}
// comma operator overloaded as well, choose your preferred way.
template <typename TToken>
const basic_formatter& operator, (const TToken& s) const {
underlying << s;
return *this;
}
template <typename TToken>
basic_formatter& operator, (const TToken& s) {
underlying << s;
return *this;
}
// Fix for MSVC8
// See https://sourceforge.net/projects/assimp/forums/forum/817654/topic/4372824
template <typename TToken>
basic_formatter& operator, (TToken& s) {
underlying << s;
return *this;
}
private:
mutable stringstream underlying;
};
typedef basic_formatter< char > format;
typedef basic_formatter< wchar_t > wformat;
} // ! namespace Formatter
} // ! namespace Assimp
#endif

View File

@ -0,0 +1,348 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Defines a helper class to represent an interleaved vertex
along with arithmetic operations to support vertex operations
such as subdivision, smoothing etc.
While the code is kept as general as possible, arithmetic operations
that are not currently well-defined (and would cause compile errors
due to missing operators in the math library), are commented.
*/
#ifndef AI_VERTEX_H_INC
#define AI_VERTEX_H_INC
#include <assimp/vector3.h>
#include <assimp/mesh.h>
#include <assimp/ai_assert.h>
#include <functional>
namespace Assimp {
///////////////////////////////////////////////////////////////////////////
// std::plus-family operates on operands with identical types - we need to
// support all the (vectype op float) combinations in vector maths.
// Providing T(float) would open the way to endless implicit conversions.
///////////////////////////////////////////////////////////////////////////
namespace Intern {
template <typename T0, typename T1, typename TRES = T0> struct plus {
TRES operator() (const T0& t0, const T1& t1) const {
return t0+t1;
}
};
template <typename T0, typename T1, typename TRES = T0> struct minus {
TRES operator() (const T0& t0, const T1& t1) const {
return t0-t1;
}
};
template <typename T0, typename T1, typename TRES = T0> struct multiplies {
TRES operator() (const T0& t0, const T1& t1) const {
return t0*t1;
}
};
template <typename T0, typename T1, typename TRES = T0> struct divides {
TRES operator() (const T0& t0, const T1& t1) const {
return t0/t1;
}
};
}
// ------------------------------------------------------------------------------------------------
/** Intermediate description a vertex with all possible components. Defines a full set of
* operators, so you may use such a 'Vertex' in basic arithmetics. All operators are applied
* to *all* vertex components equally. This is useful for stuff like interpolation
* or subdivision, but won't work if special handling is required for some vertex components. */
// ------------------------------------------------------------------------------------------------
class Vertex
{
friend Vertex operator + (const Vertex&,const Vertex&);
friend Vertex operator - (const Vertex&,const Vertex&);
// friend Vertex operator + (const Vertex&,ai_real);
// friend Vertex operator - (const Vertex&,ai_real);
friend Vertex operator * (const Vertex&,ai_real);
friend Vertex operator / (const Vertex&,ai_real);
// friend Vertex operator + (ai_real, const Vertex&);
// friend Vertex operator - (ai_real, const Vertex&);
friend Vertex operator * (ai_real, const Vertex&);
// friend Vertex operator / (ai_real, const Vertex&);
public:
Vertex() {}
// ----------------------------------------------------------------------------
/** Extract a particular vertex from a mesh and interleave all components */
explicit Vertex(const aiMesh* msh, unsigned int idx) {
ai_assert(idx < msh->mNumVertices);
position = msh->mVertices[idx];
if (msh->HasNormals()) {
normal = msh->mNormals[idx];
}
if (msh->HasTangentsAndBitangents()) {
tangent = msh->mTangents[idx];
bitangent = msh->mBitangents[idx];
}
for (unsigned int i = 0; msh->HasTextureCoords(i); ++i) {
texcoords[i] = msh->mTextureCoords[i][idx];
}
for (unsigned int i = 0; msh->HasVertexColors(i); ++i) {
colors[i] = msh->mColors[i][idx];
}
}
// ----------------------------------------------------------------------------
/** Extract a particular vertex from a anim mesh and interleave all components */
explicit Vertex(const aiAnimMesh* msh, unsigned int idx) {
ai_assert(idx < msh->mNumVertices);
position = msh->mVertices[idx];
if (msh->HasNormals()) {
normal = msh->mNormals[idx];
}
if (msh->HasTangentsAndBitangents()) {
tangent = msh->mTangents[idx];
bitangent = msh->mBitangents[idx];
}
for (unsigned int i = 0; msh->HasTextureCoords(i); ++i) {
texcoords[i] = msh->mTextureCoords[i][idx];
}
for (unsigned int i = 0; msh->HasVertexColors(i); ++i) {
colors[i] = msh->mColors[i][idx];
}
}
public:
Vertex& operator += (const Vertex& v) {
*this = *this+v;
return *this;
}
Vertex& operator -= (const Vertex& v) {
*this = *this-v;
return *this;
}
/*
Vertex& operator += (ai_real v) {
*this = *this+v;
return *this;
}
Vertex& operator -= (ai_real v) {
*this = *this-v;
return *this;
}
*/
Vertex& operator *= (ai_real v) {
*this = *this*v;
return *this;
}
Vertex& operator /= (ai_real v) {
*this = *this/v;
return *this;
}
public:
// ----------------------------------------------------------------------------
/** Convert back to non-interleaved storage */
void SortBack(aiMesh* out, unsigned int idx) const {
ai_assert(idx<out->mNumVertices);
out->mVertices[idx] = position;
if (out->HasNormals()) {
out->mNormals[idx] = normal;
}
if (out->HasTangentsAndBitangents()) {
out->mTangents[idx] = tangent;
out->mBitangents[idx] = bitangent;
}
for(unsigned int i = 0; out->HasTextureCoords(i); ++i) {
out->mTextureCoords[i][idx] = texcoords[i];
}
for(unsigned int i = 0; out->HasVertexColors(i); ++i) {
out->mColors[i][idx] = colors[i];
}
}
private:
// ----------------------------------------------------------------------------
/** Construct from two operands and a binary operation to combine them */
template <template <typename t> class op> static Vertex BinaryOp(const Vertex& v0, const Vertex& v1) {
// this is a heavy task for the compiler to optimize ... *pray*
Vertex res;
res.position = op<aiVector3D>()(v0.position,v1.position);
res.normal = op<aiVector3D>()(v0.normal,v1.normal);
res.tangent = op<aiVector3D>()(v0.tangent,v1.tangent);
res.bitangent = op<aiVector3D>()(v0.bitangent,v1.bitangent);
for (unsigned int i = 0; i < AI_MAX_NUMBER_OF_TEXTURECOORDS; ++i) {
res.texcoords[i] = op<aiVector3D>()(v0.texcoords[i],v1.texcoords[i]);
}
for (unsigned int i = 0; i < AI_MAX_NUMBER_OF_COLOR_SETS; ++i) {
res.colors[i] = op<aiColor4D>()(v0.colors[i],v1.colors[i]);
}
return res;
}
// ----------------------------------------------------------------------------
/** This time binary arithmetics of v0 with a floating-point number */
template <template <typename, typename, typename> class op> static Vertex BinaryOp(const Vertex& v0, ai_real f) {
// this is a heavy task for the compiler to optimize ... *pray*
Vertex res;
res.position = op<aiVector3D,ai_real,aiVector3D>()(v0.position,f);
res.normal = op<aiVector3D,ai_real,aiVector3D>()(v0.normal,f);
res.tangent = op<aiVector3D,ai_real,aiVector3D>()(v0.tangent,f);
res.bitangent = op<aiVector3D,ai_real,aiVector3D>()(v0.bitangent,f);
for (unsigned int i = 0; i < AI_MAX_NUMBER_OF_TEXTURECOORDS; ++i) {
res.texcoords[i] = op<aiVector3D,ai_real,aiVector3D>()(v0.texcoords[i],f);
}
for (unsigned int i = 0; i < AI_MAX_NUMBER_OF_COLOR_SETS; ++i) {
res.colors[i] = op<aiColor4D,ai_real,aiColor4D>()(v0.colors[i],f);
}
return res;
}
// ----------------------------------------------------------------------------
/** This time binary arithmetics of v0 with a floating-point number */
template <template <typename, typename, typename> class op> static Vertex BinaryOp(ai_real f, const Vertex& v0) {
// this is a heavy task for the compiler to optimize ... *pray*
Vertex res;
res.position = op<ai_real,aiVector3D,aiVector3D>()(f,v0.position);
res.normal = op<ai_real,aiVector3D,aiVector3D>()(f,v0.normal);
res.tangent = op<ai_real,aiVector3D,aiVector3D>()(f,v0.tangent);
res.bitangent = op<ai_real,aiVector3D,aiVector3D>()(f,v0.bitangent);
for (unsigned int i = 0; i < AI_MAX_NUMBER_OF_TEXTURECOORDS; ++i) {
res.texcoords[i] = op<ai_real,aiVector3D,aiVector3D>()(f,v0.texcoords[i]);
}
for (unsigned int i = 0; i < AI_MAX_NUMBER_OF_COLOR_SETS; ++i) {
res.colors[i] = op<ai_real,aiColor4D,aiColor4D>()(f,v0.colors[i]);
}
return res;
}
public:
aiVector3D position;
aiVector3D normal;
aiVector3D tangent, bitangent;
aiVector3D texcoords[AI_MAX_NUMBER_OF_TEXTURECOORDS];
aiColor4D colors[AI_MAX_NUMBER_OF_COLOR_SETS];
};
// ------------------------------------------------------------------------------------------------
AI_FORCE_INLINE Vertex operator + (const Vertex& v0,const Vertex& v1) {
return Vertex::BinaryOp<std::plus>(v0,v1);
}
AI_FORCE_INLINE Vertex operator - (const Vertex& v0,const Vertex& v1) {
return Vertex::BinaryOp<std::minus>(v0,v1);
}
// ------------------------------------------------------------------------------------------------
/*
AI_FORCE_INLINE Vertex operator + (const Vertex& v0,ai_real f) {
return Vertex::BinaryOp<Intern::plus>(v0,f);
}
AI_FORCE_INLINE Vertex operator - (const Vertex& v0,ai_real f) {
return Vertex::BinaryOp<Intern::minus>(v0,f);
}
*/
AI_FORCE_INLINE Vertex operator * (const Vertex& v0,ai_real f) {
return Vertex::BinaryOp<Intern::multiplies>(v0,f);
}
AI_FORCE_INLINE Vertex operator / (const Vertex& v0,ai_real f) {
return Vertex::BinaryOp<Intern::multiplies>(v0,1.f/f);
}
// ------------------------------------------------------------------------------------------------
/*
AI_FORCE_INLINE Vertex operator + (ai_real f,const Vertex& v0) {
return Vertex::BinaryOp<Intern::plus>(f,v0);
}
AI_FORCE_INLINE Vertex operator - (ai_real f,const Vertex& v0) {
return Vertex::BinaryOp<Intern::minus>(f,v0);
}
*/
AI_FORCE_INLINE Vertex operator * (ai_real f,const Vertex& v0) {
return Vertex::BinaryOp<Intern::multiplies>(f,v0);
}
/*
AI_FORCE_INLINE Vertex operator / (ai_real f,const Vertex& v0) {
return Vertex::BinaryOp<Intern::divides>(f,v0);
}
*/
}
#endif

View File

@ -0,0 +1,83 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
#ifndef INCLUDED_ASSIMP_XML_TOOLS_H
#define INCLUDED_ASSIMP_XML_TOOLS_H
#include <string>
namespace Assimp {
// XML escape the 5 XML special characters (",',<,> and &) in |data|
// Based on http://stackoverflow.com/questions/5665231
std::string XMLEscape(const std::string& data) {
std::string buffer;
const size_t size = data.size();
buffer.reserve(size + size / 8);
for(size_t i = 0; i < size; ++i) {
const char c = data[i];
switch(c) {
case '&' :
buffer.append("&amp;");
break;
case '\"':
buffer.append("&quot;");
break;
case '\'':
buffer.append("&apos;");
break;
case '<' :
buffer.append("&lt;");
break;
case '>' :
buffer.append("&gt;");
break;
default:
buffer.append(&c, 1);
break;
}
}
return buffer;
}
}
#endif // INCLUDED_ASSIMP_XML_TOOLS_H

View File

@ -0,0 +1,87 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file ZipArchiveIOSystem.h
* @brief Implementation of IOSystem to read a ZIP file from another IOSystem
*/
#ifndef AI_ZIPARCHIVEIOSYSTEM_H_INC
#define AI_ZIPARCHIVEIOSYSTEM_H_INC
#include <assimp/IOStream.hpp>
#include <assimp/IOSystem.hpp>
namespace Assimp {
class ZipArchiveIOSystem : public IOSystem {
public:
//! Open a Zip using the proffered IOSystem
ZipArchiveIOSystem(IOSystem* pIOHandler, const char *pFilename, const char* pMode = "r");
ZipArchiveIOSystem(IOSystem* pIOHandler, const std::string& rFilename, const char* pMode = "r");
virtual ~ZipArchiveIOSystem();
bool Exists(const char* pFilename) const override;
char getOsSeparator() const override;
IOStream* Open(const char* pFilename, const char* pMode = "rb") override;
void Close(IOStream* pFile) override;
// Specific to ZIP
//! The file was opened and is a ZIP
bool isOpen() const;
//! Get the list of all files with their simplified paths
//! Intended for use within Assimp library boundaries
void getFileList(std::vector<std::string>& rFileList) const;
//! Get the list of all files with extension (must be lowercase)
//! Intended for use within Assimp library boundaries
void getFileListExtension(std::vector<std::string>& rFileList, const std::string& extension) const;
static bool isZipArchive(IOSystem* pIOHandler, const char *pFilename);
static bool isZipArchive(IOSystem* pIOHandler, const std::string& rFilename);
private:
class Implement;
Implement *pImpl = nullptr;
};
} // Namespace Assimp
#endif // AI_ZIPARCHIVEIOSYSTEM_H_INC

View File

@ -0,0 +1,76 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
#pragma once
#ifndef AI_AABB_H_INC
#define AI_AABB_H_INC
#include <assimp/vector3.h>
struct aiAABB {
C_STRUCT aiVector3D mMin;
C_STRUCT aiVector3D mMax;
#ifdef __cplusplus
aiAABB()
: mMin()
, mMax() {
// empty
}
aiAABB(const aiVector3D &min, const aiVector3D &max )
: mMin(min)
, mMax(max) {
// empty
}
~aiAABB() {
// empty
}
#endif
};
#endif

View File

@ -0,0 +1,57 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
#pragma once
#ifndef AI_ASSERT_H_INC
#define AI_ASSERT_H_INC
#ifdef ASSIMP_BUILD_DEBUG
# include <assert.h>
# define ai_assert(expression) assert( expression )
# define ai_assert_entry() assert( false )
#else
# define ai_assert(expression)
# define ai_assert_entry()
#endif // ASSIMP_BUILD_DEBUG
#endif // AI_ASSERT_H_INC

View File

@ -0,0 +1,577 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/**
* @file anim.h
* @brief Defines the data structures in which the imported animations
* are returned.
*/
#pragma once
#ifndef AI_ANIM_H_INC
#define AI_ANIM_H_INC
#include <assimp/types.h>
#include <assimp/quaternion.h>
#ifdef __cplusplus
extern "C" {
#endif
// ---------------------------------------------------------------------------
/** A time-value pair specifying a certain 3D vector for the given time. */
struct aiVectorKey
{
/** The time of this key */
double mTime;
/** The value of this key */
C_STRUCT aiVector3D mValue;
#ifdef __cplusplus
/// @brief The default constructor.
aiVectorKey() AI_NO_EXCEPT
: mTime( 0.0 )
, mValue() {
// empty
}
/// @brief Construction from a given time and key value.
aiVectorKey(double time, const aiVector3D& value)
: mTime( time )
, mValue( value ) {
// empty
}
typedef aiVector3D elem_type;
// Comparison operators. For use with std::find();
bool operator == (const aiVectorKey& rhs) const {
return rhs.mValue == this->mValue;
}
bool operator != (const aiVectorKey& rhs ) const {
return rhs.mValue != this->mValue;
}
// Relational operators. For use with std::sort();
bool operator < (const aiVectorKey& rhs ) const {
return mTime < rhs.mTime;
}
bool operator > (const aiVectorKey& rhs ) const {
return mTime > rhs.mTime;
}
#endif // __cplusplus
};
// ---------------------------------------------------------------------------
/** A time-value pair specifying a rotation for the given time.
* Rotations are expressed with quaternions. */
struct aiQuatKey
{
/** The time of this key */
double mTime;
/** The value of this key */
C_STRUCT aiQuaternion mValue;
#ifdef __cplusplus
aiQuatKey() AI_NO_EXCEPT
: mTime( 0.0 )
, mValue() {
// empty
}
/** Construction from a given time and key value */
aiQuatKey(double time, const aiQuaternion& value)
: mTime (time)
, mValue (value)
{}
typedef aiQuaternion elem_type;
// Comparison operators. For use with std::find();
bool operator == (const aiQuatKey& rhs ) const {
return rhs.mValue == this->mValue;
}
bool operator != (const aiQuatKey& rhs ) const {
return rhs.mValue != this->mValue;
}
// Relational operators. For use with std::sort();
bool operator < (const aiQuatKey& rhs ) const {
return mTime < rhs.mTime;
}
bool operator > (const aiQuatKey& rhs ) const {
return mTime > rhs.mTime;
}
#endif
};
// ---------------------------------------------------------------------------
/** Binds a anim-mesh to a specific point in time. */
struct aiMeshKey
{
/** The time of this key */
double mTime;
/** Index into the aiMesh::mAnimMeshes array of the
* mesh corresponding to the #aiMeshAnim hosting this
* key frame. The referenced anim mesh is evaluated
* according to the rules defined in the docs for #aiAnimMesh.*/
unsigned int mValue;
#ifdef __cplusplus
aiMeshKey() AI_NO_EXCEPT
: mTime(0.0)
, mValue(0)
{
}
/** Construction from a given time and key value */
aiMeshKey(double time, const unsigned int value)
: mTime (time)
, mValue (value)
{}
typedef unsigned int elem_type;
// Comparison operators. For use with std::find();
bool operator == (const aiMeshKey& o) const {
return o.mValue == this->mValue;
}
bool operator != (const aiMeshKey& o) const {
return o.mValue != this->mValue;
}
// Relational operators. For use with std::sort();
bool operator < (const aiMeshKey& o) const {
return mTime < o.mTime;
}
bool operator > (const aiMeshKey& o) const {
return mTime > o.mTime;
}
#endif
};
// ---------------------------------------------------------------------------
/** Binds a morph anim mesh to a specific point in time. */
struct aiMeshMorphKey
{
/** The time of this key */
double mTime;
/** The values and weights at the time of this key */
unsigned int *mValues;
double *mWeights;
/** The number of values and weights */
unsigned int mNumValuesAndWeights;
#ifdef __cplusplus
aiMeshMorphKey() AI_NO_EXCEPT
: mTime(0.0)
, mValues(nullptr)
, mWeights(nullptr)
, mNumValuesAndWeights(0)
{
}
~aiMeshMorphKey()
{
if (mNumValuesAndWeights && mValues && mWeights) {
delete [] mValues;
delete [] mWeights;
}
}
#endif
};
// ---------------------------------------------------------------------------
/** Defines how an animation channel behaves outside the defined time
* range. This corresponds to aiNodeAnim::mPreState and
* aiNodeAnim::mPostState.*/
enum aiAnimBehaviour
{
/** The value from the default node transformation is taken*/
aiAnimBehaviour_DEFAULT = 0x0,
/** The nearest key value is used without interpolation */
aiAnimBehaviour_CONSTANT = 0x1,
/** The value of the nearest two keys is linearly
* extrapolated for the current time value.*/
aiAnimBehaviour_LINEAR = 0x2,
/** The animation is repeated.
*
* If the animation key go from n to m and the current
* time is t, use the value at (t-n) % (|m-n|).*/
aiAnimBehaviour_REPEAT = 0x3,
/** This value is not used, it is just here to force the
* the compiler to map this enum to a 32 Bit integer */
#ifndef SWIG
_aiAnimBehaviour_Force32Bit = INT_MAX
#endif
};
// ---------------------------------------------------------------------------
/** Describes the animation of a single node. The name specifies the
* bone/node which is affected by this animation channel. The keyframes
* are given in three separate series of values, one each for position,
* rotation and scaling. The transformation matrix computed from these
* values replaces the node's original transformation matrix at a
* specific time.
* This means all keys are absolute and not relative to the bone default pose.
* The order in which the transformations are applied is
* - as usual - scaling, rotation, translation.
*
* @note All keys are returned in their correct, chronological order.
* Duplicate keys don't pass the validation step. Most likely there
* will be no negative time values, but they are not forbidden also ( so
* implementations need to cope with them! ) */
struct aiNodeAnim {
/** The name of the node affected by this animation. The node
* must exist and it must be unique.*/
C_STRUCT aiString mNodeName;
/** The number of position keys */
unsigned int mNumPositionKeys;
/** The position keys of this animation channel. Positions are
* specified as 3D vector. The array is mNumPositionKeys in size.
*
* If there are position keys, there will also be at least one
* scaling and one rotation key.*/
C_STRUCT aiVectorKey* mPositionKeys;
/** The number of rotation keys */
unsigned int mNumRotationKeys;
/** The rotation keys of this animation channel. Rotations are
* given as quaternions, which are 4D vectors. The array is
* mNumRotationKeys in size.
*
* If there are rotation keys, there will also be at least one
* scaling and one position key. */
C_STRUCT aiQuatKey* mRotationKeys;
/** The number of scaling keys */
unsigned int mNumScalingKeys;
/** The scaling keys of this animation channel. Scalings are
* specified as 3D vector. The array is mNumScalingKeys in size.
*
* If there are scaling keys, there will also be at least one
* position and one rotation key.*/
C_STRUCT aiVectorKey* mScalingKeys;
/** Defines how the animation behaves before the first
* key is encountered.
*
* The default value is aiAnimBehaviour_DEFAULT (the original
* transformation matrix of the affected node is used).*/
C_ENUM aiAnimBehaviour mPreState;
/** Defines how the animation behaves after the last
* key was processed.
*
* The default value is aiAnimBehaviour_DEFAULT (the original
* transformation matrix of the affected node is taken).*/
C_ENUM aiAnimBehaviour mPostState;
#ifdef __cplusplus
aiNodeAnim() AI_NO_EXCEPT
: mNumPositionKeys( 0 )
, mPositionKeys( nullptr )
, mNumRotationKeys( 0 )
, mRotationKeys( nullptr )
, mNumScalingKeys( 0 )
, mScalingKeys( nullptr )
, mPreState( aiAnimBehaviour_DEFAULT )
, mPostState( aiAnimBehaviour_DEFAULT ) {
// empty
}
~aiNodeAnim() {
delete [] mPositionKeys;
delete [] mRotationKeys;
delete [] mScalingKeys;
}
#endif // __cplusplus
};
// ---------------------------------------------------------------------------
/** Describes vertex-based animations for a single mesh or a group of
* meshes. Meshes carry the animation data for each frame in their
* aiMesh::mAnimMeshes array. The purpose of aiMeshAnim is to
* define keyframes linking each mesh attachment to a particular
* point in time. */
struct aiMeshAnim
{
/** Name of the mesh to be animated. An empty string is not allowed,
* animated meshes need to be named (not necessarily uniquely,
* the name can basically serve as wild-card to select a group
* of meshes with similar animation setup)*/
C_STRUCT aiString mName;
/** Size of the #mKeys array. Must be 1, at least. */
unsigned int mNumKeys;
/** Key frames of the animation. May not be NULL. */
C_STRUCT aiMeshKey* mKeys;
#ifdef __cplusplus
aiMeshAnim() AI_NO_EXCEPT
: mNumKeys()
, mKeys()
{}
~aiMeshAnim()
{
delete[] mKeys;
}
#endif
};
// ---------------------------------------------------------------------------
/** Describes a morphing animation of a given mesh. */
struct aiMeshMorphAnim
{
/** Name of the mesh to be animated. An empty string is not allowed,
* animated meshes need to be named (not necessarily uniquely,
* the name can basically serve as wildcard to select a group
* of meshes with similar animation setup)*/
C_STRUCT aiString mName;
/** Size of the #mKeys array. Must be 1, at least. */
unsigned int mNumKeys;
/** Key frames of the animation. May not be NULL. */
C_STRUCT aiMeshMorphKey* mKeys;
#ifdef __cplusplus
aiMeshMorphAnim() AI_NO_EXCEPT
: mNumKeys()
, mKeys()
{}
~aiMeshMorphAnim()
{
delete[] mKeys;
}
#endif
};
// ---------------------------------------------------------------------------
/** An animation consists of key-frame data for a number of nodes. For
* each node affected by the animation a separate series of data is given.*/
struct aiAnimation {
/** The name of the animation. If the modeling package this data was
* exported from does support only a single animation channel, this
* name is usually empty (length is zero). */
C_STRUCT aiString mName;
/** Duration of the animation in ticks. */
double mDuration;
/** Ticks per second. 0 if not specified in the imported file */
double mTicksPerSecond;
/** The number of bone animation channels. Each channel affects
* a single node. */
unsigned int mNumChannels;
/** The node animation channels. Each channel affects a single node.
* The array is mNumChannels in size. */
C_STRUCT aiNodeAnim** mChannels;
/** The number of mesh animation channels. Each channel affects
* a single mesh and defines vertex-based animation. */
unsigned int mNumMeshChannels;
/** The mesh animation channels. Each channel affects a single mesh.
* The array is mNumMeshChannels in size. */
C_STRUCT aiMeshAnim** mMeshChannels;
/** The number of mesh animation channels. Each channel affects
* a single mesh and defines morphing animation. */
unsigned int mNumMorphMeshChannels;
/** The morph mesh animation channels. Each channel affects a single mesh.
* The array is mNumMorphMeshChannels in size. */
C_STRUCT aiMeshMorphAnim **mMorphMeshChannels;
#ifdef __cplusplus
aiAnimation() AI_NO_EXCEPT
: mDuration(-1.)
, mTicksPerSecond(0.)
, mNumChannels(0)
, mChannels(nullptr)
, mNumMeshChannels(0)
, mMeshChannels(nullptr)
, mNumMorphMeshChannels(0)
, mMorphMeshChannels(nullptr) {
// empty
}
~aiAnimation() {
// DO NOT REMOVE THIS ADDITIONAL CHECK
if ( mNumChannels && mChannels ) {
for( unsigned int a = 0; a < mNumChannels; a++) {
delete mChannels[ a ];
}
delete [] mChannels;
}
if (mNumMeshChannels && mMeshChannels) {
for( unsigned int a = 0; a < mNumMeshChannels; a++) {
delete mMeshChannels[a];
}
delete [] mMeshChannels;
}
if (mNumMorphMeshChannels && mMorphMeshChannels) {
for( unsigned int a = 0; a < mNumMorphMeshChannels; a++) {
delete mMorphMeshChannels[a];
}
delete [] mMorphMeshChannels;
}
}
#endif // __cplusplus
};
#ifdef __cplusplus
}
/// @brief Some C++ utilities for inter- and extrapolation
namespace Assimp {
// ---------------------------------------------------------------------------
/**
* @brief CPP-API: Utility class to simplify interpolations of various data types.
*
* The type of interpolation is chosen automatically depending on the
* types of the arguments.
*/
template <typename T>
struct Interpolator
{
// ------------------------------------------------------------------
/** @brief Get the result of the interpolation between a,b.
*
* The interpolation algorithm depends on the type of the operands.
* aiQuaternion's and aiQuatKey's SLERP, the rest does a simple
* linear interpolation. */
void operator () (T& out,const T& a, const T& b, ai_real d) const {
out = a + (b-a)*d;
}
}; // ! Interpolator <T>
//! @cond Never
template <>
struct Interpolator <aiQuaternion> {
void operator () (aiQuaternion& out,const aiQuaternion& a,
const aiQuaternion& b, ai_real d) const
{
aiQuaternion::Interpolate(out,a,b,d);
}
}; // ! Interpolator <aiQuaternion>
template <>
struct Interpolator <unsigned int> {
void operator () (unsigned int& out,unsigned int a,
unsigned int b, ai_real d) const
{
out = d>0.5f ? b : a;
}
}; // ! Interpolator <aiQuaternion>
template <>
struct Interpolator<aiVectorKey> {
void operator () (aiVector3D& out,const aiVectorKey& a,
const aiVectorKey& b, ai_real d) const
{
Interpolator<aiVector3D> ipl;
ipl(out,a.mValue,b.mValue,d);
}
}; // ! Interpolator <aiVectorKey>
template <>
struct Interpolator<aiQuatKey> {
void operator () (aiQuaternion& out, const aiQuatKey& a,
const aiQuatKey& b, ai_real d) const
{
Interpolator<aiQuaternion> ipl;
ipl(out,a.mValue,b.mValue,d);
}
}; // ! Interpolator <aiQuatKey>
template <>
struct Interpolator<aiMeshKey> {
void operator () (unsigned int& out, const aiMeshKey& a,
const aiMeshKey& b, ai_real d) const
{
Interpolator<unsigned int> ipl;
ipl(out,a.mValue,b.mValue,d);
}
}; // ! Interpolator <aiQuatKey>
//! @endcond
} // ! end namespace Assimp
#endif // __cplusplus
#endif // AI_ANIM_H_INC

View File

@ -0,0 +1,221 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file camera.h
* @brief Defines the aiCamera data structure
*/
#pragma once
#ifndef AI_CAMERA_H_INC
#define AI_CAMERA_H_INC
#include "types.h"
#ifdef __cplusplus
extern "C" {
#endif
// ---------------------------------------------------------------------------
/** Helper structure to describe a virtual camera.
*
* Cameras have a representation in the node graph and can be animated.
* An important aspect is that the camera itself is also part of the
* scene-graph. This means, any values such as the look-at vector are not
* *absolute*, they're <b>relative</b> to the coordinate system defined
* by the node which corresponds to the camera. This allows for camera
* animations. For static cameras parameters like the 'look-at' or 'up' vectors
* are usually specified directly in aiCamera, but beware, they could also
* be encoded in the node transformation. The following (pseudo)code sample
* shows how to do it: <br><br>
* @code
* // Get the camera matrix for a camera at a specific time
* // if the node hierarchy for the camera does not contain
* // at least one animated node this is a static computation
* get-camera-matrix (node sceneRoot, camera cam) : matrix
* {
* node cnd = find-node-for-camera(cam)
* matrix cmt = identity()
*
* // as usual - get the absolute camera transformation for this frame
* for each node nd in hierarchy from sceneRoot to cnd
* matrix cur
* if (is-animated(nd))
* cur = eval-animation(nd)
* else cur = nd->mTransformation;
* cmt = mult-matrices( cmt, cur )
* end for
*
* // now multiply with the camera's own local transform
* cam = mult-matrices (cam, get-camera-matrix(cmt) )
* }
* @endcode
*
* @note some file formats (such as 3DS, ASE) export a "target point" -
* the point the camera is looking at (it can even be animated). Assimp
* writes the target point as a subnode of the camera's main node,
* called "<camName>.Target". However this is just additional information
* then the transformation tracks of the camera main node make the
* camera already look in the right direction.
*
*/
struct aiCamera
{
/** The name of the camera.
*
* There must be a node in the scenegraph with the same name.
* This node specifies the position of the camera in the scene
* hierarchy and can be animated.
*/
C_STRUCT aiString mName;
/** Position of the camera relative to the coordinate space
* defined by the corresponding node.
*
* The default value is 0|0|0.
*/
C_STRUCT aiVector3D mPosition;
/** 'Up' - vector of the camera coordinate system relative to
* the coordinate space defined by the corresponding node.
*
* The 'right' vector of the camera coordinate system is
* the cross product of the up and lookAt vectors.
* The default value is 0|1|0. The vector
* may be normalized, but it needn't.
*/
C_STRUCT aiVector3D mUp;
/** 'LookAt' - vector of the camera coordinate system relative to
* the coordinate space defined by the corresponding node.
*
* This is the viewing direction of the user.
* The default value is 0|0|1. The vector
* may be normalized, but it needn't.
*/
C_STRUCT aiVector3D mLookAt;
/** Half horizontal field of view angle, in radians.
*
* The field of view angle is the angle between the center
* line of the screen and the left or right border.
* The default value is 1/4PI.
*/
float mHorizontalFOV;
/** Distance of the near clipping plane from the camera.
*
* The value may not be 0.f (for arithmetic reasons to prevent
* a division through zero). The default value is 0.1f.
*/
float mClipPlaneNear;
/** Distance of the far clipping plane from the camera.
*
* The far clipping plane must, of course, be further away than the
* near clipping plane. The default value is 1000.f. The ratio
* between the near and the far plane should not be too
* large (between 1000-10000 should be ok) to avoid floating-point
* inaccuracies which could lead to z-fighting.
*/
float mClipPlaneFar;
/** Screen aspect ratio.
*
* This is the ration between the width and the height of the
* screen. Typical values are 4/3, 1/2 or 1/1. This value is
* 0 if the aspect ratio is not defined in the source file.
* 0 is also the default value.
*/
float mAspect;
#ifdef __cplusplus
aiCamera() AI_NO_EXCEPT
: mUp (0.f,1.f,0.f)
, mLookAt (0.f,0.f,1.f)
, mHorizontalFOV (0.25f * (float)AI_MATH_PI)
, mClipPlaneNear (0.1f)
, mClipPlaneFar (1000.f)
, mAspect (0.f)
{}
/** @brief Get a *right-handed* camera matrix from me
* @param out Camera matrix to be filled
*/
void GetCameraMatrix (aiMatrix4x4& out) const
{
/** todo: test ... should work, but i'm not absolutely sure */
/** We don't know whether these vectors are already normalized ...*/
aiVector3D zaxis = mLookAt; zaxis.Normalize();
aiVector3D yaxis = mUp; yaxis.Normalize();
aiVector3D xaxis = mUp^mLookAt; xaxis.Normalize();
out.a4 = -(xaxis * mPosition);
out.b4 = -(yaxis * mPosition);
out.c4 = -(zaxis * mPosition);
out.a1 = xaxis.x;
out.a2 = xaxis.y;
out.a3 = xaxis.z;
out.b1 = yaxis.x;
out.b2 = yaxis.y;
out.b3 = yaxis.z;
out.c1 = zaxis.x;
out.c2 = zaxis.y;
out.c3 = zaxis.z;
out.d1 = out.d2 = out.d3 = 0.f;
out.d4 = 1.f;
}
#endif
};
#ifdef __cplusplus
}
#endif
#endif // AI_CAMERA_H_INC

View File

@ -0,0 +1,261 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2011, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file cexport.h
* @brief Defines the C-API for the Assimp export interface
*/
#pragma once
#ifndef AI_EXPORT_H_INC
#define AI_EXPORT_H_INC
#ifndef ASSIMP_BUILD_NO_EXPORT
// Public ASSIMP data structures
#include <assimp/types.h>
#ifdef __cplusplus
extern "C" {
#endif
struct aiScene; // aiScene.h
struct aiFileIO; // aiFileIO.h
// --------------------------------------------------------------------------------
/** Describes an file format which Assimp can export to. Use #aiGetExportFormatCount() to
* learn how many export formats the current Assimp build supports and #aiGetExportFormatDescription()
* to retrieve a description of an export format option.
*/
struct aiExportFormatDesc
{
/// a short string ID to uniquely identify the export format. Use this ID string to
/// specify which file format you want to export to when calling #aiExportScene().
/// Example: "dae" or "obj"
const char* id;
/// A short description of the file format to present to users. Useful if you want
/// to allow the user to select an export format.
const char* description;
/// Recommended file extension for the exported file in lower case.
const char* fileExtension;
};
// --------------------------------------------------------------------------------
/** Returns the number of export file formats available in the current Assimp build.
* Use aiGetExportFormatDescription() to retrieve infos of a specific export format.
*/
ASSIMP_API size_t aiGetExportFormatCount(void);
// --------------------------------------------------------------------------------
/** Returns a description of the nth export file format. Use #aiGetExportFormatCount()
* to learn how many export formats are supported. The description must be released by
* calling aiReleaseExportFormatDescription afterwards.
* @param pIndex Index of the export format to retrieve information for. Valid range is
* 0 to #aiGetExportFormatCount()
* @return A description of that specific export format. NULL if pIndex is out of range.
*/
ASSIMP_API const C_STRUCT aiExportFormatDesc* aiGetExportFormatDescription( size_t pIndex);
// --------------------------------------------------------------------------------
/** Release a description of the nth export file format. Must be returned by
* aiGetExportFormatDescription
* @param desc Pointer to the description
*/
ASSIMP_API void aiReleaseExportFormatDescription( const C_STRUCT aiExportFormatDesc *desc );
// --------------------------------------------------------------------------------
/** Create a modifiable copy of a scene.
* This is useful to import files via Assimp, change their topology and
* export them again. Since the scene returned by the various importer functions
* is const, a modifiable copy is needed.
* @param pIn Valid scene to be copied
* @param pOut Receives a modifyable copy of the scene. Use aiFreeScene() to
* delete it again.
*/
ASSIMP_API void aiCopyScene(const C_STRUCT aiScene* pIn,
C_STRUCT aiScene** pOut);
// --------------------------------------------------------------------------------
/** Frees a scene copy created using aiCopyScene() */
ASSIMP_API void aiFreeScene(const C_STRUCT aiScene* pIn);
// --------------------------------------------------------------------------------
/** Exports the given scene to a chosen file format and writes the result file(s) to disk.
* @param pScene The scene to export. Stays in possession of the caller, is not changed by the function.
* The scene is expected to conform to Assimp's Importer output format as specified
* in the @link data Data Structures Page @endlink. In short, this means the model data
* should use a right-handed coordinate systems, face winding should be counter-clockwise
* and the UV coordinate origin is assumed to be in the upper left. If your input data
* uses different conventions, have a look at the last parameter.
* @param pFormatId ID string to specify to which format you want to export to. Use
* aiGetExportFormatCount() / aiGetExportFormatDescription() to learn which export formats are available.
* @param pFileName Output file to write
* @param pPreprocessing Accepts any choice of the #aiPostProcessSteps enumerated
* flags, but in reality only a subset of them makes sense here. Specifying
* 'preprocessing' flags is useful if the input scene does not conform to
* Assimp's default conventions as specified in the @link data Data Structures Page @endlink.
* In short, this means the geometry data should use a right-handed coordinate systems, face
* winding should be counter-clockwise and the UV coordinate origin is assumed to be in
* the upper left. The #aiProcess_MakeLeftHanded, #aiProcess_FlipUVs and
* #aiProcess_FlipWindingOrder flags are used in the import side to allow users
* to have those defaults automatically adapted to their conventions. Specifying those flags
* for exporting has the opposite effect, respectively. Some other of the
* #aiPostProcessSteps enumerated values may be useful as well, but you'll need
* to try out what their effect on the exported file is. Many formats impose
* their own restrictions on the structure of the geometry stored therein,
* so some preprocessing may have little or no effect at all, or may be
* redundant as exporters would apply them anyhow. A good example
* is triangulation - whilst you can enforce it by specifying
* the #aiProcess_Triangulate flag, most export formats support only
* triangulate data so they would run the step anyway.
*
* If assimp detects that the input scene was directly taken from the importer side of
* the library (i.e. not copied using aiCopyScene and potetially modified afterwards),
* any postprocessing steps already applied to the scene will not be applied again, unless
* they show non-idempotent behaviour (#aiProcess_MakeLeftHanded, #aiProcess_FlipUVs and
* #aiProcess_FlipWindingOrder).
* @return a status code indicating the result of the export
* @note Use aiCopyScene() to get a modifiable copy of a previously
* imported scene.
*/
ASSIMP_API aiReturn aiExportScene( const C_STRUCT aiScene* pScene,
const char* pFormatId,
const char* pFileName,
unsigned int pPreprocessing);
// --------------------------------------------------------------------------------
/** Exports the given scene to a chosen file format using custom IO logic supplied by you.
* @param pScene The scene to export. Stays in possession of the caller, is not changed by the function.
* @param pFormatId ID string to specify to which format you want to export to. Use
* aiGetExportFormatCount() / aiGetExportFormatDescription() to learn which export formats are available.
* @param pFileName Output file to write
* @param pIO custom IO implementation to be used. Use this if you use your own storage methods.
* If none is supplied, a default implementation using standard file IO is used. Note that
* #aiExportSceneToBlob is provided as convenience function to export to memory buffers.
* @param pPreprocessing Please see the documentation for #aiExportScene
* @return a status code indicating the result of the export
* @note Include <aiFileIO.h> for the definition of #aiFileIO.
* @note Use aiCopyScene() to get a modifiable copy of a previously
* imported scene.
*/
ASSIMP_API aiReturn aiExportSceneEx( const C_STRUCT aiScene* pScene,
const char* pFormatId,
const char* pFileName,
C_STRUCT aiFileIO* pIO,
unsigned int pPreprocessing );
// --------------------------------------------------------------------------------
/** Describes a blob of exported scene data. Use #aiExportSceneToBlob() to create a blob containing an
* exported scene. The memory referred by this structure is owned by Assimp.
* to free its resources. Don't try to free the memory on your side - it will crash for most build configurations
* due to conflicting heaps.
*
* Blobs can be nested - each blob may reference another blob, which may in turn reference another blob and so on.
* This is used when exporters write more than one output file for a given #aiScene. See the remarks for
* #aiExportDataBlob::name for more information.
*/
struct aiExportDataBlob
{
/// Size of the data in bytes
size_t size;
/// The data.
void* data;
/** Name of the blob. An empty string always
indicates the first (and primary) blob,
which contains the actual file data.
Any other blobs are auxiliary files produced
by exporters (i.e. material files). Existence
of such files depends on the file format. Most
formats don't split assets across multiple files.
If used, blob names usually contain the file
extension that should be used when writing
the data to disc.
*/
C_STRUCT aiString name;
/** Pointer to the next blob in the chain or NULL if there is none. */
C_STRUCT aiExportDataBlob * next;
#ifdef __cplusplus
/// Default constructor
aiExportDataBlob() { size = 0; data = next = NULL; }
/// Releases the data
~aiExportDataBlob() { delete [] static_cast<unsigned char*>( data ); delete next; }
private:
// no copying
aiExportDataBlob(const aiExportDataBlob& );
aiExportDataBlob& operator= (const aiExportDataBlob& );
#endif // __cplusplus
};
// --------------------------------------------------------------------------------
/** Exports the given scene to a chosen file format. Returns the exported data as a binary blob which
* you can write into a file or something. When you're done with the data, use #aiReleaseExportBlob()
* to free the resources associated with the export.
* @param pScene The scene to export. Stays in possession of the caller, is not changed by the function.
* @param pFormatId ID string to specify to which format you want to export to. Use
* #aiGetExportFormatCount() / #aiGetExportFormatDescription() to learn which export formats are available.
* @param pPreprocessing Please see the documentation for #aiExportScene
* @return the exported data or NULL in case of error
*/
ASSIMP_API const C_STRUCT aiExportDataBlob* aiExportSceneToBlob( const C_STRUCT aiScene* pScene, const char* pFormatId,
unsigned int pPreprocessing );
// --------------------------------------------------------------------------------
/** Releases the memory associated with the given exported data. Use this function to free a data blob
* returned by aiExportScene().
* @param pData the data blob returned by #aiExportSceneToBlob
*/
ASSIMP_API void aiReleaseExportBlob( const C_STRUCT aiExportDataBlob* pData );
#ifdef __cplusplus
}
#endif
#endif // ASSIMP_BUILD_NO_EXPORT
#endif // AI_EXPORT_H_INC

View File

@ -0,0 +1,138 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file cfileio.h
* @brief Defines generic C routines to access memory-mapped files
*/
#pragma once
#ifndef AI_FILEIO_H_INC
#define AI_FILEIO_H_INC
#include <assimp/types.h>
#ifdef __cplusplus
extern "C" {
#endif
struct aiFileIO;
struct aiFile;
// aiFile callbacks
typedef size_t (*aiFileWriteProc) (C_STRUCT aiFile*, const char*, size_t, size_t);
typedef size_t (*aiFileReadProc) (C_STRUCT aiFile*, char*, size_t,size_t);
typedef size_t (*aiFileTellProc) (C_STRUCT aiFile*);
typedef void (*aiFileFlushProc) (C_STRUCT aiFile*);
typedef C_ENUM aiReturn (*aiFileSeek) (C_STRUCT aiFile*, size_t, C_ENUM aiOrigin);
// aiFileIO callbacks
typedef C_STRUCT aiFile* (*aiFileOpenProc) (C_STRUCT aiFileIO*, const char*, const char*);
typedef void (*aiFileCloseProc) (C_STRUCT aiFileIO*, C_STRUCT aiFile*);
// Represents user-defined data
typedef char* aiUserData;
// ----------------------------------------------------------------------------------
/** @brief C-API: File system callbacks
*
* Provided are functions to open and close files. Supply a custom structure to
* the import function. If you don't, a default implementation is used. Use custom
* file systems to enable reading from other sources, such as ZIPs
* or memory locations. */
struct aiFileIO
{
/** Function used to open a new file
*/
aiFileOpenProc OpenProc;
/** Function used to close an existing file
*/
aiFileCloseProc CloseProc;
/** User-defined, opaque data */
aiUserData UserData;
};
// ----------------------------------------------------------------------------------
/** @brief C-API: File callbacks
*
* Actually, it's a data structure to wrap a set of fXXXX (e.g fopen)
* replacement functions.
*
* The default implementation of the functions utilizes the fXXX functions from
* the CRT. However, you can supply a custom implementation to Assimp by
* delivering a custom aiFileIO. Use this to enable reading from other sources,
* such as ZIP archives or memory locations. */
struct aiFile
{
/** Callback to read from a file */
aiFileReadProc ReadProc;
/** Callback to write to a file */
aiFileWriteProc WriteProc;
/** Callback to retrieve the current position of
* the file cursor (ftell())
*/
aiFileTellProc TellProc;
/** Callback to retrieve the size of the file,
* in bytes
*/
aiFileTellProc FileSizeProc;
/** Callback to set the current position
* of the file cursor (fseek())
*/
aiFileSeek SeekProc;
/** Callback to flush the file contents
*/
aiFileFlushProc FlushProc;
/** User-defined, opaque data
*/
aiUserData UserData;
};
#ifdef __cplusplus
}
#endif
#endif // AI_FILEIO_H_INC

View File

@ -0,0 +1,565 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file cimport.h
* @brief Defines the C-API to the Open Asset Import Library.
*/
#pragma once
#ifndef AI_ASSIMP_H_INC
#define AI_ASSIMP_H_INC
#include <assimp/types.h>
#include "importerdesc.h"
#ifdef __cplusplus
extern "C" {
#endif
struct aiScene; // aiScene.h
struct aiFileIO; // aiFileIO.h
typedef void (*aiLogStreamCallback)(const char* /* message */, char* /* user */);
// --------------------------------------------------------------------------------
/** C-API: Represents a log stream. A log stream receives all log messages and
* streams them _somewhere_.
* @see aiGetPredefinedLogStream
* @see aiAttachLogStream
* @see aiDetachLogStream */
// --------------------------------------------------------------------------------
struct aiLogStream
{
/** callback to be called */
aiLogStreamCallback callback;
/** user data to be passed to the callback */
char* user;
};
// --------------------------------------------------------------------------------
/** C-API: Represents an opaque set of settings to be used during importing.
* @see aiCreatePropertyStore
* @see aiReleasePropertyStore
* @see aiImportFileExWithProperties
* @see aiSetPropertyInteger
* @see aiSetPropertyFloat
* @see aiSetPropertyString
* @see aiSetPropertyMatrix
*/
// --------------------------------------------------------------------------------
struct aiPropertyStore { char sentinel; };
/** Our own C boolean type */
typedef int aiBool;
#define AI_FALSE 0
#define AI_TRUE 1
// --------------------------------------------------------------------------------
/** Reads the given file and returns its content.
*
* If the call succeeds, the imported data is returned in an aiScene structure.
* The data is intended to be read-only, it stays property of the ASSIMP
* library and will be stable until aiReleaseImport() is called. After you're
* done with it, call aiReleaseImport() to free the resources associated with
* this file. If the import fails, NULL is returned instead. Call
* aiGetErrorString() to retrieve a human-readable error text.
* @param pFile Path and filename of the file to be imported,
* expected to be a null-terminated c-string. NULL is not a valid value.
* @param pFlags Optional post processing steps to be executed after
* a successful import. Provide a bitwise combination of the
* #aiPostProcessSteps flags.
* @return Pointer to the imported data or NULL if the import failed.
*/
ASSIMP_API const C_STRUCT aiScene* aiImportFile(
const char* pFile,
unsigned int pFlags);
// --------------------------------------------------------------------------------
/** Reads the given file using user-defined I/O functions and returns
* its content.
*
* If the call succeeds, the imported data is returned in an aiScene structure.
* The data is intended to be read-only, it stays property of the ASSIMP
* library and will be stable until aiReleaseImport() is called. After you're
* done with it, call aiReleaseImport() to free the resources associated with
* this file. If the import fails, NULL is returned instead. Call
* aiGetErrorString() to retrieve a human-readable error text.
* @param pFile Path and filename of the file to be imported,
* expected to be a null-terminated c-string. NULL is not a valid value.
* @param pFlags Optional post processing steps to be executed after
* a successful import. Provide a bitwise combination of the
* #aiPostProcessSteps flags.
* @param pFS aiFileIO structure. Will be used to open the model file itself
* and any other files the loader needs to open. Pass NULL to use the default
* implementation.
* @return Pointer to the imported data or NULL if the import failed.
* @note Include <aiFileIO.h> for the definition of #aiFileIO.
*/
ASSIMP_API const C_STRUCT aiScene* aiImportFileEx(
const char* pFile,
unsigned int pFlags,
C_STRUCT aiFileIO* pFS);
// --------------------------------------------------------------------------------
/** Same as #aiImportFileEx, but adds an extra parameter containing importer settings.
*
* @param pFile Path and filename of the file to be imported,
* expected to be a null-terminated c-string. NULL is not a valid value.
* @param pFlags Optional post processing steps to be executed after
* a successful import. Provide a bitwise combination of the
* #aiPostProcessSteps flags.
* @param pFS aiFileIO structure. Will be used to open the model file itself
* and any other files the loader needs to open. Pass NULL to use the default
* implementation.
* @param pProps #aiPropertyStore instance containing import settings.
* @return Pointer to the imported data or NULL if the import failed.
* @note Include <aiFileIO.h> for the definition of #aiFileIO.
* @see aiImportFileEx
*/
ASSIMP_API const C_STRUCT aiScene* aiImportFileExWithProperties(
const char* pFile,
unsigned int pFlags,
C_STRUCT aiFileIO* pFS,
const C_STRUCT aiPropertyStore* pProps);
// --------------------------------------------------------------------------------
/** Reads the given file from a given memory buffer,
*
* If the call succeeds, the contents of the file are returned as a pointer to an
* aiScene object. The returned data is intended to be read-only, the importer keeps
* ownership of the data and will destroy it upon destruction. If the import fails,
* NULL is returned.
* A human-readable error description can be retrieved by calling aiGetErrorString().
* @param pBuffer Pointer to the file data
* @param pLength Length of pBuffer, in bytes
* @param pFlags Optional post processing steps to be executed after
* a successful import. Provide a bitwise combination of the
* #aiPostProcessSteps flags. If you wish to inspect the imported
* scene first in order to fine-tune your post-processing setup,
* consider to use #aiApplyPostProcessing().
* @param pHint An additional hint to the library. If this is a non empty string,
* the library looks for a loader to support the file extension specified by pHint
* and passes the file to the first matching loader. If this loader is unable to
* completely the request, the library continues and tries to determine the file
* format on its own, a task that may or may not be successful.
* Check the return value, and you'll know ...
* @return A pointer to the imported data, NULL if the import failed.
*
* @note This is a straightforward way to decode models from memory
* buffers, but it doesn't handle model formats that spread their
* data across multiple files or even directories. Examples include
* OBJ or MD3, which outsource parts of their material info into
* external scripts. If you need full functionality, provide
* a custom IOSystem to make Assimp find these files and use
* the regular aiImportFileEx()/aiImportFileExWithProperties() API.
*/
ASSIMP_API const C_STRUCT aiScene* aiImportFileFromMemory(
const char* pBuffer,
unsigned int pLength,
unsigned int pFlags,
const char* pHint);
// --------------------------------------------------------------------------------
/** Same as #aiImportFileFromMemory, but adds an extra parameter containing importer settings.
*
* @param pBuffer Pointer to the file data
* @param pLength Length of pBuffer, in bytes
* @param pFlags Optional post processing steps to be executed after
* a successful import. Provide a bitwise combination of the
* #aiPostProcessSteps flags. If you wish to inspect the imported
* scene first in order to fine-tune your post-processing setup,
* consider to use #aiApplyPostProcessing().
* @param pHint An additional hint to the library. If this is a non empty string,
* the library looks for a loader to support the file extension specified by pHint
* and passes the file to the first matching loader. If this loader is unable to
* completely the request, the library continues and tries to determine the file
* format on its own, a task that may or may not be successful.
* Check the return value, and you'll know ...
* @param pProps #aiPropertyStore instance containing import settings.
* @return A pointer to the imported data, NULL if the import failed.
*
* @note This is a straightforward way to decode models from memory
* buffers, but it doesn't handle model formats that spread their
* data across multiple files or even directories. Examples include
* OBJ or MD3, which outsource parts of their material info into
* external scripts. If you need full functionality, provide
* a custom IOSystem to make Assimp find these files and use
* the regular aiImportFileEx()/aiImportFileExWithProperties() API.
* @see aiImportFileFromMemory
*/
ASSIMP_API const C_STRUCT aiScene* aiImportFileFromMemoryWithProperties(
const char* pBuffer,
unsigned int pLength,
unsigned int pFlags,
const char* pHint,
const C_STRUCT aiPropertyStore* pProps);
// --------------------------------------------------------------------------------
/** Apply post-processing to an already-imported scene.
*
* This is strictly equivalent to calling #aiImportFile()/#aiImportFileEx with the
* same flags. However, you can use this separate function to inspect the imported
* scene first to fine-tune your post-processing setup.
* @param pScene Scene to work on.
* @param pFlags Provide a bitwise combination of the #aiPostProcessSteps flags.
* @return A pointer to the post-processed data. Post processing is done in-place,
* meaning this is still the same #aiScene which you passed for pScene. However,
* _if_ post-processing failed, the scene could now be NULL. That's quite a rare
* case, post processing steps are not really designed to 'fail'. To be exact,
* the #aiProcess_ValidateDataStructure flag is currently the only post processing step
* which can actually cause the scene to be reset to NULL.
*/
ASSIMP_API const C_STRUCT aiScene* aiApplyPostProcessing(
const C_STRUCT aiScene* pScene,
unsigned int pFlags);
// --------------------------------------------------------------------------------
/** Get one of the predefine log streams. This is the quick'n'easy solution to
* access Assimp's log system. Attaching a log stream can slightly reduce Assimp's
* overall import performance.
*
* Usage is rather simple (this will stream the log to a file, named log.txt, and
* the stdout stream of the process:
* @code
* struct aiLogStream c;
* c = aiGetPredefinedLogStream(aiDefaultLogStream_FILE,"log.txt");
* aiAttachLogStream(&c);
* c = aiGetPredefinedLogStream(aiDefaultLogStream_STDOUT,NULL);
* aiAttachLogStream(&c);
* @endcode
*
* @param pStreams One of the #aiDefaultLogStream enumerated values.
* @param file Solely for the #aiDefaultLogStream_FILE flag: specifies the file to write to.
* Pass NULL for all other flags.
* @return The log stream. callback is set to NULL if something went wrong.
*/
ASSIMP_API C_STRUCT aiLogStream aiGetPredefinedLogStream(
C_ENUM aiDefaultLogStream pStreams,
const char* file);
// --------------------------------------------------------------------------------
/** Attach a custom log stream to the libraries' logging system.
*
* Attaching a log stream can slightly reduce Assimp's overall import
* performance. Multiple log-streams can be attached.
* @param stream Describes the new log stream.
* @note To ensure proper destruction of the logging system, you need to manually
* call aiDetachLogStream() on every single log stream you attach.
* Alternatively (for the lazy folks) #aiDetachAllLogStreams is provided.
*/
ASSIMP_API void aiAttachLogStream(
const C_STRUCT aiLogStream* stream);
// --------------------------------------------------------------------------------
/** Enable verbose logging. Verbose logging includes debug-related stuff and
* detailed import statistics. This can have severe impact on import performance
* and memory consumption. However, it might be useful to find out why a file
* didn't read correctly.
* @param d AI_TRUE or AI_FALSE, your decision.
*/
ASSIMP_API void aiEnableVerboseLogging(aiBool d);
// --------------------------------------------------------------------------------
/** Detach a custom log stream from the libraries' logging system.
*
* This is the counterpart of #aiAttachLogStream. If you attached a stream,
* don't forget to detach it again.
* @param stream The log stream to be detached.
* @return AI_SUCCESS if the log stream has been detached successfully.
* @see aiDetachAllLogStreams
*/
ASSIMP_API C_ENUM aiReturn aiDetachLogStream(
const C_STRUCT aiLogStream* stream);
// --------------------------------------------------------------------------------
/** Detach all active log streams from the libraries' logging system.
* This ensures that the logging system is terminated properly and all
* resources allocated by it are actually freed. If you attached a stream,
* don't forget to detach it again.
* @see aiAttachLogStream
* @see aiDetachLogStream
*/
ASSIMP_API void aiDetachAllLogStreams(void);
// --------------------------------------------------------------------------------
/** Releases all resources associated with the given import process.
*
* Call this function after you're done with the imported data.
* @param pScene The imported data to release. NULL is a valid value.
*/
ASSIMP_API void aiReleaseImport(
const C_STRUCT aiScene* pScene);
// --------------------------------------------------------------------------------
/** Returns the error text of the last failed import process.
*
* @return A textual description of the error that occurred at the last
* import process. NULL if there was no error. There can't be an error if you
* got a non-NULL #aiScene from #aiImportFile/#aiImportFileEx/#aiApplyPostProcessing.
*/
ASSIMP_API const char* aiGetErrorString(void);
// --------------------------------------------------------------------------------
/** Returns whether a given file extension is supported by ASSIMP
*
* @param szExtension Extension for which the function queries support for.
* Must include a leading dot '.'. Example: ".3ds", ".md3"
* @return AI_TRUE if the file extension is supported.
*/
ASSIMP_API aiBool aiIsExtensionSupported(
const char* szExtension);
// --------------------------------------------------------------------------------
/** Get a list of all file extensions supported by ASSIMP.
*
* If a file extension is contained in the list this does, of course, not
* mean that ASSIMP is able to load all files with this extension.
* @param szOut String to receive the extension list.
* Format of the list: "*.3ds;*.obj;*.dae". NULL is not a valid parameter.
*/
ASSIMP_API void aiGetExtensionList(
C_STRUCT aiString* szOut);
// --------------------------------------------------------------------------------
/** Get the approximated storage required by an imported asset
* @param pIn Input asset.
* @param in Data structure to be filled.
*/
ASSIMP_API void aiGetMemoryRequirements(
const C_STRUCT aiScene* pIn,
C_STRUCT aiMemoryInfo* in);
// --------------------------------------------------------------------------------
/** Create an empty property store. Property stores are used to collect import
* settings.
* @return New property store. Property stores need to be manually destroyed using
* the #aiReleasePropertyStore API function.
*/
ASSIMP_API C_STRUCT aiPropertyStore* aiCreatePropertyStore(void);
// --------------------------------------------------------------------------------
/** Delete a property store.
* @param p Property store to be deleted.
*/
ASSIMP_API void aiReleasePropertyStore(C_STRUCT aiPropertyStore* p);
// --------------------------------------------------------------------------------
/** Set an integer property.
*
* This is the C-version of #Assimp::Importer::SetPropertyInteger(). In the C
* interface, properties are always shared by all imports. It is not possible to
* specify them per import.
*
* @param store Store to modify. Use #aiCreatePropertyStore to obtain a store.
* @param szName Name of the configuration property to be set. All supported
* public properties are defined in the config.h header file (AI_CONFIG_XXX).
* @param value New value for the property
*/
ASSIMP_API void aiSetImportPropertyInteger(
C_STRUCT aiPropertyStore* store,
const char* szName,
int value);
// --------------------------------------------------------------------------------
/** Set a floating-point property.
*
* This is the C-version of #Assimp::Importer::SetPropertyFloat(). In the C
* interface, properties are always shared by all imports. It is not possible to
* specify them per import.
*
* @param store Store to modify. Use #aiCreatePropertyStore to obtain a store.
* @param szName Name of the configuration property to be set. All supported
* public properties are defined in the config.h header file (AI_CONFIG_XXX).
* @param value New value for the property
*/
ASSIMP_API void aiSetImportPropertyFloat(
C_STRUCT aiPropertyStore* store,
const char* szName,
ai_real value);
// --------------------------------------------------------------------------------
/** Set a string property.
*
* This is the C-version of #Assimp::Importer::SetPropertyString(). In the C
* interface, properties are always shared by all imports. It is not possible to
* specify them per import.
*
* @param store Store to modify. Use #aiCreatePropertyStore to obtain a store.
* @param szName Name of the configuration property to be set. All supported
* public properties are defined in the config.h header file (AI_CONFIG_XXX).
* @param st New value for the property
*/
ASSIMP_API void aiSetImportPropertyString(
C_STRUCT aiPropertyStore* store,
const char* szName,
const C_STRUCT aiString* st);
// --------------------------------------------------------------------------------
/** Set a matrix property.
*
* This is the C-version of #Assimp::Importer::SetPropertyMatrix(). In the C
* interface, properties are always shared by all imports. It is not possible to
* specify them per import.
*
* @param store Store to modify. Use #aiCreatePropertyStore to obtain a store.
* @param szName Name of the configuration property to be set. All supported
* public properties are defined in the config.h header file (AI_CONFIG_XXX).
* @param mat New value for the property
*/
ASSIMP_API void aiSetImportPropertyMatrix(
C_STRUCT aiPropertyStore* store,
const char* szName,
const C_STRUCT aiMatrix4x4* mat);
// --------------------------------------------------------------------------------
/** Construct a quaternion from a 3x3 rotation matrix.
* @param quat Receives the output quaternion.
* @param mat Matrix to 'quaternionize'.
* @see aiQuaternion(const aiMatrix3x3& pRotMatrix)
*/
ASSIMP_API void aiCreateQuaternionFromMatrix(
C_STRUCT aiQuaternion* quat,
const C_STRUCT aiMatrix3x3* mat);
// --------------------------------------------------------------------------------
/** Decompose a transformation matrix into its rotational, translational and
* scaling components.
*
* @param mat Matrix to decompose
* @param scaling Receives the scaling component
* @param rotation Receives the rotational component
* @param position Receives the translational component.
* @see aiMatrix4x4::Decompose (aiVector3D&, aiQuaternion&, aiVector3D&) const;
*/
ASSIMP_API void aiDecomposeMatrix(
const C_STRUCT aiMatrix4x4* mat,
C_STRUCT aiVector3D* scaling,
C_STRUCT aiQuaternion* rotation,
C_STRUCT aiVector3D* position);
// --------------------------------------------------------------------------------
/** Transpose a 4x4 matrix.
* @param mat Pointer to the matrix to be transposed
*/
ASSIMP_API void aiTransposeMatrix4(
C_STRUCT aiMatrix4x4* mat);
// --------------------------------------------------------------------------------
/** Transpose a 3x3 matrix.
* @param mat Pointer to the matrix to be transposed
*/
ASSIMP_API void aiTransposeMatrix3(
C_STRUCT aiMatrix3x3* mat);
// --------------------------------------------------------------------------------
/** Transform a vector by a 3x3 matrix
* @param vec Vector to be transformed.
* @param mat Matrix to transform the vector with.
*/
ASSIMP_API void aiTransformVecByMatrix3(
C_STRUCT aiVector3D* vec,
const C_STRUCT aiMatrix3x3* mat);
// --------------------------------------------------------------------------------
/** Transform a vector by a 4x4 matrix
* @param vec Vector to be transformed.
* @param mat Matrix to transform the vector with.
*/
ASSIMP_API void aiTransformVecByMatrix4(
C_STRUCT aiVector3D* vec,
const C_STRUCT aiMatrix4x4* mat);
// --------------------------------------------------------------------------------
/** Multiply two 4x4 matrices.
* @param dst First factor, receives result.
* @param src Matrix to be multiplied with 'dst'.
*/
ASSIMP_API void aiMultiplyMatrix4(
C_STRUCT aiMatrix4x4* dst,
const C_STRUCT aiMatrix4x4* src);
// --------------------------------------------------------------------------------
/** Multiply two 3x3 matrices.
* @param dst First factor, receives result.
* @param src Matrix to be multiplied with 'dst'.
*/
ASSIMP_API void aiMultiplyMatrix3(
C_STRUCT aiMatrix3x3* dst,
const C_STRUCT aiMatrix3x3* src);
// --------------------------------------------------------------------------------
/** Get a 3x3 identity matrix.
* @param mat Matrix to receive its personal identity
*/
ASSIMP_API void aiIdentityMatrix3(
C_STRUCT aiMatrix3x3* mat);
// --------------------------------------------------------------------------------
/** Get a 4x4 identity matrix.
* @param mat Matrix to receive its personal identity
*/
ASSIMP_API void aiIdentityMatrix4(
C_STRUCT aiMatrix4x4* mat);
// --------------------------------------------------------------------------------
/** Returns the number of import file formats available in the current Assimp build.
* Use aiGetImportFormatDescription() to retrieve infos of a specific import format.
*/
ASSIMP_API size_t aiGetImportFormatCount(void);
// --------------------------------------------------------------------------------
/** Returns a description of the nth import file format. Use #aiGetImportFormatCount()
* to learn how many import formats are supported.
* @param pIndex Index of the import format to retrieve information for. Valid range is
* 0 to #aiGetImportFormatCount()
* @return A description of that specific import format. NULL if pIndex is out of range.
*/
ASSIMP_API const C_STRUCT aiImporterDesc* aiGetImportFormatDescription( size_t pIndex);
#ifdef __cplusplus
}
#endif
#endif // AI_ASSIMP_H_INC

View File

@ -0,0 +1,104 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file color4.h
* @brief RGBA color structure, including operators when compiling in C++
*/
#pragma once
#ifndef AI_COLOR4D_H_INC
#define AI_COLOR4D_H_INC
#include "defs.h"
#ifdef __cplusplus
// ----------------------------------------------------------------------------------
/** Represents a color in Red-Green-Blue space including an
* alpha component. Color values range from 0 to 1. */
// ----------------------------------------------------------------------------------
template <typename TReal>
class aiColor4t
{
public:
aiColor4t() AI_NO_EXCEPT : r(), g(), b(), a() {}
aiColor4t (TReal _r, TReal _g, TReal _b, TReal _a)
: r(_r), g(_g), b(_b), a(_a) {}
explicit aiColor4t (TReal _r) : r(_r), g(_r), b(_r), a(_r) {}
aiColor4t (const aiColor4t& o) = default;
public:
// combined operators
const aiColor4t& operator += (const aiColor4t& o);
const aiColor4t& operator -= (const aiColor4t& o);
const aiColor4t& operator *= (TReal f);
const aiColor4t& operator /= (TReal f);
public:
// comparison
bool operator == (const aiColor4t& other) const;
bool operator != (const aiColor4t& other) const;
bool operator < (const aiColor4t& other) const;
// color tuple access, rgba order
inline TReal operator[](unsigned int i) const;
inline TReal& operator[](unsigned int i);
/** check whether a color is (close to) black */
inline bool IsBlack() const;
public:
// Red, green, blue and alpha color values
TReal r, g, b, a;
}; // !struct aiColor4D
typedef aiColor4t<ai_real> aiColor4D;
#else
struct aiColor4D {
ai_real r, g, b, a;
};
#endif // __cplusplus
#endif // AI_COLOR4D_H_INC

View File

@ -0,0 +1,209 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file color4.inl
* @brief Inline implementation of aiColor4t<TReal> operators
*/
#pragma once
#ifndef AI_COLOR4D_INL_INC
#define AI_COLOR4D_INL_INC
#ifdef __cplusplus
#include "color4.h"
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE const aiColor4t<TReal>& aiColor4t<TReal>::operator += (const aiColor4t<TReal>& o) {
r += o.r; g += o.g; b += o.b; a += o.a;
return *this;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE const aiColor4t<TReal>& aiColor4t<TReal>::operator -= (const aiColor4t<TReal>& o) {
r -= o.r; g -= o.g; b -= o.b; a -= o.a;
return *this;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE const aiColor4t<TReal>& aiColor4t<TReal>::operator *= (TReal f) {
r *= f; g *= f; b *= f; a *= f;
return *this;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE const aiColor4t<TReal>& aiColor4t<TReal>::operator /= (TReal f) {
r /= f; g /= f; b /= f; a /= f;
return *this;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE TReal aiColor4t<TReal>::operator[](unsigned int i) const {
switch ( i ) {
case 0:
return r;
case 1:
return g;
case 2:
return b;
case 3:
return a;
default:
break;
}
return r;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE TReal& aiColor4t<TReal>::operator[](unsigned int i) {
switch ( i ) {
case 0:
return r;
case 1:
return g;
case 2:
return b;
case 3:
return a;
default:
break;
}
return r;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE bool aiColor4t<TReal>::operator== (const aiColor4t<TReal>& other) const {
return r == other.r && g == other.g && b == other.b && a == other.a;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE bool aiColor4t<TReal>::operator!= (const aiColor4t<TReal>& other) const {
return r != other.r || g != other.g || b != other.b || a != other.a;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE bool aiColor4t<TReal>::operator< (const aiColor4t<TReal>& other) const {
return r < other.r || (
r == other.r && (
g < other.g || (
g == other.g && (
b < other.b || (
b == other.b && (
a < other.a
)
)
)
)
)
);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator + (const aiColor4t<TReal>& v1, const aiColor4t<TReal>& v2) {
return aiColor4t<TReal>( v1.r + v2.r, v1.g + v2.g, v1.b + v2.b, v1.a + v2.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator - (const aiColor4t<TReal>& v1, const aiColor4t<TReal>& v2) {
return aiColor4t<TReal>( v1.r - v2.r, v1.g - v2.g, v1.b - v2.b, v1.a - v2.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator * (const aiColor4t<TReal>& v1, const aiColor4t<TReal>& v2) {
return aiColor4t<TReal>( v1.r * v2.r, v1.g * v2.g, v1.b * v2.b, v1.a * v2.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator / (const aiColor4t<TReal>& v1, const aiColor4t<TReal>& v2) {
return aiColor4t<TReal>( v1.r / v2.r, v1.g / v2.g, v1.b / v2.b, v1.a / v2.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator * ( TReal f, const aiColor4t<TReal>& v) {
return aiColor4t<TReal>( f*v.r, f*v.g, f*v.b, f*v.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator * ( const aiColor4t<TReal>& v, TReal f) {
return aiColor4t<TReal>( f*v.r, f*v.g, f*v.b, f*v.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator / ( const aiColor4t<TReal>& v, TReal f) {
return v * (1/f);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator / ( TReal f,const aiColor4t<TReal>& v) {
return aiColor4t<TReal>(f,f,f,f)/v;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator + ( const aiColor4t<TReal>& v, TReal f) {
return aiColor4t<TReal>( f+v.r, f+v.g, f+v.b, f+v.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator - ( const aiColor4t<TReal>& v, TReal f) {
return aiColor4t<TReal>( v.r-f, v.g-f, v.b-f, v.a-f);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator + ( TReal f, const aiColor4t<TReal>& v) {
return aiColor4t<TReal>( f+v.r, f+v.g, f+v.b, f+v.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
AI_FORCE_INLINE aiColor4t<TReal> operator - ( TReal f, const aiColor4t<TReal>& v) {
return aiColor4t<TReal>( f-v.r, f-v.g, f-v.b, f-v.a);
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline bool aiColor4t<TReal> :: IsBlack() const {
// The alpha component doesn't care here. black is black.
static const TReal epsilon = 10e-3f;
return std::fabs( r ) < epsilon && std::fabs( g ) < epsilon && std::fabs( b ) < epsilon;
}
#endif // __cplusplus
#endif // AI_VECTOR3D_INL_INC

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,310 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file defs.h
* @brief Assimp build configuration setup. See the notes in the comment
* blocks to find out how to customize _your_ Assimp build.
*/
#pragma once
#ifndef AI_DEFINES_H_INC
#define AI_DEFINES_H_INC
#include <assimp/config.h>
//////////////////////////////////////////////////////////////////////////
/* Define ASSIMP_BUILD_NO_XX_IMPORTER to disable a specific
* file format loader. The loader is be excluded from the
* build in this case. 'XX' stands for the most common file
* extension of the file format. E.g.:
* ASSIMP_BUILD_NO_X_IMPORTER disables the X loader.
*
* If you're unsure about that, take a look at the implementation of the
* import plugin you wish to disable. You'll find the right define in the
* first lines of the corresponding unit.
*
* Other (mixed) configuration switches are listed here:
* ASSIMP_BUILD_NO_COMPRESSED_X
* - Disable support for compressed X files (zip)
* ASSIMP_BUILD_NO_COMPRESSED_BLEND
* - Disable support for compressed Blender files (zip)
* ASSIMP_BUILD_NO_COMPRESSED_IFC
* - Disable support for IFCZIP files (unzip)
*/
//////////////////////////////////////////////////////////////////////////
#ifndef ASSIMP_BUILD_NO_COMPRESSED_X
# define ASSIMP_BUILD_NEED_Z_INFLATE
#endif
#ifndef ASSIMP_BUILD_NO_COMPRESSED_BLEND
# define ASSIMP_BUILD_NEED_Z_INFLATE
#endif
#ifndef ASSIMP_BUILD_NO_COMPRESSED_IFC
# define ASSIMP_BUILD_NEED_Z_INFLATE
# define ASSIMP_BUILD_NEED_UNZIP
#endif
#ifndef ASSIMP_BUILD_NO_Q3BSP_IMPORTER
# define ASSIMP_BUILD_NEED_Z_INFLATE
# define ASSIMP_BUILD_NEED_UNZIP
#endif
//////////////////////////////////////////////////////////////////////////
/* Define ASSIMP_BUILD_NO_XX_PROCESS to disable a specific
* post processing step. This is the current list of process names ('XX'):
* CALCTANGENTS
* JOINVERTICES
* TRIANGULATE
* DROPFACENORMALS
* GENFACENORMALS
* GENVERTEXNORMALS
* REMOVEVC
* SPLITLARGEMESHES
* PRETRANSFORMVERTICES
* LIMITBONEWEIGHTS
* VALIDATEDS
* IMPROVECACHELOCALITY
* FIXINFACINGNORMALS
* REMOVE_REDUNDANTMATERIALS
* OPTIMIZEGRAPH
* SORTBYPTYPE
* FINDINVALIDDATA
* TRANSFORMTEXCOORDS
* GENUVCOORDS
* ENTITYMESHBUILDER
* EMBEDTEXTURES
* MAKELEFTHANDED
* FLIPUVS
* FLIPWINDINGORDER
* OPTIMIZEMESHES
* OPTIMIZEANIMS
* OPTIMIZEGRAPH
* GENENTITYMESHES
* FIXTEXTUREPATHS
* GENBOUNDINGBOXES */
//////////////////////////////////////////////////////////////////////////
#ifdef _MSC_VER
# undef ASSIMP_API
//////////////////////////////////////////////////////////////////////////
/* Define 'ASSIMP_BUILD_DLL_EXPORT' to build a DLL of the library */
//////////////////////////////////////////////////////////////////////////
# ifdef ASSIMP_BUILD_DLL_EXPORT
# define ASSIMP_API __declspec(dllexport)
# define ASSIMP_API_WINONLY __declspec(dllexport)
# pragma warning (disable : 4251)
//////////////////////////////////////////////////////////////////////////
/* Define 'ASSIMP_DLL' before including Assimp to link to ASSIMP in
* an external DLL under Windows. Default is static linkage. */
//////////////////////////////////////////////////////////////////////////
# elif (defined ASSIMP_DLL)
# define ASSIMP_API __declspec(dllimport)
# define ASSIMP_API_WINONLY __declspec(dllimport)
# else
# define ASSIMP_API
# define ASSIMP_API_WINONLY
# endif
/* Force the compiler to inline a function, if possible
*/
# define AI_FORCE_INLINE __forceinline
/* Tells the compiler that a function never returns. Used in code analysis
* to skip dead paths (e.g. after an assertion evaluated to false). */
# define AI_WONT_RETURN __declspec(noreturn)
#elif defined(SWIG)
/* Do nothing, the relevant defines are all in AssimpSwigPort.i */
#else
# define AI_WONT_RETURN
# define ASSIMP_API __attribute__ ((visibility("default")))
# define ASSIMP_API_WINONLY
# define AI_FORCE_INLINE inline
#endif // (defined _MSC_VER)
#ifdef __GNUC__
# define AI_WONT_RETURN_SUFFIX __attribute__((noreturn))
#else
# define AI_WONT_RETURN_SUFFIX
#endif // (defined __clang__)
#ifdef __cplusplus
/* No explicit 'struct' and 'enum' tags for C++, this keeps showing up
* in doxydocs.
*/
# define C_STRUCT
# define C_ENUM
#else
//////////////////////////////////////////////////////////////////////////
/* To build the documentation, make sure ASSIMP_DOXYGEN_BUILD
* is defined by Doxygen's preprocessor. The corresponding
* entries in the DOXYFILE are: */
//////////////////////////////////////////////////////////////////////////
#if 0
ENABLE_PREPROCESSING = YES
MACRO_EXPANSION = YES
EXPAND_ONLY_PREDEF = YES
SEARCH_INCLUDES = YES
INCLUDE_PATH =
INCLUDE_FILE_PATTERNS =
PREDEFINED = ASSIMP_DOXYGEN_BUILD=1
EXPAND_AS_DEFINED = C_STRUCT C_ENUM
SKIP_FUNCTION_MACROS = YES
#endif
//////////////////////////////////////////////////////////////////////////
/* Doxygen gets confused if we use c-struct typedefs to avoid
* the explicit 'struct' notation. This trick here has the same
* effect as the TYPEDEF_HIDES_STRUCT option, but we don't need
* to typedef all structs/enums. */
//////////////////////////////////////////////////////////////////////////
# if (defined ASSIMP_DOXYGEN_BUILD)
# define C_STRUCT
# define C_ENUM
# else
# define C_STRUCT struct
# define C_ENUM enum
# endif
#endif
#if (defined(__BORLANDC__) || defined (__BCPLUSPLUS__))
# error Currently, Borland is unsupported. Feel free to port Assimp.
#endif
//////////////////////////////////////////////////////////////////////////
/* Define ASSIMP_BUILD_SINGLETHREADED to compile assimp
* without threading support. The library doesn't utilize
* threads then and is itself not threadsafe. */
//////////////////////////////////////////////////////////////////////////
#ifndef ASSIMP_BUILD_SINGLETHREADED
# define ASSIMP_BUILD_SINGLETHREADED
#endif
#if defined(_DEBUG) || ! defined(NDEBUG)
# define ASSIMP_BUILD_DEBUG
#endif
//////////////////////////////////////////////////////////////////////////
/* Define ASSIMP_DOUBLE_PRECISION to compile assimp
* with double precision support (64-bit). */
//////////////////////////////////////////////////////////////////////////
#ifdef ASSIMP_DOUBLE_PRECISION
typedef double ai_real;
typedef signed long long int ai_int;
typedef unsigned long long int ai_uint;
#ifndef ASSIMP_AI_REAL_TEXT_PRECISION
#define ASSIMP_AI_REAL_TEXT_PRECISION 16
#endif // ASSIMP_AI_REAL_TEXT_PRECISION
#else // ASSIMP_DOUBLE_PRECISION
typedef float ai_real;
typedef signed int ai_int;
typedef unsigned int ai_uint;
#ifndef ASSIMP_AI_REAL_TEXT_PRECISION
#define ASSIMP_AI_REAL_TEXT_PRECISION 8
#endif // ASSIMP_AI_REAL_TEXT_PRECISION
#endif // ASSIMP_DOUBLE_PRECISION
//////////////////////////////////////////////////////////////////////////
/* Useful constants */
//////////////////////////////////////////////////////////////////////////
/* This is PI. Hi PI. */
#define AI_MATH_PI (3.141592653589793238462643383279 )
#define AI_MATH_TWO_PI (AI_MATH_PI * 2.0)
#define AI_MATH_HALF_PI (AI_MATH_PI * 0.5)
/* And this is to avoid endless casts to float */
#define AI_MATH_PI_F (3.1415926538f)
#define AI_MATH_TWO_PI_F (AI_MATH_PI_F * 2.0f)
#define AI_MATH_HALF_PI_F (AI_MATH_PI_F * 0.5f)
/* Tiny macro to convert from radians to degrees and back */
#define AI_DEG_TO_RAD(x) ((x)*(ai_real)0.0174532925)
#define AI_RAD_TO_DEG(x) ((x)*(ai_real)57.2957795)
/* Numerical limits */
static const ai_real ai_epsilon = (ai_real) 0.00001;
/* Support for big-endian builds */
#if defined(__BYTE_ORDER__)
# if (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)
# if !defined(__BIG_ENDIAN__)
# define __BIG_ENDIAN__
# endif
# else /* little endian */
# if defined (__BIG_ENDIAN__)
# undef __BIG_ENDIAN__
# endif
# endif
#endif
#if defined(__BIG_ENDIAN__)
# define AI_BUILD_BIG_ENDIAN
#endif
/* To avoid running out of memory
* This can be adjusted for specific use cases
* It's NOT a total limit, just a limit for individual allocations
*/
#define AI_MAX_ALLOC(type) ((256U * 1024 * 1024) / sizeof(type))
#ifndef _MSC_VER
# define AI_NO_EXCEPT noexcept
#else
# if (_MSC_VER >= 1915 )
# define AI_NO_EXCEPT noexcept
# else
# define AI_NO_EXCEPT
# endif
#endif // _MSC_VER
#endif // !! AI_DEFINES_H_INC

View File

@ -0,0 +1,373 @@
#pragma once
// Copyright (C) 2002-2007 Nikolaus Gebhardt
// This file is part of the "Irrlicht Engine" and the "irrXML" project.
// For conditions of distribution and use, see copyright notice in irrlicht.h and irrXML.h
// ------------------------------------------------------------------------------------
// Original description: (Schrompf)
// Adapted to the ASSIMP library because the builtin atof indeed takes AGES to parse a
// float inside a large string. Before parsing, it does a strlen on the given point.
// Changes:
// 22nd October 08 (Aramis_acg): Added temporary cast to double, added strtoul10_64
// to ensure long numbers are handled correctly
// ------------------------------------------------------------------------------------
#ifndef FAST_A_TO_F_H_INCLUDED
#define FAST_A_TO_F_H_INCLUDED
#include <cmath>
#include <limits>
#include <stdint.h>
#include <stdexcept>
#include <assimp/defs.h>
#include "StringComparison.h"
#include <assimp/DefaultLogger.hpp>
#ifdef _MSC_VER
# include <stdint.h>
#else
# include <assimp/Compiler/pstdint.h>
#endif
namespace Assimp {
const double fast_atof_table[16] = { // we write [16] here instead of [] to work around a swig bug
0.0,
0.1,
0.01,
0.001,
0.0001,
0.00001,
0.000001,
0.0000001,
0.00000001,
0.000000001,
0.0000000001,
0.00000000001,
0.000000000001,
0.0000000000001,
0.00000000000001,
0.000000000000001
};
// ------------------------------------------------------------------------------------
// Convert a string in decimal format to a number
// ------------------------------------------------------------------------------------
inline
unsigned int strtoul10( const char* in, const char** out=0) {
unsigned int value = 0;
for ( ;; ) {
if ( *in < '0' || *in > '9' ) {
break;
}
value = ( value * 10 ) + ( *in - '0' );
++in;
}
if ( out ) {
*out = in;
}
return value;
}
// ------------------------------------------------------------------------------------
// Convert a string in octal format to a number
// ------------------------------------------------------------------------------------
inline
unsigned int strtoul8( const char* in, const char** out=0) {
unsigned int value( 0 );
for ( ;; ) {
if ( *in < '0' || *in > '7' ) {
break;
}
value = ( value << 3 ) + ( *in - '0' );
++in;
}
if ( out ) {
*out = in;
}
return value;
}
// ------------------------------------------------------------------------------------
// Convert a string in hex format to a number
// ------------------------------------------------------------------------------------
inline
unsigned int strtoul16( const char* in, const char** out=0) {
unsigned int value( 0 );
for ( ;; ) {
if ( *in >= '0' && *in <= '9' ) {
value = ( value << 4u ) + ( *in - '0' );
} else if (*in >= 'A' && *in <= 'F') {
value = ( value << 4u ) + ( *in - 'A' ) + 10;
} else if (*in >= 'a' && *in <= 'f') {
value = ( value << 4u ) + ( *in - 'a' ) + 10;
} else {
break;
}
++in;
}
if ( out ) {
*out = in;
}
return value;
}
// ------------------------------------------------------------------------------------
// Convert just one hex digit
// Return value is UINT_MAX if the input character is not a hex digit.
// ------------------------------------------------------------------------------------
inline
unsigned int HexDigitToDecimal(char in) {
unsigned int out( UINT_MAX );
if ( in >= '0' && in <= '9' ) {
out = in - '0';
} else if ( in >= 'a' && in <= 'f' ) {
out = 10u + in - 'a';
} else if ( in >= 'A' && in <= 'F' ) {
out = 10u + in - 'A';
}
// return value is UINT_MAX if the input is not a hex digit
return out;
}
// ------------------------------------------------------------------------------------
// Convert a hex-encoded octet (2 characters, i.e. df or 1a).
// ------------------------------------------------------------------------------------
inline
uint8_t HexOctetToDecimal(const char* in) {
return ((uint8_t)HexDigitToDecimal(in[0])<<4)+(uint8_t)HexDigitToDecimal(in[1]);
}
// ------------------------------------------------------------------------------------
// signed variant of strtoul10
// ------------------------------------------------------------------------------------
inline
int strtol10( const char* in, const char** out=0) {
bool inv = (*in=='-');
if ( inv || *in == '+' ) {
++in;
}
int value = strtoul10(in,out);
if (inv) {
value = -value;
}
return value;
}
// ------------------------------------------------------------------------------------
// Parse a C++-like integer literal - hex and oct prefixes.
// 0xNNNN - hex
// 0NNN - oct
// NNN - dec
// ------------------------------------------------------------------------------------
inline
unsigned int strtoul_cppstyle( const char* in, const char** out=0) {
if ('0' == in[0]) {
return 'x' == in[1] ? strtoul16(in+2,out) : strtoul8(in+1,out);
}
return strtoul10(in, out);
}
// ------------------------------------------------------------------------------------
// Special version of the function, providing higher accuracy and safety
// It is mainly used by fast_atof to prevent ugly and unwanted integer overflows.
// ------------------------------------------------------------------------------------
inline
uint64_t strtoul10_64( const char* in, const char** out=0, unsigned int* max_inout=0) {
unsigned int cur = 0;
uint64_t value = 0;
if ( *in < '0' || *in > '9' ) {
throw std::invalid_argument( std::string( "The string \"" ) + in + "\" cannot be converted into a value." );
}
for ( ;; ) {
if ( *in < '0' || *in > '9' ) {
break;
}
const uint64_t new_value = ( value * (uint64_t) 10 ) + ( (uint64_t) ( *in - '0' ) );
// numeric overflow, we rely on you
if ( new_value < value ) {
ASSIMP_LOG_WARN_F( "Converting the string \"", in, "\" into a value resulted in overflow." );
return 0;
}
value = new_value;
++in;
++cur;
if (max_inout && *max_inout == cur) {
if (out) { /* skip to end */
while ( *in >= '0' && *in <= '9' ) {
++in;
}
*out = in;
}
return value;
}
}
if ( out ) {
*out = in;
}
if ( max_inout ) {
*max_inout = cur;
}
return value;
}
// ------------------------------------------------------------------------------------
// signed variant of strtoul10_64
// ------------------------------------------------------------------------------------
inline
int64_t strtol10_64(const char* in, const char** out = 0, unsigned int* max_inout = 0) {
bool inv = (*in == '-');
if ( inv || *in == '+' ) {
++in;
}
int64_t value = strtoul10_64(in, out, max_inout);
if (inv) {
value = -value;
}
return value;
}
// Number of relevant decimals for floating-point parsing.
#define AI_FAST_ATOF_RELAVANT_DECIMALS 15
// ------------------------------------------------------------------------------------
//! Provides a fast function for converting a string into a float,
//! about 6 times faster than atof in win32.
// If you find any bugs, please send them to me, niko (at) irrlicht3d.org.
// ------------------------------------------------------------------------------------
template<typename Real>
inline
const char* fast_atoreal_move(const char* c, Real& out, bool check_comma = true) {
Real f = 0;
bool inv = (*c == '-');
if (inv || *c == '+') {
++c;
}
if ((c[0] == 'N' || c[0] == 'n') && ASSIMP_strincmp(c, "nan", 3) == 0) {
out = std::numeric_limits<Real>::quiet_NaN();
c += 3;
return c;
}
if ((c[0] == 'I' || c[0] == 'i') && ASSIMP_strincmp(c, "inf", 3) == 0) {
out = std::numeric_limits<Real>::infinity();
if (inv) {
out = -out;
}
c += 3;
if ((c[0] == 'I' || c[0] == 'i') && ASSIMP_strincmp(c, "inity", 5) == 0) {
c += 5;
}
return c;
}
if (!(c[0] >= '0' && c[0] <= '9') &&
!((c[0] == '.' || (check_comma && c[0] == ',')) && c[1] >= '0' && c[1] <= '9')) {
throw std::invalid_argument("Cannot parse string "
"as real number: does not start with digit "
"or decimal point followed by digit.");
}
if (*c != '.' && (! check_comma || c[0] != ',')) {
f = static_cast<Real>( strtoul10_64 ( c, &c) );
}
if ((*c == '.' || (check_comma && c[0] == ',')) && c[1] >= '0' && c[1] <= '9') {
++c;
// NOTE: The original implementation is highly inaccurate here. The precision of a single
// IEEE 754 float is not high enough, everything behind the 6th digit tends to be more
// inaccurate than it would need to be. Casting to double seems to solve the problem.
// strtol_64 is used to prevent integer overflow.
// Another fix: this tends to become 0 for long numbers if we don't limit the maximum
// number of digits to be read. AI_FAST_ATOF_RELAVANT_DECIMALS can be a value between
// 1 and 15.
unsigned int diff = AI_FAST_ATOF_RELAVANT_DECIMALS;
double pl = static_cast<double>( strtoul10_64 ( c, &c, &diff ));
pl *= fast_atof_table[diff];
f += static_cast<Real>( pl );
}
// For backwards compatibility: eat trailing dots, but not trailing commas.
else if (*c == '.') {
++c;
}
// A major 'E' must be allowed. Necessary for proper reading of some DXF files.
// Thanks to Zhao Lei to point out that this if() must be outside the if (*c == '.' ..)
if (*c == 'e' || *c == 'E') {
++c;
const bool einv = (*c=='-');
if (einv || *c=='+') {
++c;
}
// The reason float constants are used here is that we've seen cases where compilers
// would perform such casts on compile-time constants at runtime, which would be
// bad considering how frequently fast_atoreal_move<float> is called in Assimp.
Real exp = static_cast<Real>( strtoul10_64(c, &c) );
if (einv) {
exp = -exp;
}
f *= std::pow(static_cast<Real>(10.0), exp);
}
if (inv) {
f = -f;
}
out = f;
return c;
}
// ------------------------------------------------------------------------------------
// The same but more human.
inline
ai_real fast_atof(const char* c) {
ai_real ret(0.0);
fast_atoreal_move<ai_real>(c, ret);
return ret;
}
inline
ai_real fast_atof( const char* c, const char** cout) {
ai_real ret(0.0);
*cout = fast_atoreal_move<ai_real>(c, ret);
return ret;
}
inline
ai_real fast_atof( const char** inout) {
ai_real ret(0.0);
*inout = fast_atoreal_move<ai_real>(*inout, ret);
return ret;
}
} //! namespace Assimp
#endif // FAST_A_TO_F_H_INCLUDED

View File

@ -0,0 +1,146 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file importerdesc.h
* @brief #aiImporterFlags, aiImporterDesc implementation.
*/
#pragma once
#ifndef AI_IMPORTER_DESC_H_INC
#define AI_IMPORTER_DESC_H_INC
/** Mixed set of flags for #aiImporterDesc, indicating some features
* common to many importers*/
enum aiImporterFlags
{
/** Indicates that there is a textual encoding of the
* file format; and that it is supported.*/
aiImporterFlags_SupportTextFlavour = 0x1,
/** Indicates that there is a binary encoding of the
* file format; and that it is supported.*/
aiImporterFlags_SupportBinaryFlavour = 0x2,
/** Indicates that there is a compressed encoding of the
* file format; and that it is supported.*/
aiImporterFlags_SupportCompressedFlavour = 0x4,
/** Indicates that the importer reads only a very particular
* subset of the file format. This happens commonly for
* declarative or procedural formats which cannot easily
* be mapped to #aiScene */
aiImporterFlags_LimitedSupport = 0x8,
/** Indicates that the importer is highly experimental and
* should be used with care. This only happens for trunk
* (i.e. SVN) versions, experimental code is not included
* in releases. */
aiImporterFlags_Experimental = 0x10
};
/** Meta information about a particular importer. Importers need to fill
* this structure, but they can freely decide how talkative they are.
* A common use case for loader meta info is a user interface
* in which the user can choose between various import/export file
* formats. Building such an UI by hand means a lot of maintenance
* as importers/exporters are added to Assimp, so it might be useful
* to have a common mechanism to query some rough importer
* characteristics. */
struct aiImporterDesc
{
/** Full name of the importer (i.e. Blender3D importer)*/
const char* mName;
/** Original author (left blank if unknown or whole assimp team) */
const char* mAuthor;
/** Current maintainer, left blank if the author maintains */
const char* mMaintainer;
/** Implementation comments, i.e. unimplemented features*/
const char* mComments;
/** These flags indicate some characteristics common to many
importers. */
unsigned int mFlags;
/** Minimum format version that can be loaded im major.minor format,
both are set to 0 if there is either no version scheme
or if the loader doesn't care. */
unsigned int mMinMajor;
unsigned int mMinMinor;
/** Maximum format version that can be loaded im major.minor format,
both are set to 0 if there is either no version scheme
or if the loader doesn't care. Loaders that expect to be
forward-compatible to potential future format versions should
indicate zero, otherwise they should specify the current
maximum version.*/
unsigned int mMaxMajor;
unsigned int mMaxMinor;
/** List of file extensions this importer can handle.
List entries are separated by space characters.
All entries are lower case without a leading dot (i.e.
"xml dae" would be a valid value. Note that multiple
importers may respond to the same file extension -
assimp calls all importers in the order in which they
are registered and each importer gets the opportunity
to load the file until one importer "claims" the file. Apart
from file extension checks, importers typically use
other methods to quickly reject files (i.e. magic
words) so this does not mean that common or generic
file extensions such as XML would be tediously slow. */
const char* mFileExtensions;
};
/** \brief Returns the Importer description for a given extension.
Will return a NULL-pointer if no assigned importer desc. was found for the given extension
\param extension [in] The extension to look for
\return A pointer showing to the ImporterDesc, \see aiImporterDesc.
*/
ASSIMP_API const C_STRUCT aiImporterDesc* aiGetImporterDesc( const char *extension );
#endif // AI_IMPORTER_DESC_H_INC

View File

@ -0,0 +1,149 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
#ifndef INCLUDED_AI_IRRXML_WRAPPER
#define INCLUDED_AI_IRRXML_WRAPPER
// some long includes ....
#ifdef ASSIMP_USE_HUNTER
# include <irrXML/irrXML.h>
#else
# include <irrXML.h>
#endif
#include "IOStream.hpp"
#include "BaseImporter.h"
#include <vector>
namespace Assimp {
// ---------------------------------------------------------------------------------
/** @brief Utility class to make IrrXML work together with our custom IO system
* See the IrrXML docs for more details.
*
* Construct IrrXML-Reader in BaseImporter::InternReadFile():
* @code
* // open the file
* std::unique_ptr<IOStream> file( pIOHandler->Open( pFile));
* if( file.get() == NULL) {
* throw DeadlyImportError( "Failed to open file " + pFile + ".");
* }
*
* // generate a XML reader for it
* std::unique_ptr<CIrrXML_IOStreamReader> mIOWrapper( new CIrrXML_IOStreamReader( file.get()));
* mReader = irr::io::createIrrXMLReader( mIOWrapper.get());
* if( !mReader) {
* ThrowException( "xxxx: Unable to open file.");
* }
* @endcode
**/
class CIrrXML_IOStreamReader : public irr::io::IFileReadCallBack {
public:
// ----------------------------------------------------------------------------------
//! Construction from an existing IOStream
explicit CIrrXML_IOStreamReader(IOStream* _stream)
: stream (_stream)
, t (0)
{
// Map the buffer into memory and convert it to UTF8. IrrXML provides its
// own conversion, which is merely a cast from uintNN_t to uint8_t. Thus,
// it is not suitable for our purposes and we have to do it BEFORE IrrXML
// gets the buffer. Sadly, this forces us to map the whole file into
// memory.
data.resize(stream->FileSize());
stream->Read(&data[0],data.size(),1);
// Remove null characters from the input sequence otherwise the parsing will utterly fail
// std::find is usually much faster than manually iterating
// It is very unlikely that there will be any null characters
auto null_char_iter = std::find(data.begin(), data.end(), '\0');
while (null_char_iter != data.end())
{
null_char_iter = data.erase(null_char_iter);
null_char_iter = std::find(null_char_iter, data.end(), '\0');
}
BaseImporter::ConvertToUTF8(data);
}
// ----------------------------------------------------------------------------------
//! Virtual destructor
virtual ~CIrrXML_IOStreamReader() {}
// ----------------------------------------------------------------------------------
//! Reads an amount of bytes from the file.
/** @param buffer: Pointer to output buffer.
* @param sizeToRead: Amount of bytes to read
* @return Returns how much bytes were read. */
virtual int read(void* buffer, int sizeToRead) {
if(sizeToRead<0) {
return 0;
}
if(t+sizeToRead>data.size()) {
sizeToRead = static_cast<int>(data.size()-t);
}
memcpy(buffer,&data.front()+t,sizeToRead);
t += sizeToRead;
return sizeToRead;
}
// ----------------------------------------------------------------------------------
//! Returns size of file in bytes
virtual int getSize() {
return (int)data.size();
}
private:
IOStream* stream;
std::vector<char> data;
size_t t;
}; // ! class CIrrXML_IOStreamReader
} // ! Assimp
#endif // !! INCLUDED_AI_IRRXML_WRAPPER

View File

@ -0,0 +1,259 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file light.h
* @brief Defines the aiLight data structure
*/
#pragma once
#ifndef AI_LIGHT_H_INC
#define AI_LIGHT_H_INC
#include "types.h"
#ifdef __cplusplus
extern "C" {
#endif
// ---------------------------------------------------------------------------
/** Enumerates all supported types of light sources.
*/
enum aiLightSourceType
{
aiLightSource_UNDEFINED = 0x0,
//! A directional light source has a well-defined direction
//! but is infinitely far away. That's quite a good
//! approximation for sun light.
aiLightSource_DIRECTIONAL = 0x1,
//! A point light source has a well-defined position
//! in space but no direction - it emits light in all
//! directions. A normal bulb is a point light.
aiLightSource_POINT = 0x2,
//! A spot light source emits light in a specific
//! angle. It has a position and a direction it is pointing to.
//! A good example for a spot light is a light spot in
//! sport arenas.
aiLightSource_SPOT = 0x3,
//! The generic light level of the world, including the bounces
//! of all other light sources.
//! Typically, there's at most one ambient light in a scene.
//! This light type doesn't have a valid position, direction, or
//! other properties, just a color.
aiLightSource_AMBIENT = 0x4,
//! An area light is a rectangle with predefined size that uniformly
//! emits light from one of its sides. The position is center of the
//! rectangle and direction is its normal vector.
aiLightSource_AREA = 0x5,
/** This value is not used. It is just there to force the
* compiler to map this enum to a 32 Bit integer.
*/
#ifndef SWIG
_aiLightSource_Force32Bit = INT_MAX
#endif
};
// ---------------------------------------------------------------------------
/** Helper structure to describe a light source.
*
* Assimp supports multiple sorts of light sources, including
* directional, point and spot lights. All of them are defined with just
* a single structure and distinguished by their parameters.
* Note - some file formats (such as 3DS, ASE) export a "target point" -
* the point a spot light is looking at (it can even be animated). Assimp
* writes the target point as a subnode of a spotlights's main node,
* called "<spotName>.Target". However, this is just additional information
* then, the transformation tracks of the main node make the
* spot light already point in the right direction.
*/
struct aiLight
{
/** The name of the light source.
*
* There must be a node in the scenegraph with the same name.
* This node specifies the position of the light in the scene
* hierarchy and can be animated.
*/
C_STRUCT aiString mName;
/** The type of the light source.
*
* aiLightSource_UNDEFINED is not a valid value for this member.
*/
C_ENUM aiLightSourceType mType;
/** Position of the light source in space. Relative to the
* transformation of the node corresponding to the light.
*
* The position is undefined for directional lights.
*/
C_STRUCT aiVector3D mPosition;
/** Direction of the light source in space. Relative to the
* transformation of the node corresponding to the light.
*
* The direction is undefined for point lights. The vector
* may be normalized, but it needn't.
*/
C_STRUCT aiVector3D mDirection;
/** Up direction of the light source in space. Relative to the
* transformation of the node corresponding to the light.
*
* The direction is undefined for point lights. The vector
* may be normalized, but it needn't.
*/
C_STRUCT aiVector3D mUp;
/** Constant light attenuation factor.
*
* The intensity of the light source at a given distance 'd' from
* the light's position is
* @code
* Atten = 1/( att0 + att1 * d + att2 * d*d)
* @endcode
* This member corresponds to the att0 variable in the equation.
* Naturally undefined for directional lights.
*/
float mAttenuationConstant;
/** Linear light attenuation factor.
*
* The intensity of the light source at a given distance 'd' from
* the light's position is
* @code
* Atten = 1/( att0 + att1 * d + att2 * d*d)
* @endcode
* This member corresponds to the att1 variable in the equation.
* Naturally undefined for directional lights.
*/
float mAttenuationLinear;
/** Quadratic light attenuation factor.
*
* The intensity of the light source at a given distance 'd' from
* the light's position is
* @code
* Atten = 1/( att0 + att1 * d + att2 * d*d)
* @endcode
* This member corresponds to the att2 variable in the equation.
* Naturally undefined for directional lights.
*/
float mAttenuationQuadratic;
/** Diffuse color of the light source
*
* The diffuse light color is multiplied with the diffuse
* material color to obtain the final color that contributes
* to the diffuse shading term.
*/
C_STRUCT aiColor3D mColorDiffuse;
/** Specular color of the light source
*
* The specular light color is multiplied with the specular
* material color to obtain the final color that contributes
* to the specular shading term.
*/
C_STRUCT aiColor3D mColorSpecular;
/** Ambient color of the light source
*
* The ambient light color is multiplied with the ambient
* material color to obtain the final color that contributes
* to the ambient shading term. Most renderers will ignore
* this value it, is just a remaining of the fixed-function pipeline
* that is still supported by quite many file formats.
*/
C_STRUCT aiColor3D mColorAmbient;
/** Inner angle of a spot light's light cone.
*
* The spot light has maximum influence on objects inside this
* angle. The angle is given in radians. It is 2PI for point
* lights and undefined for directional lights.
*/
float mAngleInnerCone;
/** Outer angle of a spot light's light cone.
*
* The spot light does not affect objects outside this angle.
* The angle is given in radians. It is 2PI for point lights and
* undefined for directional lights. The outer angle must be
* greater than or equal to the inner angle.
* It is assumed that the application uses a smooth
* interpolation between the inner and the outer cone of the
* spot light.
*/
float mAngleOuterCone;
/** Size of area light source. */
C_STRUCT aiVector2D mSize;
#ifdef __cplusplus
aiLight() AI_NO_EXCEPT
: mType (aiLightSource_UNDEFINED)
, mAttenuationConstant (0.f)
, mAttenuationLinear (1.f)
, mAttenuationQuadratic (0.f)
, mAngleInnerCone ((float)AI_MATH_TWO_PI)
, mAngleOuterCone ((float)AI_MATH_TWO_PI)
, mSize (0.f, 0.f)
{
}
#endif
};
#ifdef __cplusplus
}
#endif
#endif // !! AI_LIGHT_H_INC

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,390 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file material.inl
* @brief Defines the C++ getters for the material system
*/
#pragma once
#ifndef AI_MATERIAL_INL_INC
#define AI_MATERIAL_INL_INC
// ---------------------------------------------------------------------------
inline aiPropertyTypeInfo ai_real_to_property_type_info(float)
{
return aiPTI_Float;
}
inline aiPropertyTypeInfo ai_real_to_property_type_info(double)
{
return aiPTI_Double;
}
// ---------------------------------------------------------------------------
//! @cond never
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::GetTexture( aiTextureType type,
unsigned int index,
C_STRUCT aiString* path,
aiTextureMapping* mapping /*= NULL*/,
unsigned int* uvindex /*= NULL*/,
ai_real* blend /*= NULL*/,
aiTextureOp* op /*= NULL*/,
aiTextureMapMode* mapmode /*= NULL*/) const
{
return ::aiGetMaterialTexture(this,type,index,path,mapping,uvindex,blend,op,mapmode);
}
// ---------------------------------------------------------------------------
inline unsigned int aiMaterial::GetTextureCount(aiTextureType type) const
{
return ::aiGetMaterialTextureCount(this,type);
}
// ---------------------------------------------------------------------------
template <typename Type>
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx, Type* pOut,
unsigned int* pMax) const
{
unsigned int iNum = pMax ? *pMax : 1;
const aiMaterialProperty* prop;
const aiReturn ret = ::aiGetMaterialProperty(this,pKey,type,idx,
(const aiMaterialProperty**)&prop);
if ( AI_SUCCESS == ret ) {
if (prop->mDataLength < sizeof(Type)*iNum) {
return AI_FAILURE;
}
if (prop->mType != aiPTI_Buffer) {
return AI_FAILURE;
}
iNum = std::min((size_t)iNum,prop->mDataLength / sizeof(Type));
::memcpy(pOut,prop->mData,iNum * sizeof(Type));
if (pMax) {
*pMax = iNum;
}
}
return ret;
}
// ---------------------------------------------------------------------------
template <typename Type>
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,Type& pOut) const
{
const aiMaterialProperty* prop;
const aiReturn ret = ::aiGetMaterialProperty(this,pKey,type,idx,
(const aiMaterialProperty**)&prop);
if ( AI_SUCCESS == ret ) {
if (prop->mDataLength < sizeof(Type)) {
return AI_FAILURE;
}
if (prop->mType != aiPTI_Buffer) {
return AI_FAILURE;
}
::memcpy( &pOut, prop->mData, sizeof( Type ) );
}
return ret;
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,ai_real* pOut,
unsigned int* pMax) const
{
return ::aiGetMaterialFloatArray(this,pKey,type,idx,pOut,pMax);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,int* pOut,
unsigned int* pMax) const
{
return ::aiGetMaterialIntegerArray(this,pKey,type,idx,pOut,pMax);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,ai_real& pOut) const
{
return aiGetMaterialFloat(this,pKey,type,idx,&pOut);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,int& pOut) const
{
return aiGetMaterialInteger(this,pKey,type,idx,&pOut);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,aiColor4D& pOut) const
{
return aiGetMaterialColor(this,pKey,type,idx,&pOut);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,aiColor3D& pOut) const
{
aiColor4D c;
const aiReturn ret = aiGetMaterialColor(this,pKey,type,idx,&c);
pOut = aiColor3D(c.r,c.g,c.b);
return ret;
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,aiString& pOut) const
{
return aiGetMaterialString(this,pKey,type,idx,&pOut);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::Get(const char* pKey,unsigned int type,
unsigned int idx,aiUVTransform& pOut) const
{
return aiGetMaterialUVTransform(this,pKey,type,idx,&pOut);
}
// ---------------------------------------------------------------------------
template<class TYPE>
aiReturn aiMaterial::AddProperty (const TYPE* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(TYPE),
pKey,type,index,aiPTI_Buffer);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::AddProperty(const float* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(float),
pKey,type,index,aiPTI_Float);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::AddProperty(const double* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(double),
pKey,type,index,aiPTI_Double);
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::AddProperty(const aiUVTransform* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiUVTransform),
pKey,type,index,ai_real_to_property_type_info(pInput->mRotation));
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::AddProperty(const aiColor4D* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiColor4D),
pKey,type,index,ai_real_to_property_type_info(pInput->a));
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::AddProperty(const aiColor3D* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiColor3D),
pKey,type,index,ai_real_to_property_type_info(pInput->b));
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::AddProperty(const aiVector3D* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiVector3D),
pKey,type,index,ai_real_to_property_type_info(pInput->x));
}
// ---------------------------------------------------------------------------
inline aiReturn aiMaterial::AddProperty(const int* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(int),
pKey,type,index,aiPTI_Integer);
}
// ---------------------------------------------------------------------------
// The template specializations below are for backwards compatibility.
// The recommended way to add material properties is using the non-template
// overloads.
// ---------------------------------------------------------------------------
// ---------------------------------------------------------------------------
template<>
inline aiReturn aiMaterial::AddProperty<float>(const float* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(float),
pKey,type,index,aiPTI_Float);
}
// ---------------------------------------------------------------------------
template<>
inline aiReturn aiMaterial::AddProperty<double>(const double* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(double),
pKey,type,index,aiPTI_Double);
}
// ---------------------------------------------------------------------------
template<>
inline aiReturn aiMaterial::AddProperty<aiUVTransform>(const aiUVTransform* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiUVTransform),
pKey,type,index,aiPTI_Float);
}
// ---------------------------------------------------------------------------
template<>
inline aiReturn aiMaterial::AddProperty<aiColor4D>(const aiColor4D* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiColor4D),
pKey,type,index,aiPTI_Float);
}
// ---------------------------------------------------------------------------
template<>
inline aiReturn aiMaterial::AddProperty<aiColor3D>(const aiColor3D* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiColor3D),
pKey,type,index,aiPTI_Float);
}
// ---------------------------------------------------------------------------
template<>
inline aiReturn aiMaterial::AddProperty<aiVector3D>(const aiVector3D* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(aiVector3D),
pKey,type,index,aiPTI_Float);
}
// ---------------------------------------------------------------------------
template<>
inline aiReturn aiMaterial::AddProperty<int>(const int* pInput,
const unsigned int pNumValues,
const char* pKey,
unsigned int type,
unsigned int index)
{
return AddBinaryProperty((const void*)pInput,
pNumValues * sizeof(int),
pKey,type,index,aiPTI_Integer);
}
//! @endcond
#endif //! AI_MATERIAL_INL_INC

View File

@ -0,0 +1,183 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file matrix3x3.h
* @brief Definition of a 3x3 matrix, including operators when compiling in C++
*/
#pragma once
#ifndef AI_MATRIX3X3_H_INC
#define AI_MATRIX3X3_H_INC
#include "defs.h"
#ifdef __cplusplus
template <typename T> class aiMatrix4x4t;
template <typename T> class aiVector2t;
// ---------------------------------------------------------------------------
/** @brief Represents a row-major 3x3 matrix
*
* There's much confusion about matrix layouts (column vs. row order).
* This is *always* a row-major matrix. Not even with the
* #aiProcess_ConvertToLeftHanded flag, which absolutely does not affect
* matrix order - it just affects the handedness of the coordinate system
* defined thereby.
*/
template <typename TReal>
class aiMatrix3x3t
{
public:
aiMatrix3x3t() AI_NO_EXCEPT :
a1(static_cast<TReal>(1.0f)), a2(), a3(),
b1(), b2(static_cast<TReal>(1.0f)), b3(),
c1(), c2(), c3(static_cast<TReal>(1.0f)) {}
aiMatrix3x3t ( TReal _a1, TReal _a2, TReal _a3,
TReal _b1, TReal _b2, TReal _b3,
TReal _c1, TReal _c2, TReal _c3) :
a1(_a1), a2(_a2), a3(_a3),
b1(_b1), b2(_b2), b3(_b3),
c1(_c1), c2(_c2), c3(_c3)
{}
public:
// matrix multiplication.
aiMatrix3x3t& operator *= (const aiMatrix3x3t& m);
aiMatrix3x3t operator * (const aiMatrix3x3t& m) const;
// array access operators
TReal* operator[] (unsigned int p_iIndex);
const TReal* operator[] (unsigned int p_iIndex) const;
// comparison operators
bool operator== (const aiMatrix4x4t<TReal>& m) const;
bool operator!= (const aiMatrix4x4t<TReal>& m) const;
bool Equal(const aiMatrix4x4t<TReal>& m, TReal epsilon = 1e-6) const;
template <typename TOther>
operator aiMatrix3x3t<TOther> () const;
public:
// -------------------------------------------------------------------
/** @brief Construction from a 4x4 matrix. The remaining parts
* of the matrix are ignored.
*/
explicit aiMatrix3x3t( const aiMatrix4x4t<TReal>& pMatrix);
// -------------------------------------------------------------------
/** @brief Transpose the matrix
*/
aiMatrix3x3t& Transpose();
// -------------------------------------------------------------------
/** @brief Invert the matrix.
* If the matrix is not invertible all elements are set to qnan.
* Beware, use (f != f) to check whether a TReal f is qnan.
*/
aiMatrix3x3t& Inverse();
TReal Determinant() const;
public:
// -------------------------------------------------------------------
/** @brief Returns a rotation matrix for a rotation around z
* @param a Rotation angle, in radians
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix3x3t& RotationZ(TReal a, aiMatrix3x3t& out);
// -------------------------------------------------------------------
/** @brief Returns a rotation matrix for a rotation around
* an arbitrary axis.
*
* @param a Rotation angle, in radians
* @param axis Axis to rotate around
* @param out To be filled
*/
static aiMatrix3x3t& Rotation( TReal a,
const aiVector3t<TReal>& axis, aiMatrix3x3t& out);
// -------------------------------------------------------------------
/** @brief Returns a translation matrix
* @param v Translation vector
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix3x3t& Translation( const aiVector2t<TReal>& v, aiMatrix3x3t& out);
// -------------------------------------------------------------------
/** @brief A function for creating a rotation matrix that rotates a
* vector called "from" into another vector called "to".
* Input : from[3], to[3] which both must be *normalized* non-zero vectors
* Output: mtx[3][3] -- a 3x3 matrix in column-major form
* Authors: Tomas Möller, John Hughes
* "Efficiently Building a Matrix to Rotate One Vector to Another"
* Journal of Graphics Tools, 4(4):1-4, 1999
*/
static aiMatrix3x3t& FromToMatrix(const aiVector3t<TReal>& from,
const aiVector3t<TReal>& to, aiMatrix3x3t& out);
public:
TReal a1, a2, a3;
TReal b1, b2, b3;
TReal c1, c2, c3;
};
typedef aiMatrix3x3t<ai_real> aiMatrix3x3;
#else
struct aiMatrix3x3 {
ai_real a1, a2, a3;
ai_real b1, b2, b3;
ai_real c1, c2, c3;
};
#endif // __cplusplus
#endif // AI_MATRIX3X3_H_INC

View File

@ -0,0 +1,357 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file matrix3x3.inl
* @brief Inline implementation of the 3x3 matrix operators
*/
#pragma once
#ifndef AI_MATRIX3X3_INL_INC
#define AI_MATRIX3X3_INL_INC
#ifdef __cplusplus
#include "matrix3x3.h"
#include "matrix4x4.h"
#include <algorithm>
#include <cmath>
#include <limits>
// ------------------------------------------------------------------------------------------------
// Construction from a 4x4 matrix. The remaining parts of the matrix are ignored.
template <typename TReal>
inline aiMatrix3x3t<TReal>::aiMatrix3x3t( const aiMatrix4x4t<TReal>& pMatrix)
{
a1 = pMatrix.a1; a2 = pMatrix.a2; a3 = pMatrix.a3;
b1 = pMatrix.b1; b2 = pMatrix.b2; b3 = pMatrix.b3;
c1 = pMatrix.c1; c2 = pMatrix.c2; c3 = pMatrix.c3;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix3x3t<TReal>& aiMatrix3x3t<TReal>::operator *= (const aiMatrix3x3t<TReal>& m)
{
*this = aiMatrix3x3t<TReal>(m.a1 * a1 + m.b1 * a2 + m.c1 * a3,
m.a2 * a1 + m.b2 * a2 + m.c2 * a3,
m.a3 * a1 + m.b3 * a2 + m.c3 * a3,
m.a1 * b1 + m.b1 * b2 + m.c1 * b3,
m.a2 * b1 + m.b2 * b2 + m.c2 * b3,
m.a3 * b1 + m.b3 * b2 + m.c3 * b3,
m.a1 * c1 + m.b1 * c2 + m.c1 * c3,
m.a2 * c1 + m.b2 * c2 + m.c2 * c3,
m.a3 * c1 + m.b3 * c2 + m.c3 * c3);
return *this;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
template <typename TOther>
aiMatrix3x3t<TReal>::operator aiMatrix3x3t<TOther> () const
{
return aiMatrix3x3t<TOther>(static_cast<TOther>(a1),static_cast<TOther>(a2),static_cast<TOther>(a3),
static_cast<TOther>(b1),static_cast<TOther>(b2),static_cast<TOther>(b3),
static_cast<TOther>(c1),static_cast<TOther>(c2),static_cast<TOther>(c3));
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix3x3t<TReal> aiMatrix3x3t<TReal>::operator* (const aiMatrix3x3t<TReal>& m) const
{
aiMatrix3x3t<TReal> temp( *this);
temp *= m;
return temp;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline TReal* aiMatrix3x3t<TReal>::operator[] (unsigned int p_iIndex) {
switch ( p_iIndex ) {
case 0:
return &a1;
case 1:
return &b1;
case 2:
return &c1;
default:
break;
}
return &a1;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline const TReal* aiMatrix3x3t<TReal>::operator[] (unsigned int p_iIndex) const {
switch ( p_iIndex ) {
case 0:
return &a1;
case 1:
return &b1;
case 2:
return &c1;
default:
break;
}
return &a1;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline bool aiMatrix3x3t<TReal>::operator== (const aiMatrix4x4t<TReal>& m) const
{
return a1 == m.a1 && a2 == m.a2 && a3 == m.a3 &&
b1 == m.b1 && b2 == m.b2 && b3 == m.b3 &&
c1 == m.c1 && c2 == m.c2 && c3 == m.c3;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline bool aiMatrix3x3t<TReal>::operator!= (const aiMatrix4x4t<TReal>& m) const
{
return !(*this == m);
}
// ---------------------------------------------------------------------------
template<typename TReal>
inline bool aiMatrix3x3t<TReal>::Equal(const aiMatrix4x4t<TReal>& m, TReal epsilon) const {
return
std::abs(a1 - m.a1) <= epsilon &&
std::abs(a2 - m.a2) <= epsilon &&
std::abs(a3 - m.a3) <= epsilon &&
std::abs(b1 - m.b1) <= epsilon &&
std::abs(b2 - m.b2) <= epsilon &&
std::abs(b3 - m.b3) <= epsilon &&
std::abs(c1 - m.c1) <= epsilon &&
std::abs(c2 - m.c2) <= epsilon &&
std::abs(c3 - m.c3) <= epsilon;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix3x3t<TReal>& aiMatrix3x3t<TReal>::Transpose()
{
// (TReal&) don't remove, GCC complains cause of packed fields
std::swap( (TReal&)a2, (TReal&)b1);
std::swap( (TReal&)a3, (TReal&)c1);
std::swap( (TReal&)b3, (TReal&)c2);
return *this;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline TReal aiMatrix3x3t<TReal>::Determinant() const
{
return a1*b2*c3 - a1*b3*c2 + a2*b3*c1 - a2*b1*c3 + a3*b1*c2 - a3*b2*c1;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix3x3t<TReal>& aiMatrix3x3t<TReal>::Inverse()
{
// Compute the reciprocal determinant
TReal det = Determinant();
if(det == static_cast<TReal>(0.0))
{
// Matrix not invertible. Setting all elements to nan is not really
// correct in a mathematical sense; but at least qnans are easy to
// spot. XXX we might throw an exception instead, which would
// be even much better to spot :/.
const TReal nan = std::numeric_limits<TReal>::quiet_NaN();
*this = aiMatrix3x3t<TReal>( nan,nan,nan,nan,nan,nan,nan,nan,nan);
return *this;
}
TReal invdet = static_cast<TReal>(1.0) / det;
aiMatrix3x3t<TReal> res;
res.a1 = invdet * (b2 * c3 - b3 * c2);
res.a2 = -invdet * (a2 * c3 - a3 * c2);
res.a3 = invdet * (a2 * b3 - a3 * b2);
res.b1 = -invdet * (b1 * c3 - b3 * c1);
res.b2 = invdet * (a1 * c3 - a3 * c1);
res.b3 = -invdet * (a1 * b3 - a3 * b1);
res.c1 = invdet * (b1 * c2 - b2 * c1);
res.c2 = -invdet * (a1 * c2 - a2 * c1);
res.c3 = invdet * (a1 * b2 - a2 * b1);
*this = res;
return *this;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix3x3t<TReal>& aiMatrix3x3t<TReal>::RotationZ(TReal a, aiMatrix3x3t<TReal>& out)
{
out.a1 = out.b2 = std::cos(a);
out.b1 = std::sin(a);
out.a2 = - out.b1;
out.a3 = out.b3 = out.c1 = out.c2 = 0.f;
out.c3 = 1.f;
return out;
}
// ------------------------------------------------------------------------------------------------
// Returns a rotation matrix for a rotation around an arbitrary axis.
template <typename TReal>
inline aiMatrix3x3t<TReal>& aiMatrix3x3t<TReal>::Rotation( TReal a, const aiVector3t<TReal>& axis, aiMatrix3x3t<TReal>& out)
{
TReal c = std::cos( a), s = std::sin( a), t = 1 - c;
TReal x = axis.x, y = axis.y, z = axis.z;
// Many thanks to MathWorld and Wikipedia
out.a1 = t*x*x + c; out.a2 = t*x*y - s*z; out.a3 = t*x*z + s*y;
out.b1 = t*x*y + s*z; out.b2 = t*y*y + c; out.b3 = t*y*z - s*x;
out.c1 = t*x*z - s*y; out.c2 = t*y*z + s*x; out.c3 = t*z*z + c;
return out;
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix3x3t<TReal>& aiMatrix3x3t<TReal>::Translation( const aiVector2t<TReal>& v, aiMatrix3x3t<TReal>& out)
{
out = aiMatrix3x3t<TReal>();
out.a3 = v.x;
out.b3 = v.y;
return out;
}
// ----------------------------------------------------------------------------------------
/** A function for creating a rotation matrix that rotates a vector called
* "from" into another vector called "to".
* Input : from[3], to[3] which both must be *normalized* non-zero vectors
* Output: mtx[3][3] -- a 3x3 matrix in colum-major form
* Authors: Tomas Möller, John Hughes
* "Efficiently Building a Matrix to Rotate One Vector to Another"
* Journal of Graphics Tools, 4(4):1-4, 1999
*/
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix3x3t<TReal>& aiMatrix3x3t<TReal>::FromToMatrix(const aiVector3t<TReal>& from,
const aiVector3t<TReal>& to, aiMatrix3x3t<TReal>& mtx)
{
const TReal e = from * to;
const TReal f = (e < 0)? -e:e;
if (f > static_cast<TReal>(1.0) - static_cast<TReal>(0.00001)) /* "from" and "to"-vector almost parallel */
{
aiVector3D u,v; /* temporary storage vectors */
aiVector3D x; /* vector most nearly orthogonal to "from" */
x.x = (from.x > 0.0)? from.x : -from.x;
x.y = (from.y > 0.0)? from.y : -from.y;
x.z = (from.z > 0.0)? from.z : -from.z;
if (x.x < x.y)
{
if (x.x < x.z)
{
x.x = static_cast<TReal>(1.0);
x.y = x.z = static_cast<TReal>(0.0);
}
else
{
x.z = static_cast<TReal>(1.0);
x.x = x.y = static_cast<TReal>(0.0);
}
}
else
{
if (x.y < x.z)
{
x.y = static_cast<TReal>(1.0);
x.x = x.z = static_cast<TReal>(0.0);
}
else
{
x.z = static_cast<TReal>(1.0);
x.x = x.y = static_cast<TReal>(0.0);
}
}
u.x = x.x - from.x; u.y = x.y - from.y; u.z = x.z - from.z;
v.x = x.x - to.x; v.y = x.y - to.y; v.z = x.z - to.z;
const TReal c1_ = static_cast<TReal>(2.0) / (u * u);
const TReal c2_ = static_cast<TReal>(2.0) / (v * v);
const TReal c3_ = c1_ * c2_ * (u * v);
for (unsigned int i = 0; i < 3; i++)
{
for (unsigned int j = 0; j < 3; j++)
{
mtx[i][j] = - c1_ * u[i] * u[j] - c2_ * v[i] * v[j]
+ c3_ * v[i] * u[j];
}
mtx[i][i] += static_cast<TReal>(1.0);
}
}
else /* the most common case, unless "from"="to", or "from"=-"to" */
{
const aiVector3D v = from ^ to;
/* ... use this hand optimized version (9 mults less) */
const TReal h = static_cast<TReal>(1.0)/(static_cast<TReal>(1.0) + e); /* optimization by Gottfried Chen */
const TReal hvx = h * v.x;
const TReal hvz = h * v.z;
const TReal hvxy = hvx * v.y;
const TReal hvxz = hvx * v.z;
const TReal hvyz = hvz * v.y;
mtx[0][0] = e + hvx * v.x;
mtx[0][1] = hvxy - v.z;
mtx[0][2] = hvxz + v.y;
mtx[1][0] = hvxy + v.z;
mtx[1][1] = e + h * v.y * v.y;
mtx[1][2] = hvyz - v.x;
mtx[2][0] = hvxz - v.y;
mtx[2][1] = hvyz + v.x;
mtx[2][2] = e + hvz * v.z;
}
return mtx;
}
#endif // __cplusplus
#endif // AI_MATRIX3X3_INL_INC

View File

@ -0,0 +1,280 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file matrix4x4.h
* @brief 4x4 matrix structure, including operators when compiling in C++
*/
#pragma once
#ifndef AI_MATRIX4X4_H_INC
#define AI_MATRIX4X4_H_INC
#include "vector3.h"
#include "defs.h"
#ifdef __cplusplus
template<typename TReal> class aiMatrix3x3t;
template<typename TReal> class aiQuaterniont;
// ---------------------------------------------------------------------------
/** @brief Represents a row-major 4x4 matrix, use this for homogeneous
* coordinates.
*
* There's much confusion about matrix layouts (column vs. row order).
* This is *always* a row-major matrix. Not even with the
* #aiProcess_ConvertToLeftHanded flag, which absolutely does not affect
* matrix order - it just affects the handedness of the coordinate system
* defined thereby.
*/
template<typename TReal>
class aiMatrix4x4t
{
public:
/** set to identity */
aiMatrix4x4t() AI_NO_EXCEPT;
/** construction from single values */
aiMatrix4x4t ( TReal _a1, TReal _a2, TReal _a3, TReal _a4,
TReal _b1, TReal _b2, TReal _b3, TReal _b4,
TReal _c1, TReal _c2, TReal _c3, TReal _c4,
TReal _d1, TReal _d2, TReal _d3, TReal _d4);
/** construction from 3x3 matrix, remaining elements are set to identity */
explicit aiMatrix4x4t( const aiMatrix3x3t<TReal>& m);
/** construction from position, rotation and scaling components
* @param scaling The scaling for the x,y,z axes
* @param rotation The rotation as a hamilton quaternion
* @param position The position for the x,y,z axes
*/
aiMatrix4x4t(const aiVector3t<TReal>& scaling, const aiQuaterniont<TReal>& rotationCamera,
const aiVector3t<TReal>& position);
public:
// array access operators
/** @fn TReal* operator[] (unsigned int p_iIndex)
* @param [in] p_iIndex - index of the row.
* @return pointer to pointed row.
*/
TReal* operator[] (unsigned int p_iIndex);
/** @fn const TReal* operator[] (unsigned int p_iIndex) const
* @overload TReal* operator[] (unsigned int p_iIndex)
*/
const TReal* operator[] (unsigned int p_iIndex) const;
// comparison operators
bool operator== (const aiMatrix4x4t& m) const;
bool operator!= (const aiMatrix4x4t& m) const;
bool Equal(const aiMatrix4x4t& m, TReal epsilon = 1e-6) const;
// matrix multiplication.
aiMatrix4x4t& operator *= (const aiMatrix4x4t& m);
aiMatrix4x4t operator * (const aiMatrix4x4t& m) const;
aiMatrix4x4t operator * (const TReal& aFloat) const;
aiMatrix4x4t operator + (const aiMatrix4x4t& aMatrix) const;
template <typename TOther>
operator aiMatrix4x4t<TOther> () const;
public:
// -------------------------------------------------------------------
/** @brief Transpose the matrix */
aiMatrix4x4t& Transpose();
// -------------------------------------------------------------------
/** @brief Invert the matrix.
* If the matrix is not invertible all elements are set to qnan.
* Beware, use (f != f) to check whether a TReal f is qnan.
*/
aiMatrix4x4t& Inverse();
TReal Determinant() const;
// -------------------------------------------------------------------
/** @brief Returns true of the matrix is the identity matrix.
* The check is performed against a not so small epsilon.
*/
inline bool IsIdentity() const;
// -------------------------------------------------------------------
/** @brief Decompose a trafo matrix into its original components
* @param scaling Receives the output scaling for the x,y,z axes
* @param rotation Receives the output rotation as a hamilton
* quaternion
* @param position Receives the output position for the x,y,z axes
*/
void Decompose (aiVector3t<TReal>& scaling, aiQuaterniont<TReal>& rotationCamera,
aiVector3t<TReal>& position) const;
// -------------------------------------------------------------------
/** @fn void Decompose(aiVector3t<TReal>& pScaling, aiVector3t<TReal>& pRotation, aiVector3t<TReal>& pPosition) const
* @brief Decompose a trafo matrix into its original components.
* Thx to good FAQ at http://www.gamedev.ru/code/articles/faq_matrix_quat
* @param [out] pScaling - Receives the output scaling for the x,y,z axes.
* @param [out] pRotation - Receives the output rotation as a Euler angles.
* @param [out] pPosition - Receives the output position for the x,y,z axes.
*/
void Decompose(aiVector3t<TReal>& pScaling, aiVector3t<TReal>& pRotation, aiVector3t<TReal>& pPosition) const;
// -------------------------------------------------------------------
/** @fn void Decompose(aiVector3t<TReal>& pScaling, aiVector3t<TReal>& pRotationAxis, TReal& pRotationAngle, aiVector3t<TReal>& pPosition) const
* @brief Decompose a trafo matrix into its original components
* Thx to good FAQ at http://www.gamedev.ru/code/articles/faq_matrix_quat
* @param [out] pScaling - Receives the output scaling for the x,y,z axes.
* @param [out] pRotationAxis - Receives the output rotation axis.
* @param [out] pRotationAngle - Receives the output rotation angle for @ref pRotationAxis.
* @param [out] pPosition - Receives the output position for the x,y,z axes.
*/
void Decompose(aiVector3t<TReal>& pScaling, aiVector3t<TReal>& pRotationAxis, TReal& pRotationAngle, aiVector3t<TReal>& pPosition) const;
// -------------------------------------------------------------------
/** @brief Decompose a trafo matrix with no scaling into its
* original components
* @param rotation Receives the output rotation as a hamilton
* quaternion
* @param position Receives the output position for the x,y,z axes
*/
void DecomposeNoScaling (aiQuaterniont<TReal>& rotationCamera,
aiVector3t<TReal>& position) const;
// -------------------------------------------------------------------
/** @brief Creates a trafo matrix from a set of euler angles
* @param x Rotation angle for the x-axis, in radians
* @param y Rotation angle for the y-axis, in radians
* @param z Rotation angle for the z-axis, in radians
*/
aiMatrix4x4t& FromEulerAnglesXYZ(TReal x, TReal y, TReal z);
aiMatrix4x4t& FromEulerAnglesXYZ(const aiVector3t<TReal>& blubb);
public:
// -------------------------------------------------------------------
/** @brief Returns a rotation matrix for a rotation around the x axis
* @param a Rotation angle, in radians
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix4x4t& RotationX(TReal a, aiMatrix4x4t& out);
// -------------------------------------------------------------------
/** @brief Returns a rotation matrix for a rotation around the y axis
* @param a Rotation angle, in radians
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix4x4t& RotationY(TReal a, aiMatrix4x4t& out);
// -------------------------------------------------------------------
/** @brief Returns a rotation matrix for a rotation around the z axis
* @param a Rotation angle, in radians
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix4x4t& RotationZ(TReal a, aiMatrix4x4t& out);
// -------------------------------------------------------------------
/** Returns a rotation matrix for a rotation around an arbitrary axis.
* @param a Rotation angle, in radians
* @param axis Rotation axis, should be a normalized vector.
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix4x4t& Rotation(TReal a, const aiVector3t<TReal>& axis,
aiMatrix4x4t& out);
// -------------------------------------------------------------------
/** @brief Returns a translation matrix
* @param v Translation vector
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix4x4t& Translation( const aiVector3t<TReal>& v,
aiMatrix4x4t& out);
// -------------------------------------------------------------------
/** @brief Returns a scaling matrix
* @param v Scaling vector
* @param out Receives the output matrix
* @return Reference to the output matrix
*/
static aiMatrix4x4t& Scaling( const aiVector3t<TReal>& v, aiMatrix4x4t& out);
// -------------------------------------------------------------------
/** @brief A function for creating a rotation matrix that rotates a
* vector called "from" into another vector called "to".
* Input : from[3], to[3] which both must be *normalized* non-zero vectors
* Output: mtx[3][3] -- a 3x3 matrix in column-major form
* Authors: Tomas Mueller, John Hughes
* "Efficiently Building a Matrix to Rotate One Vector to Another"
* Journal of Graphics Tools, 4(4):1-4, 1999
*/
static aiMatrix4x4t& FromToMatrix(const aiVector3t<TReal>& from,
const aiVector3t<TReal>& to, aiMatrix4x4t& out);
public:
TReal a1, a2, a3, a4;
TReal b1, b2, b3, b4;
TReal c1, c2, c3, c4;
TReal d1, d2, d3, d4;
};
typedef aiMatrix4x4t<ai_real> aiMatrix4x4;
#else
struct aiMatrix4x4 {
ai_real a1, a2, a3, a4;
ai_real b1, b2, b3, b4;
ai_real c1, c2, c3, c4;
ai_real d1, d2, d3, d4;
};
#endif // __cplusplus
#endif // AI_MATRIX4X4_H_INC

View File

@ -0,0 +1,685 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file matrix4x4.inl
* @brief Inline implementation of the 4x4 matrix operators
*/
#pragma once
#ifndef AI_MATRIX4X4_INL_INC
#define AI_MATRIX4X4_INL_INC
#ifdef __cplusplus
#include "matrix4x4.h"
#include "matrix3x3.h"
#include "quaternion.h"
#include "MathFunctions.h"
#include <algorithm>
#include <limits>
#include <cmath>
// ----------------------------------------------------------------------------------------
template <typename TReal>
aiMatrix4x4t<TReal>::aiMatrix4x4t() AI_NO_EXCEPT :
a1(1.0f), a2(), a3(), a4(),
b1(), b2(1.0f), b3(), b4(),
c1(), c2(), c3(1.0f), c4(),
d1(), d2(), d3(), d4(1.0f)
{
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
aiMatrix4x4t<TReal>::aiMatrix4x4t (TReal _a1, TReal _a2, TReal _a3, TReal _a4,
TReal _b1, TReal _b2, TReal _b3, TReal _b4,
TReal _c1, TReal _c2, TReal _c3, TReal _c4,
TReal _d1, TReal _d2, TReal _d3, TReal _d4) :
a1(_a1), a2(_a2), a3(_a3), a4(_a4),
b1(_b1), b2(_b2), b3(_b3), b4(_b4),
c1(_c1), c2(_c2), c3(_c3), c4(_c4),
d1(_d1), d2(_d2), d3(_d3), d4(_d4)
{
}
// ------------------------------------------------------------------------------------------------
template <typename TReal>
template <typename TOther>
aiMatrix4x4t<TReal>::operator aiMatrix4x4t<TOther> () const
{
return aiMatrix4x4t<TOther>(static_cast<TOther>(a1),static_cast<TOther>(a2),static_cast<TOther>(a3),static_cast<TOther>(a4),
static_cast<TOther>(b1),static_cast<TOther>(b2),static_cast<TOther>(b3),static_cast<TOther>(b4),
static_cast<TOther>(c1),static_cast<TOther>(c2),static_cast<TOther>(c3),static_cast<TOther>(c4),
static_cast<TOther>(d1),static_cast<TOther>(d2),static_cast<TOther>(d3),static_cast<TOther>(d4));
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>::aiMatrix4x4t (const aiMatrix3x3t<TReal>& m)
{
a1 = m.a1; a2 = m.a2; a3 = m.a3; a4 = static_cast<TReal>(0.0);
b1 = m.b1; b2 = m.b2; b3 = m.b3; b4 = static_cast<TReal>(0.0);
c1 = m.c1; c2 = m.c2; c3 = m.c3; c4 = static_cast<TReal>(0.0);
d1 = static_cast<TReal>(0.0); d2 = static_cast<TReal>(0.0); d3 = static_cast<TReal>(0.0); d4 = static_cast<TReal>(1.0);
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>::aiMatrix4x4t (const aiVector3t<TReal>& scaling, const aiQuaterniont<TReal>& rotationCamera, const aiVector3t<TReal>& position)
{
// build a 3x3 rotation matrix
aiMatrix3x3t<TReal> m = rotationCamera.GetMatrix();
a1 = m.a1 * scaling.x;
a2 = m.a2 * scaling.x;
a3 = m.a3 * scaling.x;
a4 = position.x;
b1 = m.b1 * scaling.y;
b2 = m.b2 * scaling.y;
b3 = m.b3 * scaling.y;
b4 = position.y;
c1 = m.c1 * scaling.z;
c2 = m.c2 * scaling.z;
c3 = m.c3 * scaling.z;
c4= position.z;
d1 = static_cast<TReal>(0.0);
d2 = static_cast<TReal>(0.0);
d3 = static_cast<TReal>(0.0);
d4 = static_cast<TReal>(1.0);
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::operator *= (const aiMatrix4x4t<TReal>& m)
{
*this = aiMatrix4x4t<TReal>(
m.a1 * a1 + m.b1 * a2 + m.c1 * a3 + m.d1 * a4,
m.a2 * a1 + m.b2 * a2 + m.c2 * a3 + m.d2 * a4,
m.a3 * a1 + m.b3 * a2 + m.c3 * a3 + m.d3 * a4,
m.a4 * a1 + m.b4 * a2 + m.c4 * a3 + m.d4 * a4,
m.a1 * b1 + m.b1 * b2 + m.c1 * b3 + m.d1 * b4,
m.a2 * b1 + m.b2 * b2 + m.c2 * b3 + m.d2 * b4,
m.a3 * b1 + m.b3 * b2 + m.c3 * b3 + m.d3 * b4,
m.a4 * b1 + m.b4 * b2 + m.c4 * b3 + m.d4 * b4,
m.a1 * c1 + m.b1 * c2 + m.c1 * c3 + m.d1 * c4,
m.a2 * c1 + m.b2 * c2 + m.c2 * c3 + m.d2 * c4,
m.a3 * c1 + m.b3 * c2 + m.c3 * c3 + m.d3 * c4,
m.a4 * c1 + m.b4 * c2 + m.c4 * c3 + m.d4 * c4,
m.a1 * d1 + m.b1 * d2 + m.c1 * d3 + m.d1 * d4,
m.a2 * d1 + m.b2 * d2 + m.c2 * d3 + m.d2 * d4,
m.a3 * d1 + m.b3 * d2 + m.c3 * d3 + m.d3 * d4,
m.a4 * d1 + m.b4 * d2 + m.c4 * d3 + m.d4 * d4);
return *this;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal> aiMatrix4x4t<TReal>::operator* (const TReal& aFloat) const
{
aiMatrix4x4t<TReal> temp(
a1 * aFloat,
a2 * aFloat,
a3 * aFloat,
a4 * aFloat,
b1 * aFloat,
b2 * aFloat,
b3 * aFloat,
b4 * aFloat,
c1 * aFloat,
c2 * aFloat,
c3 * aFloat,
c4 * aFloat,
d1 * aFloat,
d2 * aFloat,
d3 * aFloat,
d4 * aFloat);
return temp;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal> aiMatrix4x4t<TReal>::operator+ (const aiMatrix4x4t<TReal>& m) const
{
aiMatrix4x4t<TReal> temp(
m.a1 + a1,
m.a2 + a2,
m.a3 + a3,
m.a4 + a4,
m.b1 + b1,
m.b2 + b2,
m.b3 + b3,
m.b4 + b4,
m.c1 + c1,
m.c2 + c2,
m.c3 + c3,
m.c4 + c4,
m.d1 + d1,
m.d2 + d2,
m.d3 + d3,
m.d4 + d4);
return temp;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal> aiMatrix4x4t<TReal>::operator* (const aiMatrix4x4t<TReal>& m) const
{
aiMatrix4x4t<TReal> temp( *this);
temp *= m;
return temp;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::Transpose()
{
// (TReal&) don't remove, GCC complains cause of packed fields
std::swap( (TReal&)b1, (TReal&)a2);
std::swap( (TReal&)c1, (TReal&)a3);
std::swap( (TReal&)c2, (TReal&)b3);
std::swap( (TReal&)d1, (TReal&)a4);
std::swap( (TReal&)d2, (TReal&)b4);
std::swap( (TReal&)d3, (TReal&)c4);
return *this;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline TReal aiMatrix4x4t<TReal>::Determinant() const
{
return a1*b2*c3*d4 - a1*b2*c4*d3 + a1*b3*c4*d2 - a1*b3*c2*d4
+ a1*b4*c2*d3 - a1*b4*c3*d2 - a2*b3*c4*d1 + a2*b3*c1*d4
- a2*b4*c1*d3 + a2*b4*c3*d1 - a2*b1*c3*d4 + a2*b1*c4*d3
+ a3*b4*c1*d2 - a3*b4*c2*d1 + a3*b1*c2*d4 - a3*b1*c4*d2
+ a3*b2*c4*d1 - a3*b2*c1*d4 - a4*b1*c2*d3 + a4*b1*c3*d2
- a4*b2*c3*d1 + a4*b2*c1*d3 - a4*b3*c1*d2 + a4*b3*c2*d1;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::Inverse()
{
// Compute the reciprocal determinant
const TReal det = Determinant();
if(det == static_cast<TReal>(0.0))
{
// Matrix not invertible. Setting all elements to nan is not really
// correct in a mathematical sense but it is easy to debug for the
// programmer.
const TReal nan = std::numeric_limits<TReal>::quiet_NaN();
*this = aiMatrix4x4t<TReal>(
nan,nan,nan,nan,
nan,nan,nan,nan,
nan,nan,nan,nan,
nan,nan,nan,nan);
return *this;
}
const TReal invdet = static_cast<TReal>(1.0) / det;
aiMatrix4x4t<TReal> res;
res.a1 = invdet * (b2 * (c3 * d4 - c4 * d3) + b3 * (c4 * d2 - c2 * d4) + b4 * (c2 * d3 - c3 * d2));
res.a2 = -invdet * (a2 * (c3 * d4 - c4 * d3) + a3 * (c4 * d2 - c2 * d4) + a4 * (c2 * d3 - c3 * d2));
res.a3 = invdet * (a2 * (b3 * d4 - b4 * d3) + a3 * (b4 * d2 - b2 * d4) + a4 * (b2 * d3 - b3 * d2));
res.a4 = -invdet * (a2 * (b3 * c4 - b4 * c3) + a3 * (b4 * c2 - b2 * c4) + a4 * (b2 * c3 - b3 * c2));
res.b1 = -invdet * (b1 * (c3 * d4 - c4 * d3) + b3 * (c4 * d1 - c1 * d4) + b4 * (c1 * d3 - c3 * d1));
res.b2 = invdet * (a1 * (c3 * d4 - c4 * d3) + a3 * (c4 * d1 - c1 * d4) + a4 * (c1 * d3 - c3 * d1));
res.b3 = -invdet * (a1 * (b3 * d4 - b4 * d3) + a3 * (b4 * d1 - b1 * d4) + a4 * (b1 * d3 - b3 * d1));
res.b4 = invdet * (a1 * (b3 * c4 - b4 * c3) + a3 * (b4 * c1 - b1 * c4) + a4 * (b1 * c3 - b3 * c1));
res.c1 = invdet * (b1 * (c2 * d4 - c4 * d2) + b2 * (c4 * d1 - c1 * d4) + b4 * (c1 * d2 - c2 * d1));
res.c2 = -invdet * (a1 * (c2 * d4 - c4 * d2) + a2 * (c4 * d1 - c1 * d4) + a4 * (c1 * d2 - c2 * d1));
res.c3 = invdet * (a1 * (b2 * d4 - b4 * d2) + a2 * (b4 * d1 - b1 * d4) + a4 * (b1 * d2 - b2 * d1));
res.c4 = -invdet * (a1 * (b2 * c4 - b4 * c2) + a2 * (b4 * c1 - b1 * c4) + a4 * (b1 * c2 - b2 * c1));
res.d1 = -invdet * (b1 * (c2 * d3 - c3 * d2) + b2 * (c3 * d1 - c1 * d3) + b3 * (c1 * d2 - c2 * d1));
res.d2 = invdet * (a1 * (c2 * d3 - c3 * d2) + a2 * (c3 * d1 - c1 * d3) + a3 * (c1 * d2 - c2 * d1));
res.d3 = -invdet * (a1 * (b2 * d3 - b3 * d2) + a2 * (b3 * d1 - b1 * d3) + a3 * (b1 * d2 - b2 * d1));
res.d4 = invdet * (a1 * (b2 * c3 - b3 * c2) + a2 * (b3 * c1 - b1 * c3) + a3 * (b1 * c2 - b2 * c1));
*this = res;
return *this;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline TReal* aiMatrix4x4t<TReal>::operator[](unsigned int p_iIndex) {
if (p_iIndex > 3) {
return NULL;
}
switch ( p_iIndex ) {
case 0:
return &a1;
case 1:
return &b1;
case 2:
return &c1;
case 3:
return &d1;
default:
break;
}
return &a1;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline const TReal* aiMatrix4x4t<TReal>::operator[](unsigned int p_iIndex) const {
if (p_iIndex > 3) {
return NULL;
}
switch ( p_iIndex ) {
case 0:
return &a1;
case 1:
return &b1;
case 2:
return &c1;
case 3:
return &d1;
default:
break;
}
return &a1;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline bool aiMatrix4x4t<TReal>::operator== (const aiMatrix4x4t<TReal>& m) const
{
return (a1 == m.a1 && a2 == m.a2 && a3 == m.a3 && a4 == m.a4 &&
b1 == m.b1 && b2 == m.b2 && b3 == m.b3 && b4 == m.b4 &&
c1 == m.c1 && c2 == m.c2 && c3 == m.c3 && c4 == m.c4 &&
d1 == m.d1 && d2 == m.d2 && d3 == m.d3 && d4 == m.d4);
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline bool aiMatrix4x4t<TReal>::operator!= (const aiMatrix4x4t<TReal>& m) const
{
return !(*this == m);
}
// ---------------------------------------------------------------------------
template<typename TReal>
inline bool aiMatrix4x4t<TReal>::Equal(const aiMatrix4x4t<TReal>& m, TReal epsilon) const {
return
std::abs(a1 - m.a1) <= epsilon &&
std::abs(a2 - m.a2) <= epsilon &&
std::abs(a3 - m.a3) <= epsilon &&
std::abs(a4 - m.a4) <= epsilon &&
std::abs(b1 - m.b1) <= epsilon &&
std::abs(b2 - m.b2) <= epsilon &&
std::abs(b3 - m.b3) <= epsilon &&
std::abs(b4 - m.b4) <= epsilon &&
std::abs(c1 - m.c1) <= epsilon &&
std::abs(c2 - m.c2) <= epsilon &&
std::abs(c3 - m.c3) <= epsilon &&
std::abs(c4 - m.c4) <= epsilon &&
std::abs(d1 - m.d1) <= epsilon &&
std::abs(d2 - m.d2) <= epsilon &&
std::abs(d3 - m.d3) <= epsilon &&
std::abs(d4 - m.d4) <= epsilon;
}
// ----------------------------------------------------------------------------------------
#define ASSIMP_MATRIX4_4_DECOMPOSE_PART \
const aiMatrix4x4t<TReal>& _this = *this;/* Create alias for conveniance. */ \
\
/* extract translation */ \
pPosition.x = _this[0][3]; \
pPosition.y = _this[1][3]; \
pPosition.z = _this[2][3]; \
\
/* extract the columns of the matrix. */ \
aiVector3t<TReal> vCols[3] = { \
aiVector3t<TReal>(_this[0][0],_this[1][0],_this[2][0]), \
aiVector3t<TReal>(_this[0][1],_this[1][1],_this[2][1]), \
aiVector3t<TReal>(_this[0][2],_this[1][2],_this[2][2]) \
}; \
\
/* extract the scaling factors */ \
pScaling.x = vCols[0].Length(); \
pScaling.y = vCols[1].Length(); \
pScaling.z = vCols[2].Length(); \
\
/* and the sign of the scaling */ \
if (Determinant() < 0) pScaling = -pScaling; \
\
/* and remove all scaling from the matrix */ \
if(pScaling.x) vCols[0] /= pScaling.x; \
if(pScaling.y) vCols[1] /= pScaling.y; \
if(pScaling.z) vCols[2] /= pScaling.z; \
\
do {} while(false)
template <typename TReal>
inline void aiMatrix4x4t<TReal>::Decompose (aiVector3t<TReal>& pScaling, aiQuaterniont<TReal>& pRotation,
aiVector3t<TReal>& pPosition) const
{
ASSIMP_MATRIX4_4_DECOMPOSE_PART;
// build a 3x3 rotation matrix
aiMatrix3x3t<TReal> m(vCols[0].x,vCols[1].x,vCols[2].x,
vCols[0].y,vCols[1].y,vCols[2].y,
vCols[0].z,vCols[1].z,vCols[2].z);
// and generate the rotation quaternion from it
pRotation = aiQuaterniont<TReal>(m);
}
template <typename TReal>
inline
void aiMatrix4x4t<TReal>::Decompose(aiVector3t<TReal>& pScaling, aiVector3t<TReal>& pRotation, aiVector3t<TReal>& pPosition) const {
ASSIMP_MATRIX4_4_DECOMPOSE_PART;
/*
assuming a right-handed coordinate system
and post-multiplication of column vectors,
the rotation matrix for an euler XYZ rotation is M = Rz * Ry * Rx.
combining gives:
| CE BDE-AF ADE+BF 0 |
M = | CF BDF+AE ADF-BE 0 |
| -D CB AC 0 |
| 0 0 0 1 |
where
A = cos(angle_x), B = sin(angle_x);
C = cos(angle_y), D = sin(angle_y);
E = cos(angle_z), F = sin(angle_z);
*/
// Use a small epsilon to solve floating-point inaccuracies
const TReal epsilon = Assimp::Math::getEpsilon<TReal>();
pRotation.y = std::asin(-vCols[0].z);// D. Angle around oY.
TReal C = std::cos(pRotation.y);
if(std::fabs(C) > epsilon)
{
// Finding angle around oX.
TReal tan_x = vCols[2].z / C;// A
TReal tan_y = vCols[1].z / C;// B
pRotation.x = std::atan2(tan_y, tan_x);
// Finding angle around oZ.
tan_x = vCols[0].x / C;// E
tan_y = vCols[0].y / C;// F
pRotation.z = std::atan2(tan_y, tan_x);
}
else
{// oY is fixed.
pRotation.x = 0;// Set angle around oX to 0. => A == 1, B == 0, C == 0, D == 1.
// And finding angle around oZ.
TReal tan_x = vCols[1].y;// BDF+AE => E
TReal tan_y = -vCols[1].x;// BDE-AF => F
pRotation.z = std::atan2(tan_y, tan_x);
}
}
#undef ASSIMP_MATRIX4_4_DECOMPOSE_PART
template <typename TReal>
inline void aiMatrix4x4t<TReal>::Decompose(aiVector3t<TReal>& pScaling, aiVector3t<TReal>& pRotationAxis, TReal& pRotationAngle,
aiVector3t<TReal>& pPosition) const
{
aiQuaterniont<TReal> pRotation;
Decompose(pScaling, pRotation, pPosition);
pRotation.Normalize();
TReal angle_cos = pRotation.w;
TReal angle_sin = std::sqrt(1.0f - angle_cos * angle_cos);
pRotationAngle = std::acos(angle_cos) * 2;
// Use a small epsilon to solve floating-point inaccuracies
const TReal epsilon = 10e-3f;
if(std::fabs(angle_sin) < epsilon) angle_sin = 1;
pRotationAxis.x = pRotation.x / angle_sin;
pRotationAxis.y = pRotation.y / angle_sin;
pRotationAxis.z = pRotation.z / angle_sin;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline void aiMatrix4x4t<TReal>::DecomposeNoScaling (aiQuaterniont<TReal>& rotationCamera,
aiVector3t<TReal>& position) const
{
const aiMatrix4x4t<TReal>& _this = *this;
// extract translation
position.x = _this[0][3];
position.y = _this[1][3];
position.z = _this[2][3];
// extract rotation
rotationCamera = aiQuaterniont<TReal>((aiMatrix3x3t<TReal>)_this);
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::FromEulerAnglesXYZ(const aiVector3t<TReal>& blubb)
{
return FromEulerAnglesXYZ(blubb.x,blubb.y,blubb.z);
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::FromEulerAnglesXYZ(TReal x, TReal y, TReal z)
{
aiMatrix4x4t<TReal>& _this = *this;
TReal cx = std::cos(x);
TReal sx = std::sin(x);
TReal cy = std::cos(y);
TReal sy = std::sin(y);
TReal cz = std::cos(z);
TReal sz = std::sin(z);
// mz*my*mx
_this.a1 = cz * cy;
_this.a2 = cz * sy * sx - sz * cx;
_this.a3 = sz * sx + cz * sy * cx;
_this.b1 = sz * cy;
_this.b2 = cz * cx + sz * sy * sx;
_this.b3 = sz * sy * cx - cz * sx;
_this.c1 = -sy;
_this.c2 = cy * sx;
_this.c3 = cy * cx;
return *this;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline bool aiMatrix4x4t<TReal>::IsIdentity() const
{
// Use a small epsilon to solve floating-point inaccuracies
const static TReal epsilon = 10e-3f;
return (a2 <= epsilon && a2 >= -epsilon &&
a3 <= epsilon && a3 >= -epsilon &&
a4 <= epsilon && a4 >= -epsilon &&
b1 <= epsilon && b1 >= -epsilon &&
b3 <= epsilon && b3 >= -epsilon &&
b4 <= epsilon && b4 >= -epsilon &&
c1 <= epsilon && c1 >= -epsilon &&
c2 <= epsilon && c2 >= -epsilon &&
c4 <= epsilon && c4 >= -epsilon &&
d1 <= epsilon && d1 >= -epsilon &&
d2 <= epsilon && d2 >= -epsilon &&
d3 <= epsilon && d3 >= -epsilon &&
a1 <= 1.f+epsilon && a1 >= 1.f-epsilon &&
b2 <= 1.f+epsilon && b2 >= 1.f-epsilon &&
c3 <= 1.f+epsilon && c3 >= 1.f-epsilon &&
d4 <= 1.f+epsilon && d4 >= 1.f-epsilon);
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::RotationX(TReal a, aiMatrix4x4t<TReal>& out)
{
/*
| 1 0 0 0 |
M = | 0 cos(A) -sin(A) 0 |
| 0 sin(A) cos(A) 0 |
| 0 0 0 1 | */
out = aiMatrix4x4t<TReal>();
out.b2 = out.c3 = std::cos(a);
out.b3 = -(out.c2 = std::sin(a));
return out;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::RotationY(TReal a, aiMatrix4x4t<TReal>& out)
{
/*
| cos(A) 0 sin(A) 0 |
M = | 0 1 0 0 |
| -sin(A) 0 cos(A) 0 |
| 0 0 0 1 |
*/
out = aiMatrix4x4t<TReal>();
out.a1 = out.c3 = std::cos(a);
out.c1 = -(out.a3 = std::sin(a));
return out;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::RotationZ(TReal a, aiMatrix4x4t<TReal>& out)
{
/*
| cos(A) -sin(A) 0 0 |
M = | sin(A) cos(A) 0 0 |
| 0 0 1 0 |
| 0 0 0 1 | */
out = aiMatrix4x4t<TReal>();
out.a1 = out.b2 = std::cos(a);
out.a2 = -(out.b1 = std::sin(a));
return out;
}
// ----------------------------------------------------------------------------------------
// Returns a rotation matrix for a rotation around an arbitrary axis.
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::Rotation( TReal a, const aiVector3t<TReal>& axis, aiMatrix4x4t<TReal>& out)
{
TReal c = std::cos( a), s = std::sin( a), t = 1 - c;
TReal x = axis.x, y = axis.y, z = axis.z;
// Many thanks to MathWorld and Wikipedia
out.a1 = t*x*x + c; out.a2 = t*x*y - s*z; out.a3 = t*x*z + s*y;
out.b1 = t*x*y + s*z; out.b2 = t*y*y + c; out.b3 = t*y*z - s*x;
out.c1 = t*x*z - s*y; out.c2 = t*y*z + s*x; out.c3 = t*z*z + c;
out.a4 = out.b4 = out.c4 = static_cast<TReal>(0.0);
out.d1 = out.d2 = out.d3 = static_cast<TReal>(0.0);
out.d4 = static_cast<TReal>(1.0);
return out;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::Translation( const aiVector3t<TReal>& v, aiMatrix4x4t<TReal>& out)
{
out = aiMatrix4x4t<TReal>();
out.a4 = v.x;
out.b4 = v.y;
out.c4 = v.z;
return out;
}
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::Scaling( const aiVector3t<TReal>& v, aiMatrix4x4t<TReal>& out)
{
out = aiMatrix4x4t<TReal>();
out.a1 = v.x;
out.b2 = v.y;
out.c3 = v.z;
return out;
}
// ----------------------------------------------------------------------------------------
/** A function for creating a rotation matrix that rotates a vector called
* "from" into another vector called "to".
* Input : from[3], to[3] which both must be *normalized* non-zero vectors
* Output: mtx[3][3] -- a 3x3 matrix in colum-major form
* Authors: Tomas Möller, John Hughes
* "Efficiently Building a Matrix to Rotate One Vector to Another"
* Journal of Graphics Tools, 4(4):1-4, 1999
*/
// ----------------------------------------------------------------------------------------
template <typename TReal>
inline aiMatrix4x4t<TReal>& aiMatrix4x4t<TReal>::FromToMatrix(const aiVector3t<TReal>& from,
const aiVector3t<TReal>& to, aiMatrix4x4t<TReal>& mtx)
{
aiMatrix3x3t<TReal> m3;
aiMatrix3x3t<TReal>::FromToMatrix(from,to,m3);
mtx = aiMatrix4x4t<TReal>(m3);
return mtx;
}
#endif // __cplusplus
#endif // AI_MATRIX4X4_INL_INC

View File

@ -0,0 +1,859 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file mesh.h
* @brief Declares the data structures in which the imported geometry is
returned by ASSIMP: aiMesh, aiFace and aiBone data structures.
*/
#pragma once
#ifndef AI_MESH_H_INC
#define AI_MESH_H_INC
#include <assimp/types.h>
#include <assimp/aabb.h>
#ifdef __cplusplus
extern "C" {
#endif
// ---------------------------------------------------------------------------
// Limits. These values are required to match the settings Assimp was
// compiled against. Therefore, do not redefine them unless you build the
// library from source using the same definitions.
// ---------------------------------------------------------------------------
/** @def AI_MAX_FACE_INDICES
* Maximum number of indices per face (polygon). */
#ifndef AI_MAX_FACE_INDICES
# define AI_MAX_FACE_INDICES 0x7fff
#endif
/** @def AI_MAX_BONE_WEIGHTS
* Maximum number of indices per face (polygon). */
#ifndef AI_MAX_BONE_WEIGHTS
# define AI_MAX_BONE_WEIGHTS 0x7fffffff
#endif
/** @def AI_MAX_VERTICES
* Maximum number of vertices per mesh. */
#ifndef AI_MAX_VERTICES
# define AI_MAX_VERTICES 0x7fffffff
#endif
/** @def AI_MAX_FACES
* Maximum number of faces per mesh. */
#ifndef AI_MAX_FACES
# define AI_MAX_FACES 0x7fffffff
#endif
/** @def AI_MAX_NUMBER_OF_COLOR_SETS
* Supported number of vertex color sets per mesh. */
#ifndef AI_MAX_NUMBER_OF_COLOR_SETS
# define AI_MAX_NUMBER_OF_COLOR_SETS 0x8
#endif // !! AI_MAX_NUMBER_OF_COLOR_SETS
/** @def AI_MAX_NUMBER_OF_TEXTURECOORDS
* Supported number of texture coord sets (UV(W) channels) per mesh */
#ifndef AI_MAX_NUMBER_OF_TEXTURECOORDS
# define AI_MAX_NUMBER_OF_TEXTURECOORDS 0x8
#endif // !! AI_MAX_NUMBER_OF_TEXTURECOORDS
// ---------------------------------------------------------------------------
/** @brief A single face in a mesh, referring to multiple vertices.
*
* If mNumIndices is 3, we call the face 'triangle', for mNumIndices > 3
* it's called 'polygon' (hey, that's just a definition!).
* <br>
* aiMesh::mPrimitiveTypes can be queried to quickly examine which types of
* primitive are actually present in a mesh. The #aiProcess_SortByPType flag
* executes a special post-processing algorithm which splits meshes with
* *different* primitive types mixed up (e.g. lines and triangles) in several
* 'clean' submeshes. Furthermore there is a configuration option (
* #AI_CONFIG_PP_SBP_REMOVE) to force #aiProcess_SortByPType to remove
* specific kinds of primitives from the imported scene, completely and forever.
* In many cases you'll probably want to set this setting to
* @code
* aiPrimitiveType_LINE|aiPrimitiveType_POINT
* @endcode
* Together with the #aiProcess_Triangulate flag you can then be sure that
* #aiFace::mNumIndices is always 3.
* @note Take a look at the @link data Data Structures page @endlink for
* more information on the layout and winding order of a face.
*/
struct aiFace
{
//! Number of indices defining this face.
//! The maximum value for this member is #AI_MAX_FACE_INDICES.
unsigned int mNumIndices;
//! Pointer to the indices array. Size of the array is given in numIndices.
unsigned int* mIndices;
#ifdef __cplusplus
//! Default constructor
aiFace() AI_NO_EXCEPT
: mNumIndices( 0 )
, mIndices( nullptr ) {
// empty
}
//! Default destructor. Delete the index array
~aiFace()
{
delete [] mIndices;
}
//! Copy constructor. Copy the index array
aiFace( const aiFace& o)
: mNumIndices(0)
, mIndices( nullptr ) {
*this = o;
}
//! Assignment operator. Copy the index array
aiFace& operator = ( const aiFace& o) {
if (&o == this) {
return *this;
}
delete[] mIndices;
mNumIndices = o.mNumIndices;
if (mNumIndices) {
mIndices = new unsigned int[mNumIndices];
::memcpy( mIndices, o.mIndices, mNumIndices * sizeof( unsigned int));
} else {
mIndices = nullptr;
}
return *this;
}
//! Comparison operator. Checks whether the index array
//! of two faces is identical
bool operator== (const aiFace& o) const {
if (mIndices == o.mIndices) {
return true;
}
if (nullptr != mIndices && mNumIndices != o.mNumIndices) {
return false;
}
if (nullptr == mIndices) {
return false;
}
for (unsigned int i = 0; i < this->mNumIndices; ++i) {
if (mIndices[i] != o.mIndices[i]) {
return false;
}
}
return true;
}
//! Inverse comparison operator. Checks whether the index
//! array of two faces is NOT identical
bool operator != (const aiFace& o) const {
return !(*this == o);
}
#endif // __cplusplus
}; // struct aiFace
// ---------------------------------------------------------------------------
/** @brief A single influence of a bone on a vertex.
*/
struct aiVertexWeight {
//! Index of the vertex which is influenced by the bone.
unsigned int mVertexId;
//! The strength of the influence in the range (0...1).
//! The influence from all bones at one vertex amounts to 1.
float mWeight;
#ifdef __cplusplus
//! Default constructor
aiVertexWeight() AI_NO_EXCEPT
: mVertexId(0)
, mWeight(0.0f) {
// empty
}
//! Initialization from a given index and vertex weight factor
//! \param pID ID
//! \param pWeight Vertex weight factor
aiVertexWeight( unsigned int pID, float pWeight )
: mVertexId( pID )
, mWeight( pWeight ) {
// empty
}
bool operator == ( const aiVertexWeight &rhs ) const {
return ( mVertexId == rhs.mVertexId && mWeight == rhs.mWeight );
}
bool operator != ( const aiVertexWeight &rhs ) const {
return ( *this == rhs );
}
#endif // __cplusplus
};
// ---------------------------------------------------------------------------
/** @brief A single bone of a mesh.
*
* A bone has a name by which it can be found in the frame hierarchy and by
* which it can be addressed by animations. In addition it has a number of
* influences on vertices, and a matrix relating the mesh position to the
* position of the bone at the time of binding.
*/
struct aiBone {
//! The name of the bone.
C_STRUCT aiString mName;
//! The number of vertices affected by this bone.
//! The maximum value for this member is #AI_MAX_BONE_WEIGHTS.
unsigned int mNumWeights;
//! The influence weights of this bone, by vertex index.
C_STRUCT aiVertexWeight* mWeights;
/** Matrix that transforms from bone space to mesh space in bind pose.
*
* This matrix describes the position of the mesh
* in the local space of this bone when the skeleton was bound.
* Thus it can be used directly to determine a desired vertex position,
* given the world-space transform of the bone when animated,
* and the position of the vertex in mesh space.
*
* It is sometimes called an inverse-bind matrix,
* or inverse bind pose matrix.
*/
C_STRUCT aiMatrix4x4 mOffsetMatrix;
#ifdef __cplusplus
//! Default constructor
aiBone() AI_NO_EXCEPT
: mName()
, mNumWeights( 0 )
, mWeights( nullptr )
, mOffsetMatrix() {
// empty
}
//! Copy constructor
aiBone(const aiBone& other)
: mName( other.mName )
, mNumWeights( other.mNumWeights )
, mWeights(nullptr)
, mOffsetMatrix( other.mOffsetMatrix ) {
if (other.mWeights && other.mNumWeights) {
mWeights = new aiVertexWeight[mNumWeights];
::memcpy(mWeights,other.mWeights,mNumWeights * sizeof(aiVertexWeight));
}
}
//! Assignment operator
aiBone &operator=(const aiBone& other) {
if (this == &other) {
return *this;
}
mName = other.mName;
mNumWeights = other.mNumWeights;
mOffsetMatrix = other.mOffsetMatrix;
if (other.mWeights && other.mNumWeights)
{
if (mWeights) {
delete[] mWeights;
}
mWeights = new aiVertexWeight[mNumWeights];
::memcpy(mWeights,other.mWeights,mNumWeights * sizeof(aiVertexWeight));
}
return *this;
}
bool operator == ( const aiBone &rhs ) const {
if ( mName != rhs.mName || mNumWeights != rhs.mNumWeights ) {
return false;
}
for ( size_t i = 0; i < mNumWeights; ++i ) {
if ( mWeights[ i ] != rhs.mWeights[ i ] ) {
return false;
}
}
return true;
}
//! Destructor - deletes the array of vertex weights
~aiBone() {
delete [] mWeights;
}
#endif // __cplusplus
};
// ---------------------------------------------------------------------------
/** @brief Enumerates the types of geometric primitives supported by Assimp.
*
* @see aiFace Face data structure
* @see aiProcess_SortByPType Per-primitive sorting of meshes
* @see aiProcess_Triangulate Automatic triangulation
* @see AI_CONFIG_PP_SBP_REMOVE Removal of specific primitive types.
*/
enum aiPrimitiveType
{
/** A point primitive.
*
* This is just a single vertex in the virtual world,
* #aiFace contains just one index for such a primitive.
*/
aiPrimitiveType_POINT = 0x1,
/** A line primitive.
*
* This is a line defined through a start and an end position.
* #aiFace contains exactly two indices for such a primitive.
*/
aiPrimitiveType_LINE = 0x2,
/** A triangular primitive.
*
* A triangle consists of three indices.
*/
aiPrimitiveType_TRIANGLE = 0x4,
/** A higher-level polygon with more than 3 edges.
*
* A triangle is a polygon, but polygon in this context means
* "all polygons that are not triangles". The "Triangulate"-Step
* is provided for your convenience, it splits all polygons in
* triangles (which are much easier to handle).
*/
aiPrimitiveType_POLYGON = 0x8,
/** This value is not used. It is just here to force the
* compiler to map this enum to a 32 Bit integer.
*/
#ifndef SWIG
_aiPrimitiveType_Force32Bit = INT_MAX
#endif
}; //! enum aiPrimitiveType
// Get the #aiPrimitiveType flag for a specific number of face indices
#define AI_PRIMITIVE_TYPE_FOR_N_INDICES(n) \
((n) > 3 ? aiPrimitiveType_POLYGON : (aiPrimitiveType)(1u << ((n)-1)))
// ---------------------------------------------------------------------------
/** @brief An AnimMesh is an attachment to an #aiMesh stores per-vertex
* animations for a particular frame.
*
* You may think of an #aiAnimMesh as a `patch` for the host mesh, which
* replaces only certain vertex data streams at a particular time.
* Each mesh stores n attached attached meshes (#aiMesh::mAnimMeshes).
* The actual relationship between the time line and anim meshes is
* established by #aiMeshAnim, which references singular mesh attachments
* by their ID and binds them to a time offset.
*/
struct aiAnimMesh
{
/**Anim Mesh name */
C_STRUCT aiString mName;
/** Replacement for aiMesh::mVertices. If this array is non-NULL,
* it *must* contain mNumVertices entries. The corresponding
* array in the host mesh must be non-NULL as well - animation
* meshes may neither add or nor remove vertex components (if
* a replacement array is NULL and the corresponding source
* array is not, the source data is taken instead)*/
C_STRUCT aiVector3D* mVertices;
/** Replacement for aiMesh::mNormals. */
C_STRUCT aiVector3D* mNormals;
/** Replacement for aiMesh::mTangents. */
C_STRUCT aiVector3D* mTangents;
/** Replacement for aiMesh::mBitangents. */
C_STRUCT aiVector3D* mBitangents;
/** Replacement for aiMesh::mColors */
C_STRUCT aiColor4D* mColors[AI_MAX_NUMBER_OF_COLOR_SETS];
/** Replacement for aiMesh::mTextureCoords */
C_STRUCT aiVector3D* mTextureCoords[AI_MAX_NUMBER_OF_TEXTURECOORDS];
/** The number of vertices in the aiAnimMesh, and thus the length of all
* the member arrays.
*
* This has always the same value as the mNumVertices property in the
* corresponding aiMesh. It is duplicated here merely to make the length
* of the member arrays accessible even if the aiMesh is not known, e.g.
* from language bindings.
*/
unsigned int mNumVertices;
/**
* Weight of the AnimMesh.
*/
float mWeight;
#ifdef __cplusplus
aiAnimMesh() AI_NO_EXCEPT
: mVertices( nullptr )
, mNormals(nullptr)
, mTangents(nullptr)
, mBitangents(nullptr)
, mColors()
, mTextureCoords()
, mNumVertices( 0 )
, mWeight( 0.0f )
{
// fixme consider moving this to the ctor initializer list as well
for( unsigned int a = 0; a < AI_MAX_NUMBER_OF_TEXTURECOORDS; a++){
mTextureCoords[a] = nullptr;
}
for( unsigned int a = 0; a < AI_MAX_NUMBER_OF_COLOR_SETS; a++) {
mColors[a] = nullptr;
}
}
~aiAnimMesh()
{
delete [] mVertices;
delete [] mNormals;
delete [] mTangents;
delete [] mBitangents;
for( unsigned int a = 0; a < AI_MAX_NUMBER_OF_TEXTURECOORDS; a++) {
delete [] mTextureCoords[a];
}
for( unsigned int a = 0; a < AI_MAX_NUMBER_OF_COLOR_SETS; a++) {
delete [] mColors[a];
}
}
/** Check whether the anim mesh overrides the vertex positions
* of its host mesh*/
bool HasPositions() const {
return mVertices != nullptr;
}
/** Check whether the anim mesh overrides the vertex normals
* of its host mesh*/
bool HasNormals() const {
return mNormals != nullptr;
}
/** Check whether the anim mesh overrides the vertex tangents
* and bitangents of its host mesh. As for aiMesh,
* tangents and bitangents always go together. */
bool HasTangentsAndBitangents() const {
return mTangents != nullptr;
}
/** Check whether the anim mesh overrides a particular
* set of vertex colors on his host mesh.
* @param pIndex 0<index<AI_MAX_NUMBER_OF_COLOR_SETS */
bool HasVertexColors( unsigned int pIndex) const {
return pIndex >= AI_MAX_NUMBER_OF_COLOR_SETS ? false : mColors[pIndex] != nullptr;
}
/** Check whether the anim mesh overrides a particular
* set of texture coordinates on his host mesh.
* @param pIndex 0<index<AI_MAX_NUMBER_OF_TEXTURECOORDS */
bool HasTextureCoords( unsigned int pIndex) const {
return pIndex >= AI_MAX_NUMBER_OF_TEXTURECOORDS ? false : mTextureCoords[pIndex] != nullptr;
}
#endif
};
// ---------------------------------------------------------------------------
/** @brief Enumerates the methods of mesh morphing supported by Assimp.
*/
enum aiMorphingMethod
{
/** Interpolation between morph targets */
aiMorphingMethod_VERTEX_BLEND = 0x1,
/** Normalized morphing between morph targets */
aiMorphingMethod_MORPH_NORMALIZED = 0x2,
/** Relative morphing between morph targets */
aiMorphingMethod_MORPH_RELATIVE = 0x3,
/** This value is not used. It is just here to force the
* compiler to map this enum to a 32 Bit integer.
*/
#ifndef SWIG
_aiMorphingMethod_Force32Bit = INT_MAX
#endif
}; //! enum aiMorphingMethod
// ---------------------------------------------------------------------------
/** @brief A mesh represents a geometry or model with a single material.
*
* It usually consists of a number of vertices and a series of primitives/faces
* referencing the vertices. In addition there might be a series of bones, each
* of them addressing a number of vertices with a certain weight. Vertex data
* is presented in channels with each channel containing a single per-vertex
* information such as a set of texture coords or a normal vector.
* If a data pointer is non-null, the corresponding data stream is present.
* From C++-programs you can also use the comfort functions Has*() to
* test for the presence of various data streams.
*
* A Mesh uses only a single material which is referenced by a material ID.
* @note The mPositions member is usually not optional. However, vertex positions
* *could* be missing if the #AI_SCENE_FLAGS_INCOMPLETE flag is set in
* @code
* aiScene::mFlags
* @endcode
*/
struct aiMesh
{
/** Bitwise combination of the members of the #aiPrimitiveType enum.
* This specifies which types of primitives are present in the mesh.
* The "SortByPrimitiveType"-Step can be used to make sure the
* output meshes consist of one primitive type each.
*/
unsigned int mPrimitiveTypes;
/** The number of vertices in this mesh.
* This is also the size of all of the per-vertex data arrays.
* The maximum value for this member is #AI_MAX_VERTICES.
*/
unsigned int mNumVertices;
/** The number of primitives (triangles, polygons, lines) in this mesh.
* This is also the size of the mFaces array.
* The maximum value for this member is #AI_MAX_FACES.
*/
unsigned int mNumFaces;
/** Vertex positions.
* This array is always present in a mesh. The array is
* mNumVertices in size.
*/
C_STRUCT aiVector3D* mVertices;
/** Vertex normals.
* The array contains normalized vectors, NULL if not present.
* The array is mNumVertices in size. Normals are undefined for
* point and line primitives. A mesh consisting of points and
* lines only may not have normal vectors. Meshes with mixed
* primitive types (i.e. lines and triangles) may have normals,
* but the normals for vertices that are only referenced by
* point or line primitives are undefined and set to QNaN (WARN:
* qNaN compares to inequal to *everything*, even to qNaN itself.
* Using code like this to check whether a field is qnan is:
* @code
* #define IS_QNAN(f) (f != f)
* @endcode
* still dangerous because even 1.f == 1.f could evaluate to false! (
* remember the subtleties of IEEE754 artithmetics). Use stuff like
* @c fpclassify instead.
* @note Normal vectors computed by Assimp are always unit-length.
* However, this needn't apply for normals that have been taken
* directly from the model file.
*/
C_STRUCT aiVector3D* mNormals;
/** Vertex tangents.
* The tangent of a vertex points in the direction of the positive
* X texture axis. The array contains normalized vectors, NULL if
* not present. The array is mNumVertices in size. A mesh consisting
* of points and lines only may not have normal vectors. Meshes with
* mixed primitive types (i.e. lines and triangles) may have
* normals, but the normals for vertices that are only referenced by
* point or line primitives are undefined and set to qNaN. See
* the #mNormals member for a detailed discussion of qNaNs.
* @note If the mesh contains tangents, it automatically also
* contains bitangents.
*/
C_STRUCT aiVector3D* mTangents;
/** Vertex bitangents.
* The bitangent of a vertex points in the direction of the positive
* Y texture axis. The array contains normalized vectors, NULL if not
* present. The array is mNumVertices in size.
* @note If the mesh contains tangents, it automatically also contains
* bitangents.
*/
C_STRUCT aiVector3D* mBitangents;
/** Vertex color sets.
* A mesh may contain 0 to #AI_MAX_NUMBER_OF_COLOR_SETS vertex
* colors per vertex. NULL if not present. Each array is
* mNumVertices in size if present.
*/
C_STRUCT aiColor4D* mColors[AI_MAX_NUMBER_OF_COLOR_SETS];
/** Vertex texture coords, also known as UV channels.
* A mesh may contain 0 to AI_MAX_NUMBER_OF_TEXTURECOORDS per
* vertex. NULL if not present. The array is mNumVertices in size.
*/
C_STRUCT aiVector3D* mTextureCoords[AI_MAX_NUMBER_OF_TEXTURECOORDS];
/** Specifies the number of components for a given UV channel.
* Up to three channels are supported (UVW, for accessing volume
* or cube maps). If the value is 2 for a given channel n, the
* component p.z of mTextureCoords[n][p] is set to 0.0f.
* If the value is 1 for a given channel, p.y is set to 0.0f, too.
* @note 4D coords are not supported
*/
unsigned int mNumUVComponents[AI_MAX_NUMBER_OF_TEXTURECOORDS];
/** The faces the mesh is constructed from.
* Each face refers to a number of vertices by their indices.
* This array is always present in a mesh, its size is given
* in mNumFaces. If the #AI_SCENE_FLAGS_NON_VERBOSE_FORMAT
* is NOT set each face references an unique set of vertices.
*/
C_STRUCT aiFace* mFaces;
/** The number of bones this mesh contains.
* Can be 0, in which case the mBones array is NULL.
*/
unsigned int mNumBones;
/** The bones of this mesh.
* A bone consists of a name by which it can be found in the
* frame hierarchy and a set of vertex weights.
*/
C_STRUCT aiBone** mBones;
/** The material used by this mesh.
* A mesh uses only a single material. If an imported model uses
* multiple materials, the import splits up the mesh. Use this value
* as index into the scene's material list.
*/
unsigned int mMaterialIndex;
/** Name of the mesh. Meshes can be named, but this is not a
* requirement and leaving this field empty is totally fine.
* There are mainly three uses for mesh names:
* - some formats name nodes and meshes independently.
* - importers tend to split meshes up to meet the
* one-material-per-mesh requirement. Assigning
* the same (dummy) name to each of the result meshes
* aids the caller at recovering the original mesh
* partitioning.
* - Vertex animations refer to meshes by their names.
**/
C_STRUCT aiString mName;
/** The number of attachment meshes. Note! Currently only works with Collada loader. */
unsigned int mNumAnimMeshes;
/** Attachment meshes for this mesh, for vertex-based animation.
* Attachment meshes carry replacement data for some of the
* mesh'es vertex components (usually positions, normals).
* Note! Currently only works with Collada loader.*/
C_STRUCT aiAnimMesh** mAnimMeshes;
/**
* Method of morphing when animeshes are specified.
*/
unsigned int mMethod;
/**
*
*/
C_STRUCT aiAABB mAABB;
#ifdef __cplusplus
//! Default constructor. Initializes all members to 0
aiMesh() AI_NO_EXCEPT
: mPrimitiveTypes( 0 )
, mNumVertices( 0 )
, mNumFaces( 0 )
, mVertices( nullptr )
, mNormals(nullptr)
, mTangents(nullptr)
, mBitangents(nullptr)
, mColors()
, mTextureCoords()
, mNumUVComponents()
, mFaces(nullptr)
, mNumBones( 0 )
, mBones(nullptr)
, mMaterialIndex( 0 )
, mNumAnimMeshes( 0 )
, mAnimMeshes(nullptr)
, mMethod( 0 )
, mAABB() {
for( unsigned int a = 0; a < AI_MAX_NUMBER_OF_TEXTURECOORDS; ++a ) {
mNumUVComponents[a] = 0;
mTextureCoords[a] = nullptr;
}
for (unsigned int a = 0; a < AI_MAX_NUMBER_OF_COLOR_SETS; ++a) {
mColors[a] = nullptr;
}
}
//! Deletes all storage allocated for the mesh
~aiMesh() {
delete [] mVertices;
delete [] mNormals;
delete [] mTangents;
delete [] mBitangents;
for( unsigned int a = 0; a < AI_MAX_NUMBER_OF_TEXTURECOORDS; a++) {
delete [] mTextureCoords[a];
}
for( unsigned int a = 0; a < AI_MAX_NUMBER_OF_COLOR_SETS; a++) {
delete [] mColors[a];
}
// DO NOT REMOVE THIS ADDITIONAL CHECK
if (mNumBones && mBones) {
for( unsigned int a = 0; a < mNumBones; a++) {
delete mBones[a];
}
delete [] mBones;
}
if (mNumAnimMeshes && mAnimMeshes) {
for( unsigned int a = 0; a < mNumAnimMeshes; a++) {
delete mAnimMeshes[a];
}
delete [] mAnimMeshes;
}
delete [] mFaces;
}
//! Check whether the mesh contains positions. Provided no special
//! scene flags are set, this will always be true
bool HasPositions() const
{ return mVertices != nullptr && mNumVertices > 0; }
//! Check whether the mesh contains faces. If no special scene flags
//! are set this should always return true
bool HasFaces() const
{ return mFaces != nullptr && mNumFaces > 0; }
//! Check whether the mesh contains normal vectors
bool HasNormals() const
{ return mNormals != nullptr && mNumVertices > 0; }
//! Check whether the mesh contains tangent and bitangent vectors
//! It is not possible that it contains tangents and no bitangents
//! (or the other way round). The existence of one of them
//! implies that the second is there, too.
bool HasTangentsAndBitangents() const
{ return mTangents != nullptr && mBitangents != nullptr && mNumVertices > 0; }
//! Check whether the mesh contains a vertex color set
//! \param pIndex Index of the vertex color set
bool HasVertexColors( unsigned int pIndex) const {
if (pIndex >= AI_MAX_NUMBER_OF_COLOR_SETS) {
return false;
} else {
return mColors[pIndex] != nullptr && mNumVertices > 0;
}
}
//! Check whether the mesh contains a texture coordinate set
//! \param pIndex Index of the texture coordinates set
bool HasTextureCoords( unsigned int pIndex) const {
if (pIndex >= AI_MAX_NUMBER_OF_TEXTURECOORDS) {
return false;
} else {
return mTextureCoords[pIndex] != nullptr && mNumVertices > 0;
}
}
//! Get the number of UV channels the mesh contains
unsigned int GetNumUVChannels() const {
unsigned int n( 0 );
while (n < AI_MAX_NUMBER_OF_TEXTURECOORDS && mTextureCoords[n]) {
++n;
}
return n;
}
//! Get the number of vertex color channels the mesh contains
unsigned int GetNumColorChannels() const {
unsigned int n(0);
while (n < AI_MAX_NUMBER_OF_COLOR_SETS && mColors[n]) {
++n;
}
return n;
}
//! Check whether the mesh contains bones
bool HasBones() const {
return mBones != nullptr && mNumBones > 0;
}
#endif // __cplusplus
};
#ifdef __cplusplus
}
#endif //! extern "C"
#endif // AI_MESH_H_INC

View File

@ -0,0 +1,380 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file metadata.h
* @brief Defines the data structures for holding node meta information.
*/
#pragma once
#ifndef AI_METADATA_H_INC
#define AI_METADATA_H_INC
#if defined(_MSC_VER) && (_MSC_VER <= 1500)
# include "Compiler/pstdint.h"
#else
# include <stdint.h>
#endif
// -------------------------------------------------------------------------------
/**
* Enum used to distinguish data types
*/
// -------------------------------------------------------------------------------
typedef enum aiMetadataType {
AI_BOOL = 0,
AI_INT32 = 1,
AI_UINT64 = 2,
AI_FLOAT = 3,
AI_DOUBLE = 4,
AI_AISTRING = 5,
AI_AIVECTOR3D = 6,
AI_META_MAX = 7,
#ifndef SWIG
FORCE_32BIT = INT_MAX
#endif
} aiMetadataType;
// -------------------------------------------------------------------------------
/**
* Metadata entry
*
* The type field uniquely identifies the underlying type of the data field
*/
// -------------------------------------------------------------------------------
struct aiMetadataEntry {
aiMetadataType mType;
void* mData;
};
#ifdef __cplusplus
#include <string>
// -------------------------------------------------------------------------------
/**
* Helper functions to get the aiType enum entry for a type
*/
// -------------------------------------------------------------------------------
inline aiMetadataType GetAiType( bool ) { return AI_BOOL; }
inline aiMetadataType GetAiType( int32_t ) { return AI_INT32; }
inline aiMetadataType GetAiType( uint64_t ) { return AI_UINT64; }
inline aiMetadataType GetAiType( float ) { return AI_FLOAT; }
inline aiMetadataType GetAiType( double ) { return AI_DOUBLE; }
inline aiMetadataType GetAiType( const aiString & ) { return AI_AISTRING; }
inline aiMetadataType GetAiType( const aiVector3D & ) { return AI_AIVECTOR3D; }
#endif // __cplusplus
// -------------------------------------------------------------------------------
/**
* Container for holding metadata.
*
* Metadata is a key-value store using string keys and values.
*/
// -------------------------------------------------------------------------------
struct aiMetadata {
/** Length of the mKeys and mValues arrays, respectively */
unsigned int mNumProperties;
/** Arrays of keys, may not be NULL. Entries in this array may not be NULL as well. */
C_STRUCT aiString* mKeys;
/** Arrays of values, may not be NULL. Entries in this array may be NULL if the
* corresponding property key has no assigned value. */
C_STRUCT aiMetadataEntry* mValues;
#ifdef __cplusplus
/**
* @brief The default constructor, set all members to zero by default.
*/
aiMetadata() AI_NO_EXCEPT
: mNumProperties(0)
, mKeys(nullptr)
, mValues(nullptr) {
// empty
}
aiMetadata( const aiMetadata &rhs )
: mNumProperties( rhs.mNumProperties )
, mKeys( nullptr )
, mValues( nullptr ) {
mKeys = new aiString[ mNumProperties ];
for ( size_t i = 0; i < static_cast<size_t>( mNumProperties ); ++i ) {
mKeys[ i ] = rhs.mKeys[ i ];
}
mValues = new aiMetadataEntry[ mNumProperties ];
for ( size_t i = 0; i < static_cast<size_t>(mNumProperties); ++i ) {
mValues[ i ].mType = rhs.mValues[ i ].mType;
switch ( rhs.mValues[ i ].mType ) {
case AI_BOOL:
mValues[ i ].mData = new bool;
::memcpy( mValues[ i ].mData, rhs.mValues[ i ].mData, sizeof(bool) );
break;
case AI_INT32: {
int32_t v;
::memcpy( &v, rhs.mValues[ i ].mData, sizeof( int32_t ) );
mValues[ i ].mData = new int32_t( v );
}
break;
case AI_UINT64: {
uint64_t v;
::memcpy( &v, rhs.mValues[ i ].mData, sizeof( uint64_t ) );
mValues[ i ].mData = new uint64_t( v );
}
break;
case AI_FLOAT: {
float v;
::memcpy( &v, rhs.mValues[ i ].mData, sizeof( float ) );
mValues[ i ].mData = new float( v );
}
break;
case AI_DOUBLE: {
double v;
::memcpy( &v, rhs.mValues[ i ].mData, sizeof( double ) );
mValues[ i ].mData = new double( v );
}
break;
case AI_AISTRING: {
aiString v;
rhs.Get<aiString>( mKeys[ i ], v );
mValues[ i ].mData = new aiString( v );
}
break;
case AI_AIVECTOR3D: {
aiVector3D v;
rhs.Get<aiVector3D>( mKeys[ i ], v );
mValues[ i ].mData = new aiVector3D( v );
}
break;
#ifndef SWIG
case FORCE_32BIT:
#endif
default:
break;
}
}
}
/**
* @brief The destructor.
*/
~aiMetadata() {
delete [] mKeys;
mKeys = nullptr;
if (mValues) {
// Delete each metadata entry
for (unsigned i=0; i<mNumProperties; ++i) {
void* data = mValues[i].mData;
switch (mValues[i].mType) {
case AI_BOOL:
delete static_cast< bool* >( data );
break;
case AI_INT32:
delete static_cast< int32_t* >( data );
break;
case AI_UINT64:
delete static_cast< uint64_t* >( data );
break;
case AI_FLOAT:
delete static_cast< float* >( data );
break;
case AI_DOUBLE:
delete static_cast< double* >( data );
break;
case AI_AISTRING:
delete static_cast< aiString* >( data );
break;
case AI_AIVECTOR3D:
delete static_cast< aiVector3D* >( data );
break;
#ifndef SWIG
case FORCE_32BIT:
#endif
default:
break;
}
}
// Delete the metadata array
delete [] mValues;
mValues = nullptr;
}
}
/**
* @brief Allocates property fields + keys.
* @param numProperties Number of requested properties.
*/
static inline
aiMetadata *Alloc( unsigned int numProperties ) {
if ( 0 == numProperties ) {
return nullptr;
}
aiMetadata *data = new aiMetadata;
data->mNumProperties = numProperties;
data->mKeys = new aiString[ data->mNumProperties ]();
data->mValues = new aiMetadataEntry[ data->mNumProperties ]();
return data;
}
/**
* @brief Deallocates property fields + keys.
*/
static inline
void Dealloc( aiMetadata *metadata ) {
delete metadata;
}
template<typename T>
inline
void Add(const std::string& key, const T& value) {
aiString* new_keys = new aiString[mNumProperties + 1];
aiMetadataEntry* new_values = new aiMetadataEntry[mNumProperties + 1];
for(unsigned int i = 0; i < mNumProperties; ++i)
{
new_keys[i] = mKeys[i];
new_values[i] = mValues[i];
}
delete mKeys;
delete mValues;
mKeys = new_keys;
mValues = new_values;
mNumProperties++;
Set(mNumProperties - 1, key, value);
}
template<typename T>
inline
bool Set( unsigned index, const std::string& key, const T& value ) {
// In range assertion
if ( index >= mNumProperties ) {
return false;
}
// Ensure that we have a valid key.
if ( key.empty() ) {
return false;
}
// Set metadata key
mKeys[index] = key;
// Set metadata type
mValues[index].mType = GetAiType(value);
// Copy the given value to the dynamic storage
mValues[index].mData = new T(value);
return true;
}
template<typename T>
inline
bool Get( unsigned index, T& value ) const {
// In range assertion
if ( index >= mNumProperties ) {
return false;
}
// Return false if the output data type does
// not match the found value's data type
if ( GetAiType( value ) != mValues[ index ].mType ) {
return false;
}
// Otherwise, output the found value and
// return true
value = *static_cast<T*>(mValues[index].mData);
return true;
}
template<typename T>
inline
bool Get( const aiString& key, T& value ) const {
// Search for the given key
for ( unsigned int i = 0; i < mNumProperties; ++i ) {
if ( mKeys[ i ] == key ) {
return Get( i, value );
}
}
return false;
}
template<typename T>
inline
bool Get( const std::string& key, T& value ) const {
return Get(aiString(key), value);
}
/// Return metadata entry for analyzing it by user.
/// \param [in] pIndex - index of the entry.
/// \param [out] pKey - pointer to the key value.
/// \param [out] pEntry - pointer to the entry: type and value.
/// \return false - if pIndex is out of range, else - true.
inline
bool Get(size_t index, const aiString*& key, const aiMetadataEntry*& entry) const {
if ( index >= mNumProperties ) {
return false;
}
key = &mKeys[index];
entry = &mValues[index];
return true;
}
#endif // __cplusplus
};
#endif // AI_METADATA_H_INC

View File

@ -0,0 +1,77 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file pbrmaterial.h
* @brief Defines the material system of the library
*/
#ifndef AI_PBRMATERIAL_H_INC
#define AI_PBRMATERIAL_H_INC
#define AI_MATKEY_GLTF_PBRMETALLICROUGHNESS_BASE_COLOR_FACTOR "$mat.gltf.pbrMetallicRoughness.baseColorFactor", 0, 0
#define AI_MATKEY_GLTF_PBRMETALLICROUGHNESS_METALLIC_FACTOR "$mat.gltf.pbrMetallicRoughness.metallicFactor", 0, 0
#define AI_MATKEY_GLTF_PBRMETALLICROUGHNESS_ROUGHNESS_FACTOR "$mat.gltf.pbrMetallicRoughness.roughnessFactor", 0, 0
#define AI_MATKEY_GLTF_PBRMETALLICROUGHNESS_BASE_COLOR_TEXTURE aiTextureType_DIFFUSE, 1
#define AI_MATKEY_GLTF_PBRMETALLICROUGHNESS_METALLICROUGHNESS_TEXTURE aiTextureType_UNKNOWN, 0
#define AI_MATKEY_GLTF_ALPHAMODE "$mat.gltf.alphaMode", 0, 0
#define AI_MATKEY_GLTF_ALPHACUTOFF "$mat.gltf.alphaCutoff", 0, 0
#define AI_MATKEY_GLTF_PBRSPECULARGLOSSINESS "$mat.gltf.pbrSpecularGlossiness", 0, 0
#define AI_MATKEY_GLTF_PBRSPECULARGLOSSINESS_GLOSSINESS_FACTOR "$mat.gltf.pbrMetallicRoughness.glossinessFactor", 0, 0
#define AI_MATKEY_GLTF_UNLIT "$mat.gltf.unlit", 0, 0
#define _AI_MATKEY_GLTF_TEXTURE_TEXCOORD_BASE "$tex.file.texCoord"
#define _AI_MATKEY_GLTF_MAPPINGNAME_BASE "$tex.mappingname"
#define _AI_MATKEY_GLTF_MAPPINGID_BASE "$tex.mappingid"
#define _AI_MATKEY_GLTF_MAPPINGFILTER_MAG_BASE "$tex.mappingfiltermag"
#define _AI_MATKEY_GLTF_MAPPINGFILTER_MIN_BASE "$tex.mappingfiltermin"
#define _AI_MATKEY_GLTF_SCALE_BASE "$tex.scale"
#define _AI_MATKEY_GLTF_STRENGTH_BASE "$tex.strength"
#define AI_MATKEY_GLTF_TEXTURE_TEXCOORD(type, N) _AI_MATKEY_GLTF_TEXTURE_TEXCOORD_BASE, type, N
#define AI_MATKEY_GLTF_MAPPINGNAME(type, N) _AI_MATKEY_GLTF_MAPPINGNAME_BASE, type, N
#define AI_MATKEY_GLTF_MAPPINGID(type, N) _AI_MATKEY_GLTF_MAPPINGID_BASE, type, N
#define AI_MATKEY_GLTF_MAPPINGFILTER_MAG(type, N) _AI_MATKEY_GLTF_MAPPINGFILTER_MAG_BASE, type, N
#define AI_MATKEY_GLTF_MAPPINGFILTER_MIN(type, N) _AI_MATKEY_GLTF_MAPPINGFILTER_MIN_BASE, type, N
#define AI_MATKEY_GLTF_TEXTURE_SCALE(type, N) _AI_MATKEY_GLTF_SCALE_BASE, type, N
#define AI_MATKEY_GLTF_TEXTURE_STRENGTH(type, N) _AI_MATKEY_GLTF_STRENGTH_BASE, type, N
#endif //!!AI_PBRMATERIAL_H_INC

View File

@ -0,0 +1,92 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2016, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file Android implementation of IOSystem using the standard C file functions.
* Aimed to ease the access to android assets */
#if __ANDROID__ and __ANDROID_API__ > 9 and defined(AI_CONFIG_ANDROID_JNI_ASSIMP_MANAGER_SUPPORT)
#ifndef AI_ANDROIDJNIIOSYSTEM_H_INC
#define AI_ANDROIDJNIIOSYSTEM_H_INC
#include <assimp/DefaultIOSystem.h>
#include <android/asset_manager.h>
#include <android/asset_manager_jni.h>
#include <android/native_activity.h>
namespace Assimp {
// ---------------------------------------------------------------------------
/** Android extension to DefaultIOSystem using the standard C file functions */
class ASSIMP_API AndroidJNIIOSystem : public DefaultIOSystem
{
public:
/** Initialize android activity data */
std::string mApkWorkspacePath;
AAssetManager* mApkAssetManager;
/** Constructor. */
AndroidJNIIOSystem(ANativeActivity* activity);
/** Destructor. */
~AndroidJNIIOSystem();
// -------------------------------------------------------------------
/** Tests for the existence of a file at the given path. */
bool Exists( const char* pFile) const;
// -------------------------------------------------------------------
/** Opens a file at the given path, with given mode */
IOStream* Open( const char* strFile, const char* strMode);
// ------------------------------------------------------------------------------------------------
// Inits Android extractor
void AndroidActivityInit(ANativeActivity* activity);
// ------------------------------------------------------------------------------------------------
// Extracts android asset
bool AndroidExtractAsset(std::string name);
};
} //!ns Assimp
#endif //AI_ANDROIDJNIIOSYSTEM_H_INC
#endif //__ANDROID__ and __ANDROID_API__ > 9 and defined(AI_CONFIG_ANDROID_JNI_ASSIMP_MANAGER_SUPPORT)

View File

@ -0,0 +1,684 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file postprocess.h
* @brief Definitions for import post processing steps
*/
#pragma once
#ifndef AI_POSTPROCESS_H_INC
#define AI_POSTPROCESS_H_INC
#include "types.h"
#ifdef __cplusplus
extern "C" {
#endif
// -----------------------------------------------------------------------------------
/** @enum aiPostProcessSteps
* @brief Defines the flags for all possible post processing steps.
*
* @note Some steps are influenced by properties set on the Assimp::Importer itself
*
* @see Assimp::Importer::ReadFile()
* @see Assimp::Importer::SetPropertyInteger()
* @see aiImportFile
* @see aiImportFileEx
*/
// -----------------------------------------------------------------------------------
enum aiPostProcessSteps
{
// -------------------------------------------------------------------------
/** <hr>Calculates the tangents and bitangents for the imported meshes.
*
* Does nothing if a mesh does not have normals. You might want this post
* processing step to be executed if you plan to use tangent space calculations
* such as normal mapping applied to the meshes. There's an importer property,
* <tt>#AI_CONFIG_PP_CT_MAX_SMOOTHING_ANGLE</tt>, which allows you to specify
* a maximum smoothing angle for the algorithm. However, usually you'll
* want to leave it at the default value.
*/
aiProcess_CalcTangentSpace = 0x1,
// -------------------------------------------------------------------------
/** <hr>Identifies and joins identical vertex data sets within all
* imported meshes.
*
* After this step is run, each mesh contains unique vertices,
* so a vertex may be used by multiple faces. You usually want
* to use this post processing step. If your application deals with
* indexed geometry, this step is compulsory or you'll just waste rendering
* time. <b>If this flag is not specified</b>, no vertices are referenced by
* more than one face and <b>no index buffer is required</b> for rendering.
*/
aiProcess_JoinIdenticalVertices = 0x2,
// -------------------------------------------------------------------------
/** <hr>Converts all the imported data to a left-handed coordinate space.
*
* By default the data is returned in a right-handed coordinate space (which
* OpenGL prefers). In this space, +X points to the right,
* +Z points towards the viewer, and +Y points upwards. In the DirectX
* coordinate space +X points to the right, +Y points upwards, and +Z points
* away from the viewer.
*
* You'll probably want to consider this flag if you use Direct3D for
* rendering. The #aiProcess_ConvertToLeftHanded flag supersedes this
* setting and bundles all conversions typically required for D3D-based
* applications.
*/
aiProcess_MakeLeftHanded = 0x4,
// -------------------------------------------------------------------------
/** <hr>Triangulates all faces of all meshes.
*
* By default the imported mesh data might contain faces with more than 3
* indices. For rendering you'll usually want all faces to be triangles.
* This post processing step splits up faces with more than 3 indices into
* triangles. Line and point primitives are *not* modified! If you want
* 'triangles only' with no other kinds of primitives, try the following
* solution:
* <ul>
* <li>Specify both #aiProcess_Triangulate and #aiProcess_SortByPType </li>
* <li>Ignore all point and line meshes when you process assimp's output</li>
* </ul>
*/
aiProcess_Triangulate = 0x8,
// -------------------------------------------------------------------------
/** <hr>Removes some parts of the data structure (animations, materials,
* light sources, cameras, textures, vertex components).
*
* The components to be removed are specified in a separate
* importer property, <tt>#AI_CONFIG_PP_RVC_FLAGS</tt>. This is quite useful
* if you don't need all parts of the output structure. Vertex colors
* are rarely used today for example... Calling this step to remove unneeded
* data from the pipeline as early as possible results in increased
* performance and a more optimized output data structure.
* This step is also useful if you want to force Assimp to recompute
* normals or tangents. The corresponding steps don't recompute them if
* they're already there (loaded from the source asset). By using this
* step you can make sure they are NOT there.
*
* This flag is a poor one, mainly because its purpose is usually
* misunderstood. Consider the following case: a 3D model has been exported
* from a CAD app, and it has per-face vertex colors. Vertex positions can't be
* shared, thus the #aiProcess_JoinIdenticalVertices step fails to
* optimize the data because of these nasty little vertex colors.
* Most apps don't even process them, so it's all for nothing. By using
* this step, unneeded components are excluded as early as possible
* thus opening more room for internal optimizations.
*/
aiProcess_RemoveComponent = 0x10,
// -------------------------------------------------------------------------
/** <hr>Generates normals for all faces of all meshes.
*
* This is ignored if normals are already there at the time this flag
* is evaluated. Model importers try to load them from the source file, so
* they're usually already there. Face normals are shared between all points
* of a single face, so a single point can have multiple normals, which
* forces the library to duplicate vertices in some cases.
* #aiProcess_JoinIdenticalVertices is *senseless* then.
*
* This flag may not be specified together with #aiProcess_GenSmoothNormals.
*/
aiProcess_GenNormals = 0x20,
// -------------------------------------------------------------------------
/** <hr>Generates smooth normals for all vertices in the mesh.
*
* This is ignored if normals are already there at the time this flag
* is evaluated. Model importers try to load them from the source file, so
* they're usually already there.
*
* This flag may not be specified together with
* #aiProcess_GenNormals. There's a importer property,
* <tt>#AI_CONFIG_PP_GSN_MAX_SMOOTHING_ANGLE</tt> which allows you to specify
* an angle maximum for the normal smoothing algorithm. Normals exceeding
* this limit are not smoothed, resulting in a 'hard' seam between two faces.
* Using a decent angle here (e.g. 80 degrees) results in very good visual
* appearance.
*/
aiProcess_GenSmoothNormals = 0x40,
// -------------------------------------------------------------------------
/** <hr>Splits large meshes into smaller sub-meshes.
*
* This is quite useful for real-time rendering, where the number of triangles
* which can be maximally processed in a single draw-call is limited
* by the video driver/hardware. The maximum vertex buffer is usually limited
* too. Both requirements can be met with this step: you may specify both a
* triangle and vertex limit for a single mesh.
*
* The split limits can (and should!) be set through the
* <tt>#AI_CONFIG_PP_SLM_VERTEX_LIMIT</tt> and <tt>#AI_CONFIG_PP_SLM_TRIANGLE_LIMIT</tt>
* importer properties. The default values are <tt>#AI_SLM_DEFAULT_MAX_VERTICES</tt> and
* <tt>#AI_SLM_DEFAULT_MAX_TRIANGLES</tt>.
*
* Note that splitting is generally a time-consuming task, but only if there's
* something to split. The use of this step is recommended for most users.
*/
aiProcess_SplitLargeMeshes = 0x80,
// -------------------------------------------------------------------------
/** <hr>Removes the node graph and pre-transforms all vertices with
* the local transformation matrices of their nodes.
*
* The output scene still contains nodes, however there is only a
* root node with children, each one referencing only one mesh,
* and each mesh referencing one material. For rendering, you can
* simply render all meshes in order - you don't need to pay
* attention to local transformations and the node hierarchy.
* Animations are removed during this step.
* This step is intended for applications without a scenegraph.
* The step CAN cause some problems: if e.g. a mesh of the asset
* contains normals and another, using the same material index, does not,
* they will be brought together, but the first meshes's part of
* the normal list is zeroed. However, these artifacts are rare.
* @note The <tt>#AI_CONFIG_PP_PTV_NORMALIZE</tt> configuration property
* can be set to normalize the scene's spatial dimension to the -1...1
* range.
*/
aiProcess_PreTransformVertices = 0x100,
// -------------------------------------------------------------------------
/** <hr>Limits the number of bones simultaneously affecting a single vertex
* to a maximum value.
*
* If any vertex is affected by more than the maximum number of bones, the least
* important vertex weights are removed and the remaining vertex weights are
* renormalized so that the weights still sum up to 1.
* The default bone weight limit is 4 (defined as <tt>#AI_LMW_MAX_WEIGHTS</tt> in
* config.h), but you can use the <tt>#AI_CONFIG_PP_LBW_MAX_WEIGHTS</tt> importer
* property to supply your own limit to the post processing step.
*
* If you intend to perform the skinning in hardware, this post processing
* step might be of interest to you.
*/
aiProcess_LimitBoneWeights = 0x200,
// -------------------------------------------------------------------------
/** <hr>Validates the imported scene data structure.
* This makes sure that all indices are valid, all animations and
* bones are linked correctly, all material references are correct .. etc.
*
* It is recommended that you capture Assimp's log output if you use this flag,
* so you can easily find out what's wrong if a file fails the
* validation. The validator is quite strict and will find *all*
* inconsistencies in the data structure... It is recommended that plugin
* developers use it to debug their loaders. There are two types of
* validation failures:
* <ul>
* <li>Error: There's something wrong with the imported data. Further
* postprocessing is not possible and the data is not usable at all.
* The import fails. #Importer::GetErrorString() or #aiGetErrorString()
* carry the error message around.</li>
* <li>Warning: There are some minor issues (e.g. 1000000 animation
* keyframes with the same time), but further postprocessing and use
* of the data structure is still safe. Warning details are written
* to the log file, <tt>#AI_SCENE_FLAGS_VALIDATION_WARNING</tt> is set
* in #aiScene::mFlags</li>
* </ul>
*
* This post-processing step is not time-consuming. Its use is not
* compulsory, but recommended.
*/
aiProcess_ValidateDataStructure = 0x400,
// -------------------------------------------------------------------------
/** <hr>Reorders triangles for better vertex cache locality.
*
* The step tries to improve the ACMR (average post-transform vertex cache
* miss ratio) for all meshes. The implementation runs in O(n) and is
* roughly based on the 'tipsify' algorithm (see <a href="
* http://www.cs.princeton.edu/gfx/pubs/Sander_2007_%3ETR/tipsy.pdf">this
* paper</a>).
*
* If you intend to render huge models in hardware, this step might
* be of interest to you. The <tt>#AI_CONFIG_PP_ICL_PTCACHE_SIZE</tt>
* importer property can be used to fine-tune the cache optimization.
*/
aiProcess_ImproveCacheLocality = 0x800,
// -------------------------------------------------------------------------
/** <hr>Searches for redundant/unreferenced materials and removes them.
*
* This is especially useful in combination with the
* #aiProcess_PreTransformVertices and #aiProcess_OptimizeMeshes flags.
* Both join small meshes with equal characteristics, but they can't do
* their work if two meshes have different materials. Because several
* material settings are lost during Assimp's import filters,
* (and because many exporters don't check for redundant materials), huge
* models often have materials which are are defined several times with
* exactly the same settings.
*
* Several material settings not contributing to the final appearance of
* a surface are ignored in all comparisons (e.g. the material name).
* So, if you're passing additional information through the
* content pipeline (probably using *magic* material names), don't
* specify this flag. Alternatively take a look at the
* <tt>#AI_CONFIG_PP_RRM_EXCLUDE_LIST</tt> importer property.
*/
aiProcess_RemoveRedundantMaterials = 0x1000,
// -------------------------------------------------------------------------
/** <hr>This step tries to determine which meshes have normal vectors
* that are facing inwards and inverts them.
*
* The algorithm is simple but effective:
* the bounding box of all vertices + their normals is compared against
* the volume of the bounding box of all vertices without their normals.
* This works well for most objects, problems might occur with planar
* surfaces. However, the step tries to filter such cases.
* The step inverts all in-facing normals. Generally it is recommended
* to enable this step, although the result is not always correct.
*/
aiProcess_FixInfacingNormals = 0x2000,
// -------------------------------------------------------------------------
/** <hr>This step splits meshes with more than one primitive type in
* homogeneous sub-meshes.
*
* The step is executed after the triangulation step. After the step
* returns, just one bit is set in aiMesh::mPrimitiveTypes. This is
* especially useful for real-time rendering where point and line
* primitives are often ignored or rendered separately.
* You can use the <tt>#AI_CONFIG_PP_SBP_REMOVE</tt> importer property to
* specify which primitive types you need. This can be used to easily
* exclude lines and points, which are rarely used, from the import.
*/
aiProcess_SortByPType = 0x8000,
// -------------------------------------------------------------------------
/** <hr>This step searches all meshes for degenerate primitives and
* converts them to proper lines or points.
*
* A face is 'degenerate' if one or more of its points are identical.
* To have the degenerate stuff not only detected and collapsed but
* removed, try one of the following procedures:
* <br><b>1.</b> (if you support lines and points for rendering but don't
* want the degenerates)<br>
* <ul>
* <li>Specify the #aiProcess_FindDegenerates flag.
* </li>
* <li>Set the <tt>#AI_CONFIG_PP_FD_REMOVE</tt> importer property to
* 1. This will cause the step to remove degenerate triangles from the
* import as soon as they're detected. They won't pass any further
* pipeline steps.
* </li>
* </ul>
* <br><b>2.</b>(if you don't support lines and points at all)<br>
* <ul>
* <li>Specify the #aiProcess_FindDegenerates flag.
* </li>
* <li>Specify the #aiProcess_SortByPType flag. This moves line and
* point primitives to separate meshes.
* </li>
* <li>Set the <tt>#AI_CONFIG_PP_SBP_REMOVE</tt> importer property to
* @code aiPrimitiveType_POINTS | aiPrimitiveType_LINES
* @endcode to cause SortByPType to reject point
* and line meshes from the scene.
* </li>
* </ul>
*
* This step also removes very small triangles with a surface area smaller
* than 10^-6. If you rely on having these small triangles, or notice holes
* in your model, set the property <tt>#AI_CONFIG_PP_FD_CHECKAREA</tt> to
* false.
* @note Degenerate polygons are not necessarily evil and that's why
* they're not removed by default. There are several file formats which
* don't support lines or points, and some exporters bypass the
* format specification and write them as degenerate triangles instead.
*/
aiProcess_FindDegenerates = 0x10000,
// -------------------------------------------------------------------------
/** <hr>This step searches all meshes for invalid data, such as zeroed
* normal vectors or invalid UV coords and removes/fixes them. This is
* intended to get rid of some common exporter errors.
*
* This is especially useful for normals. If they are invalid, and
* the step recognizes this, they will be removed and can later
* be recomputed, i.e. by the #aiProcess_GenSmoothNormals flag.<br>
* The step will also remove meshes that are infinitely small and reduce
* animation tracks consisting of hundreds if redundant keys to a single
* key. The <tt>AI_CONFIG_PP_FID_ANIM_ACCURACY</tt> config property decides
* the accuracy of the check for duplicate animation tracks.
*/
aiProcess_FindInvalidData = 0x20000,
// -------------------------------------------------------------------------
/** <hr>This step converts non-UV mappings (such as spherical or
* cylindrical mapping) to proper texture coordinate channels.
*
* Most applications will support UV mapping only, so you will
* probably want to specify this step in every case. Note that Assimp is not
* always able to match the original mapping implementation of the
* 3D app which produced a model perfectly. It's always better to let the
* modelling app compute the UV channels - 3ds max, Maya, Blender,
* LightWave, and Modo do this for example.
*
* @note If this step is not requested, you'll need to process the
* <tt>#AI_MATKEY_MAPPING</tt> material property in order to display all assets
* properly.
*/
aiProcess_GenUVCoords = 0x40000,
// -------------------------------------------------------------------------
/** <hr>This step applies per-texture UV transformations and bakes
* them into stand-alone vtexture coordinate channels.
*
* UV transformations are specified per-texture - see the
* <tt>#AI_MATKEY_UVTRANSFORM</tt> material key for more information.
* This step processes all textures with
* transformed input UV coordinates and generates a new (pre-transformed) UV channel
* which replaces the old channel. Most applications won't support UV
* transformations, so you will probably want to specify this step.
*
* @note UV transformations are usually implemented in real-time apps by
* transforming texture coordinates at vertex shader stage with a 3x3
* (homogenous) transformation matrix.
*/
aiProcess_TransformUVCoords = 0x80000,
// -------------------------------------------------------------------------
/** <hr>This step searches for duplicate meshes and replaces them
* with references to the first mesh.
*
* This step takes a while, so don't use it if speed is a concern.
* Its main purpose is to workaround the fact that many export
* file formats don't support instanced meshes, so exporters need to
* duplicate meshes. This step removes the duplicates again. Please
* note that Assimp does not currently support per-node material
* assignment to meshes, which means that identical meshes with
* different materials are currently *not* joined, although this is
* planned for future versions.
*/
aiProcess_FindInstances = 0x100000,
// -------------------------------------------------------------------------
/** <hr>A post-processing step to reduce the number of meshes.
*
* This will, in fact, reduce the number of draw calls.
*
* This is a very effective optimization and is recommended to be used
* together with #aiProcess_OptimizeGraph, if possible. The flag is fully
* compatible with both #aiProcess_SplitLargeMeshes and #aiProcess_SortByPType.
*/
aiProcess_OptimizeMeshes = 0x200000,
// -------------------------------------------------------------------------
/** <hr>A post-processing step to optimize the scene hierarchy.
*
* Nodes without animations, bones, lights or cameras assigned are
* collapsed and joined.
*
* Node names can be lost during this step. If you use special 'tag nodes'
* to pass additional information through your content pipeline, use the
* <tt>#AI_CONFIG_PP_OG_EXCLUDE_LIST</tt> importer property to specify a
* list of node names you want to be kept. Nodes matching one of the names
* in this list won't be touched or modified.
*
* Use this flag with caution. Most simple files will be collapsed to a
* single node, so complex hierarchies are usually completely lost. This is not
* useful for editor environments, but probably a very effective
* optimization if you just want to get the model data, convert it to your
* own format, and render it as fast as possible.
*
* This flag is designed to be used with #aiProcess_OptimizeMeshes for best
* results.
*
* @note 'Crappy' scenes with thousands of extremely small meshes packed
* in deeply nested nodes exist for almost all file formats.
* #aiProcess_OptimizeMeshes in combination with #aiProcess_OptimizeGraph
* usually fixes them all and makes them renderable.
*/
aiProcess_OptimizeGraph = 0x400000,
// -------------------------------------------------------------------------
/** <hr>This step flips all UV coordinates along the y-axis and adjusts
* material settings and bitangents accordingly.
*
* <b>Output UV coordinate system:</b>
* @code
* 0y|0y ---------- 1x|0y
* | |
* | |
* | |
* 0x|1y ---------- 1x|1y
* @endcode
*
* You'll probably want to consider this flag if you use Direct3D for
* rendering. The #aiProcess_ConvertToLeftHanded flag supersedes this
* setting and bundles all conversions typically required for D3D-based
* applications.
*/
aiProcess_FlipUVs = 0x800000,
// -------------------------------------------------------------------------
/** <hr>This step adjusts the output face winding order to be CW.
*
* The default face winding order is counter clockwise (CCW).
*
* <b>Output face order:</b>
* @code
* x2
*
* x0
* x1
* @endcode
*/
aiProcess_FlipWindingOrder = 0x1000000,
// -------------------------------------------------------------------------
/** <hr>This step splits meshes with many bones into sub-meshes so that each
* sub-mesh has fewer or as many bones as a given limit.
*/
aiProcess_SplitByBoneCount = 0x2000000,
// -------------------------------------------------------------------------
/** <hr>This step removes bones losslessly or according to some threshold.
*
* In some cases (i.e. formats that require it) exporters are forced to
* assign dummy bone weights to otherwise static meshes assigned to
* animated meshes. Full, weight-based skinning is expensive while
* animating nodes is extremely cheap, so this step is offered to clean up
* the data in that regard.
*
* Use <tt>#AI_CONFIG_PP_DB_THRESHOLD</tt> to control this.
* Use <tt>#AI_CONFIG_PP_DB_ALL_OR_NONE</tt> if you want bones removed if and
* only if all bones within the scene qualify for removal.
*/
aiProcess_Debone = 0x4000000,
// -------------------------------------------------------------------------
/** <hr>This step will perform a global scale of the model.
*
* Some importers are providing a mechanism to define a scaling unit for the
* model. This post processing step can be used to do so. You need to get the
* global scaling from your importer settings like in FBX. Use the flag
* AI_CONFIG_GLOBAL_SCALE_FACTOR_KEY from the global property table to configure this.
*
* Use <tt>#AI_CONFIG_GLOBAL_SCALE_FACTOR_KEY</tt> to setup the global scaling factor.
*/
aiProcess_GlobalScale = 0x8000000,
// -------------------------------------------------------------------------
/** <hr>A postprocessing step to embed of textures.
*
* This will remove external data dependencies for textures.
* If a texture's file does not exist at the specified path
* (due, for instance, to an absolute path generated on another system),
* it will check if a file with the same name exists at the root folder
* of the imported model. And if so, it uses that.
*/
aiProcess_EmbedTextures = 0x10000000,
// aiProcess_GenEntityMeshes = 0x100000,
// aiProcess_OptimizeAnimations = 0x200000
// aiProcess_FixTexturePaths = 0x200000
aiProcess_ForceGenNormals = 0x20000000,
// -------------------------------------------------------------------------
/** <hr>Drops normals for all faces of all meshes.
*
* This is ignored if no normals are present.
* Face normals are shared between all points of a single face,
* so a single point can have multiple normals, which
* forces the library to duplicate vertices in some cases.
* #aiProcess_JoinIdenticalVertices is *senseless* then.
* This process gives sense back to aiProcess_JoinIdenticalVertices
*/
aiProcess_DropNormals = 0x40000000,
// -------------------------------------------------------------------------
/**
*/
aiProcess_GenBoundingBoxes = 0x80000000
};
// ---------------------------------------------------------------------------------------
/** @def aiProcess_ConvertToLeftHanded
* @brief Shortcut flag for Direct3D-based applications.
*
* Supersedes the #aiProcess_MakeLeftHanded and #aiProcess_FlipUVs and
* #aiProcess_FlipWindingOrder flags.
* The output data matches Direct3D's conventions: left-handed geometry, upper-left
* origin for UV coordinates and finally clockwise face order, suitable for CCW culling.
*
* @deprecated
*/
#define aiProcess_ConvertToLeftHanded ( \
aiProcess_MakeLeftHanded | \
aiProcess_FlipUVs | \
aiProcess_FlipWindingOrder | \
0 )
// ---------------------------------------------------------------------------------------
/** @def aiProcessPreset_TargetRealtime_Fast
* @brief Default postprocess configuration optimizing the data for real-time rendering.
*
* Applications would want to use this preset to load models on end-user PCs,
* maybe for direct use in game.
*
* If you're using DirectX, don't forget to combine this value with
* the #aiProcess_ConvertToLeftHanded step. If you don't support UV transformations
* in your application apply the #aiProcess_TransformUVCoords step, too.
* @note Please take the time to read the docs for the steps enabled by this preset.
* Some of them offer further configurable properties, while some of them might not be of
* use for you so it might be better to not specify them.
*/
#define aiProcessPreset_TargetRealtime_Fast ( \
aiProcess_CalcTangentSpace | \
aiProcess_GenNormals | \
aiProcess_JoinIdenticalVertices | \
aiProcess_Triangulate | \
aiProcess_GenUVCoords | \
aiProcess_SortByPType | \
0 )
// ---------------------------------------------------------------------------------------
/** @def aiProcessPreset_TargetRealtime_Quality
* @brief Default postprocess configuration optimizing the data for real-time rendering.
*
* Unlike #aiProcessPreset_TargetRealtime_Fast, this configuration
* performs some extra optimizations to improve rendering speed and
* to minimize memory usage. It could be a good choice for a level editor
* environment where import speed is not so important.
*
* If you're using DirectX, don't forget to combine this value with
* the #aiProcess_ConvertToLeftHanded step. If you don't support UV transformations
* in your application apply the #aiProcess_TransformUVCoords step, too.
* @note Please take the time to read the docs for the steps enabled by this preset.
* Some of them offer further configurable properties, while some of them might not be
* of use for you so it might be better to not specify them.
*/
#define aiProcessPreset_TargetRealtime_Quality ( \
aiProcess_CalcTangentSpace | \
aiProcess_GenSmoothNormals | \
aiProcess_JoinIdenticalVertices | \
aiProcess_ImproveCacheLocality | \
aiProcess_LimitBoneWeights | \
aiProcess_RemoveRedundantMaterials | \
aiProcess_SplitLargeMeshes | \
aiProcess_Triangulate | \
aiProcess_GenUVCoords | \
aiProcess_SortByPType | \
aiProcess_FindDegenerates | \
aiProcess_FindInvalidData | \
0 )
// ---------------------------------------------------------------------------------------
/** @def aiProcessPreset_TargetRealtime_MaxQuality
* @brief Default postprocess configuration optimizing the data for real-time rendering.
*
* This preset enables almost every optimization step to achieve perfectly
* optimized data. It's your choice for level editor environments where import speed
* is not important.
*
* If you're using DirectX, don't forget to combine this value with
* the #aiProcess_ConvertToLeftHanded step. If you don't support UV transformations
* in your application, apply the #aiProcess_TransformUVCoords step, too.
* @note Please take the time to read the docs for the steps enabled by this preset.
* Some of them offer further configurable properties, while some of them might not be
* of use for you so it might be better to not specify them.
*/
#define aiProcessPreset_TargetRealtime_MaxQuality ( \
aiProcessPreset_TargetRealtime_Quality | \
aiProcess_FindInstances | \
aiProcess_ValidateDataStructure | \
aiProcess_OptimizeMeshes | \
0 )
#ifdef __cplusplus
} // end of extern "C"
#endif
#endif // AI_POSTPROCESS_H_INC

View File

@ -0,0 +1,165 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file qnan.h
* @brief Some utilities for our dealings with qnans.
*
* @note Some loaders use qnans to mark invalid values tempoarily, also
* Assimp explicitly enforces undefined normals to be set to qnan.
* qnan utilities are available in standard libraries (C99 for example)
* but last time I checked compiler coverage was so bad that I decided
* to reinvent the wheel.
*/
#ifndef AI_QNAN_H_INCLUDED
#define AI_QNAN_H_INCLUDED
#include <assimp/defs.h>
#include <limits>
#include <stdint.h>
// ---------------------------------------------------------------------------
/** Data structure to represent the bit pattern of a 32 Bit
* IEEE 754 floating-point number. */
union _IEEESingle
{
float Float;
struct
{
uint32_t Frac : 23;
uint32_t Exp : 8;
uint32_t Sign : 1;
} IEEE;
};
// ---------------------------------------------------------------------------
/** Data structure to represent the bit pattern of a 64 Bit
* IEEE 754 floating-point number. */
union _IEEEDouble
{
double Double;
struct
{
uint64_t Frac : 52;
uint64_t Exp : 11;
uint64_t Sign : 1;
} IEEE;
};
// ---------------------------------------------------------------------------
/** Check whether a given float is qNaN.
* @param in Input value */
AI_FORCE_INLINE bool is_qnan(float in)
{
// the straightforward solution does not work:
// return (in != in);
// compiler generates code like this
// load <in> to <register-with-different-width>
// compare <register-with-different-width> against <in>
// FIXME: Use <float> stuff instead? I think fpclassify needs C99
_IEEESingle temp;
memcpy(&temp, &in, sizeof(float));
return (temp.IEEE.Exp == (1u << 8)-1 &&
temp.IEEE.Frac);
}
// ---------------------------------------------------------------------------
/** Check whether a given double is qNaN.
* @param in Input value */
AI_FORCE_INLINE bool is_qnan(double in)
{
// the straightforward solution does not work:
// return (in != in);
// compiler generates code like this
// load <in> to <register-with-different-width>
// compare <register-with-different-width> against <in>
// FIXME: Use <float> stuff instead? I think fpclassify needs C99
_IEEEDouble temp;
memcpy(&temp, &in, sizeof(in));
return (temp.IEEE.Exp == (1u << 11)-1 &&
temp.IEEE.Frac);
}
// ---------------------------------------------------------------------------
/** @brief check whether a float is either NaN or (+/-) INF.
*
* Denorms return false, they're treated like normal values.
* @param in Input value */
AI_FORCE_INLINE bool is_special_float(float in)
{
_IEEESingle temp;
memcpy(&temp, &in, sizeof(float));
return (temp.IEEE.Exp == (1u << 8)-1);
}
// ---------------------------------------------------------------------------
/** @brief check whether a double is either NaN or (+/-) INF.
*
* Denorms return false, they're treated like normal values.
* @param in Input value */
AI_FORCE_INLINE bool is_special_float(double in)
{
_IEEESingle temp;
memcpy(&temp, &in, sizeof(float));
return (temp.IEEE.Exp == (1u << 11)-1);
}
// ---------------------------------------------------------------------------
/** Check whether a float is NOT qNaN.
* @param in Input value */
template<class TReal>
AI_FORCE_INLINE bool is_not_qnan(TReal in)
{
return !is_qnan(in);
}
// ---------------------------------------------------------------------------
/** @brief Get a fresh qnan. */
AI_FORCE_INLINE ai_real get_qnan()
{
return std::numeric_limits<ai_real>::quiet_NaN();
}
#endif // !! AI_QNAN_H_INCLUDED

View File

@ -0,0 +1,130 @@
/*
Open Asset Import Library (assimp)
----------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the
following conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
----------------------------------------------------------------------
*/
/** @file quaternion.h
* @brief Quaternion structure, including operators when compiling in C++
*/
#pragma once
#ifndef AI_QUATERNION_H_INC
#define AI_QUATERNION_H_INC
#ifdef __cplusplus
#include "defs.h"
template <typename TReal> class aiVector3t;
template <typename TReal> class aiMatrix3x3t;
// ---------------------------------------------------------------------------
/** Represents a quaternion in a 4D vector. */
template <typename TReal>
class aiQuaterniont
{
public:
aiQuaterniont() AI_NO_EXCEPT : w(1.0), x(), y(), z() {}
aiQuaterniont(TReal pw, TReal px, TReal py, TReal pz)
: w(pw), x(px), y(py), z(pz) {}
/** Construct from rotation matrix. Result is undefined if the matrix is not orthonormal. */
explicit aiQuaterniont( const aiMatrix3x3t<TReal>& pRotMatrix);
/** Construct from euler angles */
aiQuaterniont( TReal rotx, TReal roty, TReal rotz);
/** Construct from an axis-angle pair */
aiQuaterniont( aiVector3t<TReal> axis, TReal angle);
/** Construct from a normalized quaternion stored in a vec3 */
explicit aiQuaterniont( aiVector3t<TReal> normalized);
/** Returns a matrix representation of the quaternion */
aiMatrix3x3t<TReal> GetMatrix() const;
public:
bool operator== (const aiQuaterniont& o) const;
bool operator!= (const aiQuaterniont& o) const;
bool Equal(const aiQuaterniont& o, TReal epsilon = 1e-6) const;
public:
/** Normalize the quaternion */
aiQuaterniont& Normalize();
/** Compute quaternion conjugate */
aiQuaterniont& Conjugate ();
/** Rotate a point by this quaternion */
aiVector3t<TReal> Rotate (const aiVector3t<TReal>& in);
/** Multiply two quaternions */
aiQuaterniont operator* (const aiQuaterniont& two) const;
public:
/** Performs a spherical interpolation between two quaternions and writes the result into the third.
* @param pOut Target object to received the interpolated rotation.
* @param pStart Start rotation of the interpolation at factor == 0.
* @param pEnd End rotation, factor == 1.
* @param pFactor Interpolation factor between 0 and 1. Values outside of this range yield undefined results.
*/
static void Interpolate( aiQuaterniont& pOut, const aiQuaterniont& pStart,
const aiQuaterniont& pEnd, TReal pFactor);
public:
//! w,x,y,z components of the quaternion
TReal w, x, y, z;
} ;
typedef aiQuaterniont<ai_real> aiQuaternion;
#else
struct aiQuaternion {
ai_real w, x, y, z;
};
#endif
#endif // AI_QUATERNION_H_INC

View File

@ -0,0 +1,286 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file quaternion.inl
* @brief Inline implementation of aiQuaterniont<TReal> operators
*/
#pragma once
#ifndef AI_QUATERNION_INL_INC
#define AI_QUATERNION_INL_INC
#ifdef __cplusplus
#include "quaternion.h"
#include <cmath>
// ---------------------------------------------------------------------------
template<typename TReal>
bool aiQuaterniont<TReal>::operator== (const aiQuaterniont& o) const
{
return x == o.x && y == o.y && z == o.z && w == o.w;
}
// ---------------------------------------------------------------------------
template<typename TReal>
bool aiQuaterniont<TReal>::operator!= (const aiQuaterniont& o) const
{
return !(*this == o);
}
// ---------------------------------------------------------------------------
template<typename TReal>
inline bool aiQuaterniont<TReal>::Equal(const aiQuaterniont& o, TReal epsilon) const {
return
std::abs(x - o.x) <= epsilon &&
std::abs(y - o.y) <= epsilon &&
std::abs(z - o.z) <= epsilon &&
std::abs(w - o.w) <= epsilon;
}
// ---------------------------------------------------------------------------
// Constructs a quaternion from a rotation matrix
template<typename TReal>
inline aiQuaterniont<TReal>::aiQuaterniont( const aiMatrix3x3t<TReal> &pRotMatrix)
{
TReal t = pRotMatrix.a1 + pRotMatrix.b2 + pRotMatrix.c3;
// large enough
if( t > static_cast<TReal>(0))
{
TReal s = std::sqrt(1 + t) * static_cast<TReal>(2.0);
x = (pRotMatrix.c2 - pRotMatrix.b3) / s;
y = (pRotMatrix.a3 - pRotMatrix.c1) / s;
z = (pRotMatrix.b1 - pRotMatrix.a2) / s;
w = static_cast<TReal>(0.25) * s;
} // else we have to check several cases
else if( pRotMatrix.a1 > pRotMatrix.b2 && pRotMatrix.a1 > pRotMatrix.c3 )
{
// Column 0:
TReal s = std::sqrt( static_cast<TReal>(1.0) + pRotMatrix.a1 - pRotMatrix.b2 - pRotMatrix.c3) * static_cast<TReal>(2.0);
x = static_cast<TReal>(0.25) * s;
y = (pRotMatrix.b1 + pRotMatrix.a2) / s;
z = (pRotMatrix.a3 + pRotMatrix.c1) / s;
w = (pRotMatrix.c2 - pRotMatrix.b3) / s;
}
else if( pRotMatrix.b2 > pRotMatrix.c3)
{
// Column 1:
TReal s = std::sqrt( static_cast<TReal>(1.0) + pRotMatrix.b2 - pRotMatrix.a1 - pRotMatrix.c3) * static_cast<TReal>(2.0);
x = (pRotMatrix.b1 + pRotMatrix.a2) / s;
y = static_cast<TReal>(0.25) * s;
z = (pRotMatrix.c2 + pRotMatrix.b3) / s;
w = (pRotMatrix.a3 - pRotMatrix.c1) / s;
} else
{
// Column 2:
TReal s = std::sqrt( static_cast<TReal>(1.0) + pRotMatrix.c3 - pRotMatrix.a1 - pRotMatrix.b2) * static_cast<TReal>(2.0);
x = (pRotMatrix.a3 + pRotMatrix.c1) / s;
y = (pRotMatrix.c2 + pRotMatrix.b3) / s;
z = static_cast<TReal>(0.25) * s;
w = (pRotMatrix.b1 - pRotMatrix.a2) / s;
}
}
// ---------------------------------------------------------------------------
// Construction from euler angles
template<typename TReal>
inline aiQuaterniont<TReal>::aiQuaterniont( TReal fPitch, TReal fYaw, TReal fRoll )
{
const TReal fSinPitch(std::sin(fPitch*static_cast<TReal>(0.5)));
const TReal fCosPitch(std::cos(fPitch*static_cast<TReal>(0.5)));
const TReal fSinYaw(std::sin(fYaw*static_cast<TReal>(0.5)));
const TReal fCosYaw(std::cos(fYaw*static_cast<TReal>(0.5)));
const TReal fSinRoll(std::sin(fRoll*static_cast<TReal>(0.5)));
const TReal fCosRoll(std::cos(fRoll*static_cast<TReal>(0.5)));
const TReal fCosPitchCosYaw(fCosPitch*fCosYaw);
const TReal fSinPitchSinYaw(fSinPitch*fSinYaw);
x = fSinRoll * fCosPitchCosYaw - fCosRoll * fSinPitchSinYaw;
y = fCosRoll * fSinPitch * fCosYaw + fSinRoll * fCosPitch * fSinYaw;
z = fCosRoll * fCosPitch * fSinYaw - fSinRoll * fSinPitch * fCosYaw;
w = fCosRoll * fCosPitchCosYaw + fSinRoll * fSinPitchSinYaw;
}
// ---------------------------------------------------------------------------
// Returns a matrix representation of the quaternion
template<typename TReal>
inline aiMatrix3x3t<TReal> aiQuaterniont<TReal>::GetMatrix() const
{
aiMatrix3x3t<TReal> resMatrix;
resMatrix.a1 = static_cast<TReal>(1.0) - static_cast<TReal>(2.0) * (y * y + z * z);
resMatrix.a2 = static_cast<TReal>(2.0) * (x * y - z * w);
resMatrix.a3 = static_cast<TReal>(2.0) * (x * z + y * w);
resMatrix.b1 = static_cast<TReal>(2.0) * (x * y + z * w);
resMatrix.b2 = static_cast<TReal>(1.0) - static_cast<TReal>(2.0) * (x * x + z * z);
resMatrix.b3 = static_cast<TReal>(2.0) * (y * z - x * w);
resMatrix.c1 = static_cast<TReal>(2.0) * (x * z - y * w);
resMatrix.c2 = static_cast<TReal>(2.0) * (y * z + x * w);
resMatrix.c3 = static_cast<TReal>(1.0) - static_cast<TReal>(2.0) * (x * x + y * y);
return resMatrix;
}
// ---------------------------------------------------------------------------
// Construction from an axis-angle pair
template<typename TReal>
inline aiQuaterniont<TReal>::aiQuaterniont( aiVector3t<TReal> axis, TReal angle)
{
axis.Normalize();
const TReal sin_a = std::sin( angle / 2 );
const TReal cos_a = std::cos( angle / 2 );
x = axis.x * sin_a;
y = axis.y * sin_a;
z = axis.z * sin_a;
w = cos_a;
}
// ---------------------------------------------------------------------------
// Construction from am existing, normalized quaternion
template<typename TReal>
inline aiQuaterniont<TReal>::aiQuaterniont( aiVector3t<TReal> normalized)
{
x = normalized.x;
y = normalized.y;
z = normalized.z;
const TReal t = static_cast<TReal>(1.0) - (x*x) - (y*y) - (z*z);
if (t < static_cast<TReal>(0.0)) {
w = static_cast<TReal>(0.0);
}
else w = std::sqrt (t);
}
// ---------------------------------------------------------------------------
// Performs a spherical interpolation between two quaternions
// Implementation adopted from the gmtl project. All others I found on the net fail in some cases.
// Congrats, gmtl!
template<typename TReal>
inline void aiQuaterniont<TReal>::Interpolate( aiQuaterniont& pOut, const aiQuaterniont& pStart, const aiQuaterniont& pEnd, TReal pFactor)
{
// calc cosine theta
TReal cosom = pStart.x * pEnd.x + pStart.y * pEnd.y + pStart.z * pEnd.z + pStart.w * pEnd.w;
// adjust signs (if necessary)
aiQuaterniont end = pEnd;
if( cosom < static_cast<TReal>(0.0))
{
cosom = -cosom;
end.x = -end.x; // Reverse all signs
end.y = -end.y;
end.z = -end.z;
end.w = -end.w;
}
// Calculate coefficients
TReal sclp, sclq;
if( (static_cast<TReal>(1.0) - cosom) > static_cast<TReal>(0.0001)) // 0.0001 -> some epsillon
{
// Standard case (slerp)
TReal omega, sinom;
omega = std::acos( cosom); // extract theta from dot product's cos theta
sinom = std::sin( omega);
sclp = std::sin( (static_cast<TReal>(1.0) - pFactor) * omega) / sinom;
sclq = std::sin( pFactor * omega) / sinom;
} else
{
// Very close, do linear interp (because it's faster)
sclp = static_cast<TReal>(1.0) - pFactor;
sclq = pFactor;
}
pOut.x = sclp * pStart.x + sclq * end.x;
pOut.y = sclp * pStart.y + sclq * end.y;
pOut.z = sclp * pStart.z + sclq * end.z;
pOut.w = sclp * pStart.w + sclq * end.w;
}
// ---------------------------------------------------------------------------
template<typename TReal>
inline aiQuaterniont<TReal>& aiQuaterniont<TReal>::Normalize()
{
// compute the magnitude and divide through it
const TReal mag = std::sqrt(x*x + y*y + z*z + w*w);
if (mag)
{
const TReal invMag = static_cast<TReal>(1.0)/mag;
x *= invMag;
y *= invMag;
z *= invMag;
w *= invMag;
}
return *this;
}
// ---------------------------------------------------------------------------
template<typename TReal>
inline aiQuaterniont<TReal> aiQuaterniont<TReal>::operator* (const aiQuaterniont& t) const
{
return aiQuaterniont(w*t.w - x*t.x - y*t.y - z*t.z,
w*t.x + x*t.w + y*t.z - z*t.y,
w*t.y + y*t.w + z*t.x - x*t.z,
w*t.z + z*t.w + x*t.y - y*t.x);
}
// ---------------------------------------------------------------------------
template<typename TReal>
inline aiQuaterniont<TReal>& aiQuaterniont<TReal>::Conjugate ()
{
x = -x;
y = -y;
z = -z;
return *this;
}
// ---------------------------------------------------------------------------
template<typename TReal>
inline aiVector3t<TReal> aiQuaterniont<TReal>::Rotate (const aiVector3t<TReal>& v)
{
aiQuaterniont q2(0.f,v.x,v.y,v.z), q = *this, qinv = q;
qinv.Conjugate();
q = q*q2*qinv;
return aiVector3t<TReal>(q.x,q.y,q.z);
}
#endif
#endif // AI_QUATERNION_INL_INC

View File

@ -0,0 +1,425 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file scene.h
* @brief Defines the data structures in which the imported scene is returned.
*/
#pragma once
#ifndef AI_SCENE_H_INC
#define AI_SCENE_H_INC
#include "types.h"
#include "texture.h"
#include "mesh.h"
#include "light.h"
#include "camera.h"
#include "material.h"
#include "anim.h"
#include "metadata.h"
#ifdef __cplusplus
# include <cstdlib>
extern "C" {
#endif
#ifdef __GNUC__
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wattributes"
#endif
// -------------------------------------------------------------------------------
/**
* A node in the imported hierarchy.
*
* Each node has name, a parent node (except for the root node),
* a transformation relative to its parent and possibly several child nodes.
* Simple file formats don't support hierarchical structures - for these formats
* the imported scene does consist of only a single root node without children.
*/
// -------------------------------------------------------------------------------
struct ASSIMP_API aiNode
{
/** The name of the node.
*
* The name might be empty (length of zero) but all nodes which
* need to be referenced by either bones or animations are named.
* Multiple nodes may have the same name, except for nodes which are referenced
* by bones (see #aiBone and #aiMesh::mBones). Their names *must* be unique.
*
* Cameras and lights reference a specific node by name - if there
* are multiple nodes with this name, they are assigned to each of them.
* <br>
* There are no limitations with regard to the characters contained in
* the name string as it is usually taken directly from the source file.
*
* Implementations should be able to handle tokens such as whitespace, tabs,
* line feeds, quotation marks, ampersands etc.
*
* Sometimes assimp introduces new nodes not present in the source file
* into the hierarchy (usually out of necessity because sometimes the
* source hierarchy format is simply not compatible). Their names are
* surrounded by @verbatim <> @endverbatim e.g.
* @verbatim<DummyRootNode> @endverbatim.
*/
C_STRUCT aiString mName;
/** The transformation relative to the node's parent. */
C_STRUCT aiMatrix4x4 mTransformation;
/** Parent node. NULL if this node is the root node. */
C_STRUCT aiNode* mParent;
/** The number of child nodes of this node. */
unsigned int mNumChildren;
/** The child nodes of this node. NULL if mNumChildren is 0. */
C_STRUCT aiNode** mChildren;
/** The number of meshes of this node. */
unsigned int mNumMeshes;
/** The meshes of this node. Each entry is an index into the
* mesh list of the #aiScene.
*/
unsigned int* mMeshes;
/** Metadata associated with this node or NULL if there is no metadata.
* Whether any metadata is generated depends on the source file format. See the
* @link importer_notes @endlink page for more information on every source file
* format. Importers that don't document any metadata don't write any.
*/
C_STRUCT aiMetadata* mMetaData;
#ifdef __cplusplus
/** Constructor */
aiNode();
/** Construction from a specific name */
explicit aiNode(const std::string& name);
/** Destructor */
~aiNode();
/** Searches for a node with a specific name, beginning at this
* nodes. Normally you will call this method on the root node
* of the scene.
*
* @param name Name to search for
* @return NULL or a valid Node if the search was successful.
*/
inline
const aiNode* FindNode(const aiString& name) const {
return FindNode(name.data);
}
inline
aiNode* FindNode(const aiString& name) {
return FindNode(name.data);
}
const aiNode* FindNode(const char* name) const;
aiNode* FindNode(const char* name);
/**
* @brief Will add new children.
* @param numChildren Number of children to add.
* @param children The array with pointers showing to the children.
*/
void addChildren(unsigned int numChildren, aiNode **children);
#endif // __cplusplus
};
#ifdef __GNUC__
#pragma GCC diagnostic pop
#endif
// -------------------------------------------------------------------------------
/**
* Specifies that the scene data structure that was imported is not complete.
* This flag bypasses some internal validations and allows the import
* of animation skeletons, material libraries or camera animation paths
* using Assimp. Most applications won't support such data.
*/
#define AI_SCENE_FLAGS_INCOMPLETE 0x1
/**
* This flag is set by the validation postprocess-step (aiPostProcess_ValidateDS)
* if the validation is successful. In a validated scene you can be sure that
* any cross references in the data structure (e.g. vertex indices) are valid.
*/
#define AI_SCENE_FLAGS_VALIDATED 0x2
/**
* This flag is set by the validation postprocess-step (aiPostProcess_ValidateDS)
* if the validation is successful but some issues have been found.
* This can for example mean that a texture that does not exist is referenced
* by a material or that the bone weights for a vertex don't sum to 1.0 ... .
* In most cases you should still be able to use the import. This flag could
* be useful for applications which don't capture Assimp's log output.
*/
#define AI_SCENE_FLAGS_VALIDATION_WARNING 0x4
/**
* This flag is currently only set by the aiProcess_JoinIdenticalVertices step.
* It indicates that the vertices of the output meshes aren't in the internal
* verbose format anymore. In the verbose format all vertices are unique,
* no vertex is ever referenced by more than one face.
*/
#define AI_SCENE_FLAGS_NON_VERBOSE_FORMAT 0x8
/**
* Denotes pure height-map terrain data. Pure terrains usually consist of quads,
* sometimes triangles, in a regular grid. The x,y coordinates of all vertex
* positions refer to the x,y coordinates on the terrain height map, the z-axis
* stores the elevation at a specific point.
*
* TER (Terragen) and HMP (3D Game Studio) are height map formats.
* @note Assimp is probably not the best choice for loading *huge* terrains -
* fully triangulated data takes extremely much free store and should be avoided
* as long as possible (typically you'll do the triangulation when you actually
* need to render it).
*/
#define AI_SCENE_FLAGS_TERRAIN 0x10
/**
* Specifies that the scene data can be shared between structures. For example:
* one vertex in few faces. \ref AI_SCENE_FLAGS_NON_VERBOSE_FORMAT can not be
* used for this because \ref AI_SCENE_FLAGS_NON_VERBOSE_FORMAT has internal
* meaning about postprocessing steps.
*/
#define AI_SCENE_FLAGS_ALLOW_SHARED 0x20
// -------------------------------------------------------------------------------
/** The root structure of the imported data.
*
* Everything that was imported from the given file can be accessed from here.
* Objects of this class are generally maintained and owned by Assimp, not
* by the caller. You shouldn't want to instance it, nor should you ever try to
* delete a given scene on your own.
*/
// -------------------------------------------------------------------------------
struct aiScene
{
/** Any combination of the AI_SCENE_FLAGS_XXX flags. By default
* this value is 0, no flags are set. Most applications will
* want to reject all scenes with the AI_SCENE_FLAGS_INCOMPLETE
* bit set.
*/
unsigned int mFlags;
/** The root node of the hierarchy.
*
* There will always be at least the root node if the import
* was successful (and no special flags have been set).
* Presence of further nodes depends on the format and content
* of the imported file.
*/
C_STRUCT aiNode* mRootNode;
/** The number of meshes in the scene. */
unsigned int mNumMeshes;
/** The array of meshes.
*
* Use the indices given in the aiNode structure to access
* this array. The array is mNumMeshes in size. If the
* AI_SCENE_FLAGS_INCOMPLETE flag is not set there will always
* be at least ONE material.
*/
C_STRUCT aiMesh** mMeshes;
/** The number of materials in the scene. */
unsigned int mNumMaterials;
/** The array of materials.
*
* Use the index given in each aiMesh structure to access this
* array. The array is mNumMaterials in size. If the
* AI_SCENE_FLAGS_INCOMPLETE flag is not set there will always
* be at least ONE material.
*/
C_STRUCT aiMaterial** mMaterials;
/** The number of animations in the scene. */
unsigned int mNumAnimations;
/** The array of animations.
*
* All animations imported from the given file are listed here.
* The array is mNumAnimations in size.
*/
C_STRUCT aiAnimation** mAnimations;
/** The number of textures embedded into the file */
unsigned int mNumTextures;
/** The array of embedded textures.
*
* Not many file formats embed their textures into the file.
* An example is Quake's MDL format (which is also used by
* some GameStudio versions)
*/
C_STRUCT aiTexture** mTextures;
/** The number of light sources in the scene. Light sources
* are fully optional, in most cases this attribute will be 0
*/
unsigned int mNumLights;
/** The array of light sources.
*
* All light sources imported from the given file are
* listed here. The array is mNumLights in size.
*/
C_STRUCT aiLight** mLights;
/** The number of cameras in the scene. Cameras
* are fully optional, in most cases this attribute will be 0
*/
unsigned int mNumCameras;
/** The array of cameras.
*
* All cameras imported from the given file are listed here.
* The array is mNumCameras in size. The first camera in the
* array (if existing) is the default camera view into
* the scene.
*/
C_STRUCT aiCamera** mCameras;
/**
* @brief The global metadata assigned to the scene itself.
*
* This data contains global metadata which belongs to the scene like
* unit-conversions, versions, vendors or other model-specific data. This
* can be used to store format-specific metadata as well.
*/
C_STRUCT aiMetadata* mMetaData;
#ifdef __cplusplus
//! Default constructor - set everything to 0/NULL
ASSIMP_API aiScene();
//! Destructor
ASSIMP_API ~aiScene();
//! Check whether the scene contains meshes
//! Unless no special scene flags are set this will always be true.
inline bool HasMeshes() const {
return mMeshes != NULL && mNumMeshes > 0;
}
//! Check whether the scene contains materials
//! Unless no special scene flags are set this will always be true.
inline bool HasMaterials() const {
return mMaterials != NULL && mNumMaterials > 0;
}
//! Check whether the scene contains lights
inline bool HasLights() const {
return mLights != NULL && mNumLights > 0;
}
//! Check whether the scene contains textures
inline bool HasTextures() const {
return mTextures != NULL && mNumTextures > 0;
}
//! Check whether the scene contains cameras
inline bool HasCameras() const {
return mCameras != NULL && mNumCameras > 0;
}
//! Check whether the scene contains animations
inline bool HasAnimations() const {
return mAnimations != NULL && mNumAnimations > 0;
}
//! Returns a short filename from a full path
static const char* GetShortFilename(const char* filename) {
const char* lastSlash = strrchr(filename, '/');
if (lastSlash == nullptr) {
lastSlash = strrchr(filename, '\\');
}
const char* shortFilename = lastSlash != nullptr ? lastSlash + 1 : filename;
return shortFilename;
}
//! Returns an embedded texture
const aiTexture* GetEmbeddedTexture(const char* filename) const {
// lookup using texture ID (if referenced like: "*1", "*2", etc.)
if ('*' == *filename) {
int index = std::atoi(filename + 1);
if (0 > index || mNumTextures <= static_cast<unsigned>(index))
return nullptr;
return mTextures[index];
}
// lookup using filename
const char* shortFilename = GetShortFilename(filename);
for (unsigned int i = 0; i < mNumTextures; i++) {
const char* shortTextureFilename = GetShortFilename(mTextures[i]->mFilename.C_Str());
if (strcmp(shortTextureFilename, shortFilename) == 0) {
return mTextures[i];
}
}
return nullptr;
}
#endif // __cplusplus
/** Internal data, do not touch */
#ifdef __cplusplus
void* mPrivate;
#else
char* mPrivate;
#endif
};
#ifdef __cplusplus
} //! namespace Assimp
#endif
#endif // AI_SCENE_H_INC

View File

@ -0,0 +1,227 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file texture.h
* @brief Defines texture helper structures for the library
*
* Used for file formats which embed their textures into the model file.
* Supported are both normal textures, which are stored as uncompressed
* pixels, and "compressed" textures, which are stored in a file format
* such as PNG or TGA.
*/
#pragma once
#ifndef AI_TEXTURE_H_INC
#define AI_TEXTURE_H_INC
#include "types.h"
#ifdef __cplusplus
extern "C" {
#endif
// --------------------------------------------------------------------------------
/** \def AI_EMBEDDED_TEXNAME_PREFIX
* \ref AI_MAKE_EMBEDDED_TEXNAME
*/
#ifndef AI_EMBEDDED_TEXNAME_PREFIX
# define AI_EMBEDDED_TEXNAME_PREFIX "*"
#endif
/** @def AI_MAKE_EMBEDDED_TEXNAME
* Used to build the reserved path name used by the material system to
* reference textures that are embedded into their corresponding
* model files. The parameter specifies the index of the texture
* (zero-based, in the aiScene::mTextures array)
*/
#if (!defined AI_MAKE_EMBEDDED_TEXNAME)
# define AI_MAKE_EMBEDDED_TEXNAME(_n_) AI_EMBEDDED_TEXNAME_PREFIX # _n_
#endif
#include "./Compiler/pushpack1.h"
// --------------------------------------------------------------------------------
/** @brief Helper structure to represent a texel in a ARGB8888 format
*
* Used by aiTexture.
*/
struct aiTexel
{
unsigned char b,g,r,a;
#ifdef __cplusplus
//! Comparison operator
bool operator== (const aiTexel& other) const
{
return b == other.b && r == other.r &&
g == other.g && a == other.a;
}
//! Inverse comparison operator
bool operator!= (const aiTexel& other) const
{
return b != other.b || r != other.r ||
g != other.g || a != other.a;
}
//! Conversion to a floating-point 4d color
operator aiColor4D() const
{
return aiColor4D(r/255.f,g/255.f,b/255.f,a/255.f);
}
#endif // __cplusplus
} PACK_STRUCT;
#include "./Compiler/poppack1.h"
#define HINTMAXTEXTURELEN 9
// --------------------------------------------------------------------------------
/** Helper structure to describe an embedded texture
*
* Normally textures are contained in external files but some file formats embed
* them directly in the model file. There are two types of embedded textures:
* 1. Uncompressed textures. The color data is given in an uncompressed format.
* 2. Compressed textures stored in a file format like png or jpg. The raw file
* bytes are given so the application must utilize an image decoder (e.g. DevIL) to
* get access to the actual color data.
*
* Embedded textures are referenced from materials using strings like "*0", "*1", etc.
* as the texture paths (a single asterisk character followed by the
* zero-based index of the texture in the aiScene::mTextures array).
*/
struct aiTexture {
/** Width of the texture, in pixels
*
* If mHeight is zero the texture is compressed in a format
* like JPEG. In this case mWidth specifies the size of the
* memory area pcData is pointing to, in bytes.
*/
unsigned int mWidth;
/** Height of the texture, in pixels
*
* If this value is zero, pcData points to an compressed texture
* in any format (e.g. JPEG).
*/
unsigned int mHeight;
/** A hint from the loader to make it easier for applications
* to determine the type of embedded textures.
*
* If mHeight != 0 this member is show how data is packed. Hint will consist of
* two parts: channel order and channel bitness (count of the bits for every
* color channel). For simple parsing by the viewer it's better to not omit
* absent color channel and just use 0 for bitness. For example:
* 1. Image contain RGBA and 8 bit per channel, achFormatHint == "rgba8888";
* 2. Image contain ARGB and 8 bit per channel, achFormatHint == "argb8888";
* 3. Image contain RGB and 5 bit for R and B channels and 6 bit for G channel, achFormatHint == "rgba5650";
* 4. One color image with B channel and 1 bit for it, achFormatHint == "rgba0010";
* If mHeight == 0 then achFormatHint is set set to '\\0\\0\\0\\0' if the loader has no additional
* information about the texture file format used OR the
* file extension of the format without a trailing dot. If there
* are multiple file extensions for a format, the shortest
* extension is chosen (JPEG maps to 'jpg', not to 'jpeg').
* E.g. 'dds\\0', 'pcx\\0', 'jpg\\0'. All characters are lower-case.
* The fourth character will always be '\\0'.
*/
char achFormatHint[ HINTMAXTEXTURELEN ];// 8 for string + 1 for terminator.
/** Data of the texture.
*
* Points to an array of mWidth * mHeight aiTexel's.
* The format of the texture data is always ARGB8888 to
* make the implementation for user of the library as easy
* as possible. If mHeight = 0 this is a pointer to a memory
* buffer of size mWidth containing the compressed texture
* data. Good luck, have fun!
*/
C_STRUCT aiTexel* pcData;
/** Texture original filename
*
* Used to get the texture reference
*/
C_STRUCT aiString mFilename;
#ifdef __cplusplus
//! For compressed textures (mHeight == 0): compare the
//! format hint against a given string.
//! @param s Input string. 3 characters are maximally processed.
//! Example values: "jpg", "png"
//! @return true if the given string matches the format hint
bool CheckFormat(const char* s) const {
if (nullptr == s) {
return false;
}
return (0 == ::strncmp(achFormatHint, s, sizeof(achFormatHint)));
}
// Construction
aiTexture() AI_NO_EXCEPT
: mWidth(0)
, mHeight(0)
, pcData(nullptr)
, mFilename() {
achFormatHint[0] = achFormatHint[1] = 0;
achFormatHint[2] = achFormatHint[3] = 0;
}
// Destruction
~aiTexture () {
delete[] pcData;
}
#endif
};
#ifdef __cplusplus
}
#endif
#endif // AI_TEXTURE_H_INC

View File

@ -0,0 +1,541 @@
/*
---------------------------------------------------------------------------
Open Asset Import Library (assimp)
---------------------------------------------------------------------------
Copyright (c) 2006-2019, assimp team
All rights reserved.
Redistribution and use of this software in source and binary forms,
with or without modification, are permitted provided that the following
conditions are met:
* Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the
following disclaimer in the documentation and/or other
materials provided with the distribution.
* Neither the name of the assimp team, nor the names of its
contributors may be used to endorse or promote products
derived from this software without specific prior
written permission of the assimp team.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file types.h
* Basic data types and primitives, such as vectors or colors.
*/
#pragma once
#ifndef AI_TYPES_H_INC
#define AI_TYPES_H_INC
// Some runtime headers
#include <sys/types.h>
#include <stddef.h>
#include <string.h>
#include <limits.h>
#include <stdint.h>
// Our compile configuration
#include "defs.h"
// Some types moved to separate header due to size of operators
#include "vector3.h"
#include "vector2.h"
#include "color4.h"
#include "matrix3x3.h"
#include "matrix4x4.h"
#include "quaternion.h"
typedef int32_t ai_int32;
typedef uint32_t ai_uint32 ;
#ifdef __cplusplus
#include <cstring>
#include <new> // for std::nothrow_t
#include <string> // for aiString::Set(const std::string&)
namespace Assimp {
//! @cond never
namespace Intern {
// --------------------------------------------------------------------
/** @brief Internal helper class to utilize our internal new/delete
* routines for allocating object of this and derived classes.
*
* By doing this you can safely share class objects between Assimp
* and the application - it works even over DLL boundaries. A good
* example is the #IOSystem where the application allocates its custom
* #IOSystem, then calls #Importer::SetIOSystem(). When the Importer
* destructs, Assimp calls operator delete on the stored #IOSystem.
* If it lies on a different heap than Assimp is working with,
* the application is determined to crash.
*/
// --------------------------------------------------------------------
#ifndef SWIG
struct ASSIMP_API AllocateFromAssimpHeap {
// http://www.gotw.ca/publications/mill15.htm
// new/delete overload
void *operator new ( size_t num_bytes) /* throw( std::bad_alloc ) */;
void *operator new ( size_t num_bytes, const std::nothrow_t& ) throw();
void operator delete ( void* data);
// array new/delete overload
void *operator new[] ( size_t num_bytes) /* throw( std::bad_alloc ) */;
void *operator new[] ( size_t num_bytes, const std::nothrow_t& ) throw();
void operator delete[] ( void* data);
}; // struct AllocateFromAssimpHeap
#endif
} // namespace Intern
//! @endcond
} // namespace Assimp
extern "C" {
#endif
/** Maximum dimension for strings, ASSIMP strings are zero terminated. */
#ifdef __cplusplus
static const size_t MAXLEN = 1024;
#else
# define MAXLEN 1024
#endif
// ----------------------------------------------------------------------------------
/** Represents a plane in a three-dimensional, euclidean space
*/
struct aiPlane {
#ifdef __cplusplus
aiPlane () AI_NO_EXCEPT : a(0.f), b(0.f), c(0.f), d(0.f) {}
aiPlane (ai_real _a, ai_real _b, ai_real _c, ai_real _d)
: a(_a), b(_b), c(_c), d(_d) {}
aiPlane (const aiPlane& o) : a(o.a), b(o.b), c(o.c), d(o.d) {}
#endif // !__cplusplus
//! Plane equation
ai_real a,b,c,d;
}; // !struct aiPlane
// ----------------------------------------------------------------------------------
/** Represents a ray
*/
struct aiRay {
#ifdef __cplusplus
aiRay () AI_NO_EXCEPT {}
aiRay (const aiVector3D& _pos, const aiVector3D& _dir)
: pos(_pos), dir(_dir) {}
aiRay (const aiRay& o) : pos (o.pos), dir (o.dir) {}
#endif // !__cplusplus
//! Position and direction of the ray
C_STRUCT aiVector3D pos, dir;
}; // !struct aiRay
// ----------------------------------------------------------------------------------
/** Represents a color in Red-Green-Blue space.
*/
struct aiColor3D
{
#ifdef __cplusplus
aiColor3D () AI_NO_EXCEPT : r(0.0f), g(0.0f), b(0.0f) {}
aiColor3D (ai_real _r, ai_real _g, ai_real _b) : r(_r), g(_g), b(_b) {}
explicit aiColor3D (ai_real _r) : r(_r), g(_r), b(_r) {}
aiColor3D (const aiColor3D& o) : r(o.r), g(o.g), b(o.b) {}
aiColor3D &operator=(const aiColor3D &o) {
r = o.r;
g = o.g;
b = o.b;
return *this;
}
/** Component-wise comparison */
// TODO: add epsilon?
bool operator == (const aiColor3D& other) const
{return r == other.r && g == other.g && b == other.b;}
/** Component-wise inverse comparison */
// TODO: add epsilon?
bool operator != (const aiColor3D& other) const
{return r != other.r || g != other.g || b != other.b;}
/** Component-wise comparison */
// TODO: add epsilon?
bool operator < (const aiColor3D& other) const {
return r < other.r || ( r == other.r && (g < other.g || (g == other.g && b < other.b ) ) );
}
/** Component-wise addition */
aiColor3D operator+(const aiColor3D& c) const {
return aiColor3D(r+c.r,g+c.g,b+c.b);
}
/** Component-wise subtraction */
aiColor3D operator-(const aiColor3D& c) const {
return aiColor3D(r-c.r,g-c.g,b-c.b);
}
/** Component-wise multiplication */
aiColor3D operator*(const aiColor3D& c) const {
return aiColor3D(r*c.r,g*c.g,b*c.b);
}
/** Multiply with a scalar */
aiColor3D operator*(ai_real f) const {
return aiColor3D(r*f,g*f,b*f);
}
/** Access a specific color component */
ai_real operator[](unsigned int i) const {
return *(&r + i);
}
/** Access a specific color component */
ai_real& operator[](unsigned int i) {
if ( 0 == i ) {
return r;
} else if ( 1 == i ) {
return g;
} else if ( 2 == i ) {
return b;
}
return r;
}
/** Check whether a color is black */
bool IsBlack() const {
static const ai_real epsilon = ai_real(10e-3);
return std::fabs( r ) < epsilon && std::fabs( g ) < epsilon && std::fabs( b ) < epsilon;
}
#endif // !__cplusplus
//! Red, green and blue color values
ai_real r, g, b;
}; // !struct aiColor3D
// ----------------------------------------------------------------------------------
/** Represents an UTF-8 string, zero byte terminated.
*
* The character set of an aiString is explicitly defined to be UTF-8. This Unicode
* transformation was chosen in the belief that most strings in 3d files are limited
* to ASCII, thus the character set needed to be strictly ASCII compatible.
*
* Most text file loaders provide proper Unicode input file handling, special unicode
* characters are correctly transcoded to UTF8 and are kept throughout the libraries'
* import pipeline.
*
* For most applications, it will be absolutely sufficient to interpret the
* aiString as ASCII data and work with it as one would work with a plain char*.
* Windows users in need of proper support for i.e asian characters can use the
* MultiByteToWideChar(), WideCharToMultiByte() WinAPI functionality to convert the
* UTF-8 strings to their working character set (i.e. MBCS, WideChar).
*
* We use this representation instead of std::string to be C-compatible. The
* (binary) length of such a string is limited to MAXLEN characters (including the
* the terminating zero).
*/
struct aiString
{
#ifdef __cplusplus
/** Default constructor, the string is set to have zero length */
aiString() AI_NO_EXCEPT
: length( 0 ) {
data[0] = '\0';
#ifdef ASSIMP_BUILD_DEBUG
// Debug build: overwrite the string on its full length with ESC (27)
memset(data+1,27,MAXLEN-1);
#endif
}
/** Copy constructor */
aiString(const aiString& rOther)
: length(rOther.length)
{
// Crop the string to the maximum length
length = length>=MAXLEN?MAXLEN-1:length;
memcpy( data, rOther.data, length);
data[length] = '\0';
}
/** Constructor from std::string */
explicit aiString(const std::string& pString) :
length( (ai_uint32) pString.length())
{
length = length>=MAXLEN?MAXLEN-1:length;
memcpy( data, pString.c_str(), length);
data[length] = '\0';
}
/** Copy a std::string to the aiString */
void Set( const std::string& pString) {
if( pString.length() > MAXLEN - 1) {
return;
}
length = (ai_uint32)pString.length();
memcpy( data, pString.c_str(), length);
data[length] = 0;
}
/** Copy a const char* to the aiString */
void Set( const char* sz) {
const ai_int32 len = (ai_uint32) ::strlen(sz);
if( len > (ai_int32)MAXLEN - 1) {
return;
}
length = len;
memcpy( data, sz, len);
data[len] = 0;
}
/** Assignment operator */
aiString& operator = (const aiString &rOther) {
if (this == &rOther) {
return *this;
}
length = rOther.length;;
memcpy( data, rOther.data, length);
data[length] = '\0';
return *this;
}
/** Assign a const char* to the string */
aiString& operator = (const char* sz) {
Set(sz);
return *this;
}
/** Assign a cstd::string to the string */
aiString& operator = ( const std::string& pString) {
Set(pString);
return *this;
}
/** Comparison operator */
bool operator==(const aiString& other) const {
return (length == other.length && 0 == memcmp(data,other.data,length));
}
/** Inverse comparison operator */
bool operator!=(const aiString& other) const {
return (length != other.length || 0 != memcmp(data,other.data,length));
}
/** Append a string to the string */
void Append (const char* app) {
const ai_uint32 len = (ai_uint32) ::strlen(app);
if (!len) {
return;
}
if (length + len >= MAXLEN) {
return;
}
memcpy(&data[length],app,len+1);
length += len;
}
/** Clear the string - reset its length to zero */
void Clear () {
length = 0;
data[0] = '\0';
#ifdef ASSIMP_BUILD_DEBUG
// Debug build: overwrite the string on its full length with ESC (27)
memset(data+1,27,MAXLEN-1);
#endif
}
/** Returns a pointer to the underlying zero-terminated array of characters */
const char* C_Str() const {
return data;
}
#endif // !__cplusplus
/** Binary length of the string excluding the terminal 0. This is NOT the
* logical length of strings containing UTF-8 multi-byte sequences! It's
* the number of bytes from the beginning of the string to its end.*/
ai_uint32 length;
/** String buffer. Size limit is MAXLEN */
char data[MAXLEN];
} ; // !struct aiString
// ----------------------------------------------------------------------------------
/** Standard return type for some library functions.
* Rarely used, and if, mostly in the C API.
*/
typedef enum aiReturn
{
/** Indicates that a function was successful */
aiReturn_SUCCESS = 0x0,
/** Indicates that a function failed */
aiReturn_FAILURE = -0x1,
/** Indicates that not enough memory was available
* to perform the requested operation
*/
aiReturn_OUTOFMEMORY = -0x3,
/** @cond never
* Force 32-bit size enum
*/
_AI_ENFORCE_ENUM_SIZE = 0x7fffffff
/// @endcond
} aiReturn; // !enum aiReturn
// just for backwards compatibility, don't use these constants anymore
#define AI_SUCCESS aiReturn_SUCCESS
#define AI_FAILURE aiReturn_FAILURE
#define AI_OUTOFMEMORY aiReturn_OUTOFMEMORY
// ----------------------------------------------------------------------------------
/** Seek origins (for the virtual file system API).
* Much cooler than using SEEK_SET, SEEK_CUR or SEEK_END.
*/
enum aiOrigin
{
/** Beginning of the file */
aiOrigin_SET = 0x0,
/** Current position of the file pointer */
aiOrigin_CUR = 0x1,
/** End of the file, offsets must be negative */
aiOrigin_END = 0x2,
/** @cond never
* Force 32-bit size enum
*/
_AI_ORIGIN_ENFORCE_ENUM_SIZE = 0x7fffffff
/// @endcond
}; // !enum aiOrigin
// ----------------------------------------------------------------------------------
/** @brief Enumerates predefined log streaming destinations.
* Logging to these streams can be enabled with a single call to
* #LogStream::createDefaultStream.
*/
enum aiDefaultLogStream
{
/** Stream the log to a file */
aiDefaultLogStream_FILE = 0x1,
/** Stream the log to std::cout */
aiDefaultLogStream_STDOUT = 0x2,
/** Stream the log to std::cerr */
aiDefaultLogStream_STDERR = 0x4,
/** MSVC only: Stream the log the the debugger
* (this relies on OutputDebugString from the Win32 SDK)
*/
aiDefaultLogStream_DEBUGGER = 0x8,
/** @cond never
* Force 32-bit size enum
*/
_AI_DLS_ENFORCE_ENUM_SIZE = 0x7fffffff
/// @endcond
}; // !enum aiDefaultLogStream
// just for backwards compatibility, don't use these constants anymore
#define DLS_FILE aiDefaultLogStream_FILE
#define DLS_STDOUT aiDefaultLogStream_STDOUT
#define DLS_STDERR aiDefaultLogStream_STDERR
#define DLS_DEBUGGER aiDefaultLogStream_DEBUGGER
// ----------------------------------------------------------------------------------
/** Stores the memory requirements for different components (e.g. meshes, materials,
* animations) of an import. All sizes are in bytes.
* @see Importer::GetMemoryRequirements()
*/
struct aiMemoryInfo
{
#ifdef __cplusplus
/** Default constructor */
aiMemoryInfo() AI_NO_EXCEPT
: textures (0)
, materials (0)
, meshes (0)
, nodes (0)
, animations (0)
, cameras (0)
, lights (0)
, total (0)
{}
#endif
/** Storage allocated for texture data */
unsigned int textures;
/** Storage allocated for material data */
unsigned int materials;
/** Storage allocated for mesh data */
unsigned int meshes;
/** Storage allocated for node data */
unsigned int nodes;
/** Storage allocated for animation data */
unsigned int animations;
/** Storage allocated for camera data */
unsigned int cameras;
/** Storage allocated for light data */
unsigned int lights;
/** Total storage allocated for the full import. */
unsigned int total;
}; // !struct aiMemoryInfo
#ifdef __cplusplus
}
#endif //! __cplusplus
// Include implementation files
#include "vector2.inl"
#include "vector3.inl"
#include "color4.inl"
#include "quaternion.inl"
#include "matrix3x3.inl"
#include "matrix4x4.inl"
#endif // AI_TYPES_H_INC

Some files were not shown because too many files have changed in this diff Show More