Ver Fonte

WIP version of a LWO file loader. Not working yet.

git-svn-id: https://assimp.svn.sourceforge.net/svnroot/assimp/trunk@82 67173fc5-114c-0410-ac8e-9d2fd5bffc1f
aramis_acg há 17 anos atrás
pai
commit
42ef23e745
8 ficheiros alterados com 1080 adições e 18 exclusões
  1. 47 18
      code/ByteSwap.h
  2. 57 0
      code/IFF.h
  3. 6 0
      code/Importer.cpp
  4. 300 0
      code/LWOFileData.h
  5. 487 0
      code/LWOLoader.cpp
  6. 158 0
      code/LWOLoader.h
  7. 1 0
      code/STLLoader.cpp
  8. 24 0
      workspaces/vc8/assimp.vcproj

+ 47 - 18
code/ByteSwap.h

@@ -44,6 +44,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 #define AI_BYTESWAP_H_INC
 
 #include "../include/aiAssert.h"
+#include "../include/aiTypes.h"
 
 namespace Assimp
 {
@@ -61,26 +62,39 @@ class ByteSwap
 public:
 	//! Swap the byte oder of 2 byte of data
 	//! \param szOut Buffer to be swapped
-	static inline void Swap2(char* szOut)
+	static inline void Swap2(void* _szOut)
 	{
-		ai_assert(NULL != szOut);
+		ai_assert(NULL != _szOut);
+		int8_t* szOut = (int8_t*)_szOut;
 		std::swap(szOut[0],szOut[1]);
 	}
 
 	//! Swap the byte oder of 4 byte of data
 	//! \param szOut Buffer to be swapped
-	static inline void Swap4(char* szOut)
+	static inline void Swap4(void* _szOut)
 	{
-		ai_assert(NULL != szOut);
+#if _MSC_VER >= 1400 && (defined _M_X86)
+		__asm
+		{
+			mov edi, _szOut
+			mov eax, dword_ptr[edi]
+			bswap eax
+			mov dword_ptr[edi], eax
+		};
+#else
+		ai_assert(NULL != _szOut);
+		int8_t* szOut = (int8_t*)_szOut;
 		std::swap(szOut[0],szOut[3]);
 		std::swap(szOut[1],szOut[2]);
+#endif
 	}
 
 	//! Swap the byte oder of 8 byte of data
 	//! \param szOut Buffer to be swapped
-	static inline void Swap8(char* szOut)
+	static inline void Swap8(void* _szOut)
 	{
-		ai_assert(NULL != szOut);
+		ai_assert(NULL != _szOut);
+		int8_t* szOut = (int8_t*)_szOut;
 		std::swap(szOut[0],szOut[7]);
 		std::swap(szOut[1],szOut[6]);
 		std::swap(szOut[2],szOut[5]);
@@ -91,47 +105,54 @@ public:
 	//! \param fOut Float value to be swapped
 	static inline void Swap(float* fOut)
 	{
-		Swap4((char*)fOut);
+		Swap4(fOut);
 	}
 
 	//! Swap a double precision float
 	//! \param fOut Double value to be swapped
 	static inline void Swap(double* fOut)
 	{
-		Swap8((char*)fOut);
+		Swap8(fOut);
 	}
 
 	//! Swap a 16 bit integer
 	//! \param fOut Integer to be swapped
 	static inline void Swap(int16_t* fOut)
 	{
-		Swap2((char*)fOut);
+		Swap2(fOut);
 	}
 
 	//! Swap a 32 bit integer
 	//! \param fOut Integer to be swapped
 	static inline void Swap(int32_t* fOut)	
 	{
-		Swap4((char*)fOut);
+		Swap4(fOut);
 	}
 
 	//! Swap a 64 bit integer
 	//! \param fOut Integer to be swapped
 	static inline void Swap(int64_t* fOut)
 	{
-		Swap8((char*)fOut);
+		Swap8(fOut);
 	}
 };
 };
 
-// byteswap macros for BigEndian support 
+// byteswap macros for BigEndian/LittleEndian support 
 #if (defined AI_BUILD_BIG_ENDIAN)
-#	define AI_SWAP2(p) ByteSwap::Swap2((char*)&(p))
-#	define AI_SWAP4(p) ByteSwap::Swap4((char*)&(p))
-#	define AI_SWAP8(p) ByteSwap::Swap8((char*)&(p))
-#	define AI_SWAP2P(p) ByteSwap::Swap2((char*)(p))
-#	define AI_SWAP4P(p) ByteSwap::Swap4((char*)(p))
-#	define AI_SWAP8P(p) ByteSwap::Swap8((char*)(p))
+#	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_SWAP2(p)
@@ -141,7 +162,15 @@ public:
 #	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
 
 
+
 #endif //!! AI_BYTESWAP_H_INC

+ 57 - 0
code/IFF.h

@@ -0,0 +1,57 @@
+
+
+// Definitions for the Interchange File Format (IFF)
+// Alexander Gessler, 2006
+// Adapted for Assimp August 2008
+
+#ifndef AI_IFF_H_INCLUDED
+#define AI_IFF_H_INCLUDED
+
+#include "ByteSwap.h"
+
+namespace Assimp {
+namespace IFF {
+
+//! Describes an IFF chunk header
+struct ChunkHeader
+{
+	//! Type of the chunk header - FourCC
+	uint32_t type;
+
+	//! Length of the chunk data, in bytes
+	uint32_t length;
+};
+
+
+#define AI_IFF_FOURCC(a,b,c,d) ((uint32_t) (((uint8_t)a << 24u) | \
+	((uint8_t)b << 16u) | ((uint8_t)c << 8u) | ((uint8_t)d)))
+
+
+#define AI_IFF_FOURCC_FORM AI_IFF_FOURCC('F','O','R','M')
+
+
+/////////////////////////////////////////////////////////////////////////////////
+//! Read the file header and return the type of the file and its size
+//! @param outFile Pointer to the file data. The buffer must at 
+//!   least be 12 bytes large.
+//! @param fileType Receives the type of the file
+//! @return 0 if everything was OK, otherwise an error message
+/////////////////////////////////////////////////////////////////////////////////
+inline const char* ReadHeader(const uint8_t* outFile,uint32_t& fileType) 
+{
+	LE_NCONST ChunkHeader* head = (LE_NCONST ChunkHeader*) outFile;
+	AI_LSWAP4(head->length);
+	AI_LSWAP4(head->type);
+	if(AI_IFF_FOURCC_FORM != head->type)
+	{
+		return "The file is not an IFF file: FORM chunk is missing";
+	}
+	fileType = *((uint32_t*)(head+1));
+	AI_LSWAP4(fileType);
+	return 0;
+}
+
+
+}}
+
+#endif // !! AI_IFF_H_INCLUDED

+ 6 - 0
code/Importer.cpp

@@ -98,6 +98,9 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 #if (!defined AI_BUILD_NO_STL_IMPORTER)
 #	include "STLLoader.h"
 #endif
+#if (!defined AI_BUILD_NO_LWO_IMPORTER)
+#	include "LWOLoader.h"
+#endif
 
 // PostProcess-Steps
 #if (!defined AI_BUILD_NO_CALCTANGENTS_PROCESS)
@@ -195,6 +198,9 @@ Importer::Importer() :
 #if (!defined AI_BUILD_NO_STL_IMPORTER)
 	mImporter.push_back( new STLImporter());
 #endif
+#if (!defined AI_BUILD_NO_LWO_IMPORTER)
+	mImporter.push_back( new LWOImporter());
+#endif
 
 	// add an instance of each post processing step here in the order 
 	// of sequence it is executed

+ 300 - 0
code/LWOFileData.h

@@ -0,0 +1,300 @@
+/*
+Open Asset Import Library (ASSIMP)
+----------------------------------------------------------------------
+
+Copyright (c) 2006-2008, ASSIMP Development 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 Development 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 chunk constants used by the LWO file format
+
+The chunks are taken from LWO2.h, found in the sourcecode of
+a project called Nxabega (http://www.sourceforge.net/projects/nxabega).
+I assume they are from the official LightWave SDK headers.
+Original copyright notice: "Ernie Wright  17 Sep 00" 
+ 
+*/
+#ifndef AI_LWO_FILEDATA_INCLUDED
+#define AI_LWO_FILEDATA_INCLUDED
+
+
+#include "IFF.h"
+#include "../include/aiMesh.h"
+
+namespace Assimp {
+namespace LWO {
+
+#define AI_LWO_FOURCC_LWOB AI_IFF_FOURCC('L','W','O','B')
+#define AI_LWO_FOURCC_LWO2 AI_IFF_FOURCC('L','W','O','2')
+
+// chunks specific to the LWOB format
+#define AI_LWO_SRFS  AI_IFF_FOURCC('S','R','F','S')
+#define AI_LWO_FLAG  AI_IFF_FOURCC('F','L','A','G')
+#define AI_LWO_VLUM  AI_IFF_FOURCC('V','L','U','M')
+#define AI_LWO_VDIF  AI_IFF_FOURCC('V','D','I','F')
+#define AI_LWO_VSPC  AI_IFF_FOURCC('V','S','P','C')
+#define AI_LWO_RFLT  AI_IFF_FOURCC('R','F','L','T')
+#define AI_LWO_BTEX  AI_IFF_FOURCC('B','T','E','X')
+#define AI_LWO_CTEX  AI_IFF_FOURCC('C','T','E','X')
+#define AI_LWO_DTEX  AI_IFF_FOURCC('D','T','E','X')
+#define AI_LWO_LTEX  AI_IFF_FOURCC('L','T','E','X')
+#define AI_LWO_RTEX  AI_IFF_FOURCC('R','T','E','X')
+#define AI_LWO_STEX  AI_IFF_FOURCC('S','T','E','X')
+#define AI_LWO_TTEX  AI_IFF_FOURCC('T','T','E','X')
+#define AI_LWO_TFLG  AI_IFF_FOURCC('T','F','L','G')
+#define AI_LWO_TSIZ  AI_IFF_FOURCC('T','S','I','Z')
+#define AI_LWO_TCTR  AI_IFF_FOURCC('T','C','T','R')
+#define AI_LWO_TFAL  AI_IFF_FOURCC('T','F','A','L')
+#define AI_LWO_TVEL  AI_IFF_FOURCC('T','V','E','L')
+#define AI_LWO_TCLR  AI_IFF_FOURCC('T','C','L','R')
+#define AI_LWO_TVAL  AI_IFF_FOURCC('T','V','A','L')
+#define AI_LWO_TAMP  AI_IFF_FOURCC('T','A','M','P')
+#define AI_LWO_TIMG  AI_IFF_FOURCC('T','I','M','G')
+#define AI_LWO_TAAS  AI_IFF_FOURCC('T','A','A','S')
+#define AI_LWO_TREF  AI_IFF_FOURCC('T','R','E','F')
+#define AI_LWO_TOPC  AI_IFF_FOURCC('T','O','P','C')
+#define AI_LWO_SDAT  AI_IFF_FOURCC('S','D','A','T')
+#define AI_LWO_TFP0  AI_IFF_FOURCC('T','F','P','0')
+#define AI_LWO_TFP1  AI_IFF_FOURCC('T','F','P','1')
+
+
+/* top-level chunks */
+#define AI_LWO_LAYR  AI_IFF_FOURCC('L','A','Y','R')
+#define AI_LWO_TAGS  AI_IFF_FOURCC('T','A','G','S')
+#define AI_LWO_PNTS  AI_IFF_FOURCC('P','N','T','S')
+#define AI_LWO_BBOX  AI_IFF_FOURCC('B','B','O','X')
+#define AI_LWO_VMAP  AI_IFF_FOURCC('V','M','A','P')
+#define AI_LWO_VMAD  AI_IFF_FOURCC('V','M','A','D')
+#define AI_LWO_POLS  AI_IFF_FOURCC('P','O','L','S')
+#define AI_LWO_PTAG  AI_IFF_FOURCC('P','T','A','G')
+#define AI_LWO_ENVL  AI_IFF_FOURCC('E','N','V','L')
+#define AI_LWO_CLIP  AI_IFF_FOURCC('C','L','I','P')
+#define AI_LWO_SURF  AI_IFF_FOURCC('S','U','R','F')
+#define AI_LWO_DESC  AI_IFF_FOURCC('D','E','S','C')
+#define AI_LWO_TEXT  AI_IFF_FOURCC('T','E','X','T')
+#define AI_LWO_ICON  AI_IFF_FOURCC('I','C','O','N')
+
+/* polygon types */
+#define AI_LWO_FACE  AI_IFF_FOURCC('F','A','C','E')
+#define AI_LWO_CURV  AI_IFF_FOURCC('C','U','R','V')
+#define AI_LWO_PTCH  AI_IFF_FOURCC('P','T','C','H')
+#define AI_LWO_MBAL  AI_IFF_FOURCC('M','B','A','L')
+#define AI_LWO_BONE  AI_IFF_FOURCC('B','O','N','E')
+
+/* polygon tags */
+#define AI_LWO_SURF  AI_IFF_FOURCC('S','U','R','F')
+#define AI_LWO_PART  AI_IFF_FOURCC('P','A','R','T')
+#define AI_LWO_SMGP  AI_IFF_FOURCC('S','M','G','P')
+
+/* envelopes */
+#define AI_LWO_PRE   AI_IFF_FOURCC('P','R','E',' ')
+#define AI_LWO_POST  AI_IFF_FOURCC('P','O','S','T')
+#define AI_LWO_KEY   AI_IFF_FOURCC('K','E','Y',' ')
+#define AI_LWO_SPAN  AI_IFF_FOURCC('S','P','A','N')
+#define AI_LWO_TCB   AI_IFF_FOURCC('T','C','B',' ')
+#define AI_LWO_HERM  AI_IFF_FOURCC('H','E','R','M')
+#define AI_LWO_BEZI  AI_IFF_FOURCC('B','E','Z','I')
+#define AI_LWO_BEZ2  AI_IFF_FOURCC('B','E','Z','2')
+#define AI_LWO_LINE  AI_IFF_FOURCC('L','I','N','E')
+#define AI_LWO_STEP  AI_IFF_FOURCC('S','T','E','P')
+
+/* clips */
+#define AI_LWO_STIL  AI_IFF_FOURCC('S','T','I','L')
+#define AI_LWO_ISEQ  AI_IFF_FOURCC('I','S','E','Q')
+#define AI_LWO_ANIM  AI_IFF_FOURCC('A','N','I','M')
+#define AI_LWO_XREF  AI_IFF_FOURCC('X','R','E','F')
+#define AI_LWO_STCC  AI_IFF_FOURCC('S','T','C','C')
+#define AI_LWO_TIME  AI_IFF_FOURCC('T','I','M','E')
+#define AI_LWO_CONT  AI_IFF_FOURCC('C','O','N','T')
+#define AI_LWO_BRIT  AI_IFF_FOURCC('B','R','I','T')
+#define AI_LWO_SATR  AI_IFF_FOURCC('S','A','T','R')
+#define AI_LWO_HUE   AI_IFF_FOURCC('H','U','E',' ')
+#define AI_LWO_GAMM  AI_IFF_FOURCC('G','A','M','M')
+#define AI_LWO_NEGA  AI_IFF_FOURCC('N','E','G','A')
+#define AI_LWO_IFLT  AI_IFF_FOURCC('I','F','L','T')
+#define AI_LWO_PFLT  AI_IFF_FOURCC('P','F','L','T')
+
+/* surfaces */
+#define AI_LWO_COLR  AI_IFF_FOURCC('C','O','L','R')
+#define AI_LWO_LUMI  AI_IFF_FOURCC('L','U','M','I')
+#define AI_LWO_DIFF  AI_IFF_FOURCC('D','I','F','F')
+#define AI_LWO_SPEC  AI_IFF_FOURCC('S','P','E','C')
+#define AI_LWO_GLOS  AI_IFF_FOURCC('G','L','O','S')
+#define AI_LWO_REFL  AI_IFF_FOURCC('R','E','F','L')
+#define AI_LWO_RFOP  AI_IFF_FOURCC('R','F','O','P')
+#define AI_LWO_RIMG  AI_IFF_FOURCC('R','I','M','G')
+#define AI_LWO_RSAN  AI_IFF_FOURCC('R','S','A','N')
+#define AI_LWO_TRAN  AI_IFF_FOURCC('T','R','A','N')
+#define AI_LWO_TROP  AI_IFF_FOURCC('T','R','O','P')
+#define AI_LWO_TIMG  AI_IFF_FOURCC('T','I','M','G')
+#define AI_LWO_RIND  AI_IFF_FOURCC('R','I','N','D')
+#define AI_LWO_TRNL  AI_IFF_FOURCC('T','R','N','L')
+#define AI_LWO_BUMP  AI_IFF_FOURCC('B','U','M','P')
+#define AI_LWO_SMAN  AI_IFF_FOURCC('S','M','A','N')
+#define AI_LWO_SIDE  AI_IFF_FOURCC('S','I','D','E')
+#define AI_LWO_CLRH  AI_IFF_FOURCC('C','L','R','H')
+#define AI_LWO_CLRF  AI_IFF_FOURCC('C','L','R','F')
+#define AI_LWO_ADTR  AI_IFF_FOURCC('A','D','T','R')
+#define AI_LWO_SHRP  AI_IFF_FOURCC('S','H','R','P')
+#define AI_LWO_LINE  AI_IFF_FOURCC('L','I','N','E')
+#define AI_LWO_LSIZ  AI_IFF_FOURCC('L','S','I','Z')
+#define AI_LWO_ALPH  AI_IFF_FOURCC('A','L','P','H')
+#define AI_LWO_AVAL  AI_IFF_FOURCC('A','V','A','L')
+#define AI_LWO_GVAL  AI_IFF_FOURCC('G','V','A','L')
+#define AI_LWO_BLOK  AI_IFF_FOURCC('B','L','O','K')
+
+/* texture layer */
+#define AI_LWO_TYPE  AI_IFF_FOURCC('T','Y','P','E')
+#define AI_LWO_CHAN  AI_IFF_FOURCC('C','H','A','N')
+#define AI_LWO_NAME  AI_IFF_FOURCC('N','A','M','E')
+#define AI_LWO_ENAB  AI_IFF_FOURCC('E','N','A','B')
+#define AI_LWO_OPAC  AI_IFF_FOURCC('O','P','A','C')
+#define AI_LWO_FLAG  AI_IFF_FOURCC('F','L','A','G')
+#define AI_LWO_PROJ  AI_IFF_FOURCC('P','R','O','J')
+#define AI_LWO_STCK  AI_IFF_FOURCC('S','T','C','K')
+#define AI_LWO_TAMP  AI_IFF_FOURCC('T','A','M','P')
+
+/* texture coordinates */
+#define AI_LWO_TMAP  AI_IFF_FOURCC('T','M','A','P')
+#define AI_LWO_AXIS  AI_IFF_FOURCC('A','X','I','S')
+#define AI_LWO_CNTR  AI_IFF_FOURCC('C','N','T','R')
+#define AI_LWO_SIZE  AI_IFF_FOURCC('S','I','Z','E')
+#define AI_LWO_ROTA  AI_IFF_FOURCC('R','O','T','A')
+#define AI_LWO_OREF  AI_IFF_FOURCC('O','R','E','F')
+#define AI_LWO_FALL  AI_IFF_FOURCC('F','A','L','L')
+#define AI_LWO_CSYS  AI_IFF_FOURCC('C','S','Y','S')
+
+/* image map */
+#define AI_LWO_IMAP  AI_IFF_FOURCC('I','M','A','P')
+#define AI_LWO_IMAG  AI_IFF_FOURCC('I','M','A','G')
+#define AI_LWO_WRAP  AI_IFF_FOURCC('W','R','A','P')
+#define AI_LWO_WRPW  AI_IFF_FOURCC('W','R','P','W')
+#define AI_LWO_WRPH  AI_IFF_FOURCC('W','R','P','H')
+#define AI_LWO_VMAP  AI_IFF_FOURCC('V','M','A','P')
+#define AI_LWO_AAST  AI_IFF_FOURCC('A','A','S','T')
+#define AI_LWO_PIXB  AI_IFF_FOURCC('P','I','X','B')
+
+/* procedural */
+#define AI_LWO_PROC  AI_IFF_FOURCC('P','R','O','C')
+#define AI_LWO_COLR  AI_IFF_FOURCC('C','O','L','R')
+#define AI_LWO_VALU  AI_IFF_FOURCC('V','A','L','U')
+#define AI_LWO_FUNC  AI_IFF_FOURCC('F','U','N','C')
+#define AI_LWO_FTPS  AI_IFF_FOURCC('F','T','P','S')
+#define AI_LWO_ITPS  AI_IFF_FOURCC('I','T','P','S')
+#define AI_LWO_ETPS  AI_IFF_FOURCC('E','T','P','S')
+
+/* gradient */
+#define AI_LWO_GRAD  AI_IFF_FOURCC('G','R','A','D')
+#define AI_LWO_GRST  AI_IFF_FOURCC('G','R','S','T')
+#define AI_LWO_GREN  AI_IFF_FOURCC('G','R','E','N')
+#define AI_LWO_PNAM  AI_IFF_FOURCC('P','N','A','M')
+#define AI_LWO_INAM  AI_IFF_FOURCC('I','N','A','M')
+#define AI_LWO_GRPT  AI_IFF_FOURCC('G','R','P','T')
+#define AI_LWO_FKEY  AI_IFF_FOURCC('F','K','E','Y')
+#define AI_LWO_IKEY  AI_IFF_FOURCC('I','K','E','Y')
+
+/* shader */
+#define AI_LWO_SHDR  AI_IFF_FOURCC('S','H','D','R')
+#define AI_LWO_DATA  AI_IFF_FOURCC('D','A','T','A')
+
+
+// ---------------------------------------------------------------------------
+/** \brief Data structure for a face in a LWO file
+ */
+struct Face : public aiFace
+{
+	Face() : surfaceIndex(0) {}
+	unsigned int surfaceIndex;
+};
+
+
+
+// ---------------------------------------------------------------------------
+/** \brief Data structure for a LWO file texture
+ */
+struct Texture
+{
+	Texture()
+		: mStrength(1.0f)
+	{}
+
+	//! File name of the texture
+	std::string mFileName;
+
+	//! Strength of the texture
+	float mStrength;
+};
+
+
+// ---------------------------------------------------------------------------
+/** \brief Data structure for a LWO file surface (= material)
+ */
+struct Surface
+{
+	Surface()
+		: bDoubleSided			(false)
+		, mDiffuseValue			(1.0f)
+		, mSpecularValue		(1.0f)
+		, mTransparency			(0.0f)
+		, mGlossiness			(0.0f)
+		, mMaximumSmoothAngle	(90.0f)
+	{}
+
+	//! Name of the surface
+	std::string mName;
+
+	//! Color of the surface
+	aiColor3D mColor;
+
+	//! true for two-sided materials
+	bool bDoubleSided;
+
+	//! Various material parameters
+	float mDiffuseValue,mSpecularValue,mTransparency,mGlossiness;
+
+	//! Maximum angle between two adjacent triangles
+	//! that they can be smoothed
+	float mMaximumSmoothAngle;
+
+	//! Textures
+	Texture mColorTexture,mDiffuseTexture,mSpecularTexture,
+		mBumpTexture,mTransparencyTexture;
+};
+
+}}
+
+
+#endif // !! AI_LWO_FILEDATA_INCLUDED
+

+ 487 - 0
code/LWOLoader.cpp

@@ -0,0 +1,487 @@
+/*
+---------------------------------------------------------------------------
+Open Asset Import Library (ASSIMP)
+---------------------------------------------------------------------------
+
+Copyright (c) 2006-2008, ASSIMP Development 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 Development 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 Implementation of the LWO importer class */
+
+// internal headers
+#include "LWOLoader.h"
+#include "MaterialSystem.h"
+#include "ByteSwap.h"
+
+// public assimp headers
+#include "../include/IOStream.h"
+#include "../include/IOSystem.h"
+#include "../include/aiMesh.h"
+#include "../include/aiScene.h"
+#include "../include/aiAssert.h"
+#include "../include/DefaultLogger.h"
+
+// boost headers
+#include <boost/scoped_ptr.hpp>
+
+using namespace Assimp;
+
+
+// ------------------------------------------------------------------------------------------------
+// Constructor to be privately used by Importer
+LWOImporter::LWOImporter()
+{
+}
+
+// ------------------------------------------------------------------------------------------------
+// Destructor, private as well 
+LWOImporter::~LWOImporter()
+{
+	mFaces.clear();
+	mTempPoints.clear();
+	mSurfaces.clear();
+}
+
+// ------------------------------------------------------------------------------------------------
+// Returns whether the class can handle the format of the given file. 
+bool LWOImporter::CanRead( const std::string& pFile, IOSystem* pIOHandler) const
+{
+	// simple check of file extension is enough for the moment
+	std::string::size_type pos = pFile.find_last_of('.');
+	// no file extension - can't read
+	if( pos == std::string::npos)return false;
+	std::string extension = pFile.substr( pos);
+
+	if (extension.length() < 4)return false;
+	if (extension[0] != '.')return false;
+
+	if (extension[1] != 'l' && extension[1] != 'L')return false;
+	if (extension[2] != 'w' && extension[2] != 'W')return false;
+	if (extension[3] != 'o' && extension[3] != 'O')return false;
+
+	return true;
+}
+// ------------------------------------------------------------------------------------------------
+// Imports the given file into the given scene structure. 
+void LWOImporter::InternReadFile( const std::string& pFile, 
+	aiScene* pScene, 
+	IOSystem* pIOHandler)
+{
+	boost::scoped_ptr<IOStream> file( pIOHandler->Open( pFile, "rb"));
+
+	// Check whether we can read from the file
+	if( file.get() == NULL)
+		throw new ImportErrorException( "Failed to open LWO file " + pFile + ".");
+
+	if((this->fileSize = (unsigned int)file->FileSize()) < 12)
+		throw new ImportErrorException("LWO: The file is too small to contain the IFF header");
+
+	// allocate storage and copy the contents of the file to a memory buffer
+	std::vector< uint8_t > mBuffer(fileSize);
+	file->Read( &mBuffer[0], 1, fileSize);
+	this->pScene = pScene;
+
+	// determine the type of the file
+	uint32_t fileType;
+	const char* sz = IFF::ReadHeader(&mBuffer[0],fileType);
+	if (sz)throw new ImportErrorException(sz);
+
+	mFileBuffer = &mBuffer[0] + 12;
+	fileSize -= 12;
+
+	try 
+	{
+		// old lightwave file format (prior to v6)
+		if (AI_LWO_FOURCC_LWOB == fileType)
+			this->LoadLWOBFile();
+		// new lightwave format
+		else if (AI_LWO_FOURCC_LWO2 == fileType)
+			this->LoadLWO2File();
+		// we don't know this format
+		else 
+		{
+			char szBuff[5];
+			szBuff[0] = (char)(fileType >> 24u);
+			szBuff[1] = (char)(fileType >> 16u);
+			szBuff[2] = (char)(fileType >> 8u);
+			szBuff[3] = (char)(fileType);
+			throw new ImportErrorException(std::string("Unknown LWO sub format: ") + szBuff);
+		}
+
+		// generate a default surface if necessary
+		if (mSurfaces.empty())
+			mSurfaces.push_back(LWO::Surface());
+
+		// now sort all faces by the surfaces assigned to them
+		typedef std::vector<unsigned int> SortedRep;
+		std::vector<SortedRep> pSorted(mSurfaces.size());
+
+		unsigned int i = 0;
+		for (FaceList::iterator it = mFaces.begin(), end = mFaces.end();
+			it != end;++it,++i)
+		{
+			if ((*it).surfaceIndex >= mSurfaces.size())
+			{
+				DefaultLogger::get()->warn("LWO: Invalid face surface index");
+				(*it).surfaceIndex = mSurfaces.size()-1;
+			}
+			pSorted[(*it).surfaceIndex].push_back(i);
+		}
+
+		// now generate output meshes
+		for (unsigned int p = 0; p < mSurfaces.size();++p)
+			if (!pSorted[p].empty())pScene->mNumMeshes++;
+
+		if (!(pScene->mNumMaterials = pScene->mNumMeshes))
+			throw new ImportErrorException("LWO: There are no meshes");
+
+		pScene->mMeshes = new aiMesh*[pScene->mNumMeshes];
+		pScene->mMaterials = new aiMaterial*[pScene->mNumMaterials];
+		for (unsigned int p = 0,i = 0;i < mSurfaces.size();++i)
+		{
+			SortedRep& sorted = pSorted[i];
+			if (sorted.empty())continue;
+
+			// generate the mesh 
+			aiMesh* mesh = pScene->mMeshes[p] = new aiMesh();
+			mesh->mNumFaces = sorted.size();
+
+			for (SortedRep::const_iterator it = sorted.begin(), end = sorted.end();
+				it != end;++it)
+			{
+				mesh->mNumVertices += mFaces[*it].mNumIndices;
+			}
+
+			mesh->mVertices = new aiVector3D[mesh->mNumVertices];
+			mesh->mFaces = new aiFace[mesh->mNumFaces];
+			mesh->mMaterialIndex = p;
+
+			// now convert all faces
+			unsigned int vert = 0;
+			for (SortedRep::const_iterator it = sorted.begin(), end = sorted.end();
+				it != end;++it)
+			{
+				LWO::Face& face = mFaces[*it];
+
+				// copy all vertices
+				for (unsigned int q = 0; q  < face.mNumIndices;++q)
+				{
+					*mesh->mVertices++ = mTempPoints[face.mIndices[q]];
+					face.mIndices[q] = vert++;
+				}
+
+				mesh->mFaces->mIndices = face.mIndices;
+				mesh->mFaces->mNumIndices = face.mNumIndices;
+				face.mIndices = NULL; // make sure it won't be deleted
+
+				mesh->mFaces++;
+			}
+			mesh->mFaces -= mesh->mNumFaces;
+			mesh->mVertices -= mesh->mNumVertices;
+
+			// generate the corresponding material
+			MaterialHelper* pcMat = new MaterialHelper();
+			pScene->mMaterials[p] = pcMat;
+
+			// todo
+
+			++p;
+		}
+	}
+	// make sure the arrays are cleaned up ...
+	catch (ImportErrorException* ex)
+	{
+		this->~LWOImporter();
+		throw ex;
+	}
+	this->~LWOImporter();
+}
+// ------------------------------------------------------------------------------------------------
+void LWOImporter::CountVertsAndFaces(unsigned int& verts, unsigned int& faces,
+	LE_NCONST uint8_t*& cursor, const uint8_t* const end, unsigned int max)
+{
+	while (cursor < end && max--)
+	{
+		uint16_t numIndices = *((uint16_t*)cursor);cursor+=2;
+		verts += numIndices;faces++;
+		cursor += numIndices*2;
+		int16_t surface = *((uint16_t*)cursor);cursor+=2;
+		if (surface < 0)
+		{
+			// there are detail polygons
+			numIndices = *((uint16_t*)cursor);cursor+=2;
+			CountVertsAndFaces(verts,faces,cursor,end,numIndices);
+		}
+	}
+}
+// ------------------------------------------------------------------------------------------------
+void LWOImporter::CopyFaceIndices(LWOImporter::FaceList::iterator& it,LE_NCONST uint8_t*& cursor, 
+	const uint8_t* const end, unsigned int max)
+{
+	while (cursor < end && max--)
+	{
+		LWO::Face& face = *it;++it;
+		face.mNumIndices = *((uint16_t*)cursor);
+		if (cursor + face.mNumIndices*2 + 4 >= end)break;
+		face.mIndices = new unsigned int[face.mNumIndices];
+		for (unsigned int i = 0; i < face.mNumIndices;++i)
+		{
+			face.mIndices[i] = *((uint16_t*)(cursor+=2));
+			if (face.mIndices[i] >= mTempPoints.size())
+			{
+				face.mIndices[i] = mTempPoints.size()-1;
+				DefaultLogger::get()->warn("LWO: Face index is out of range");
+			}
+		}
+		cursor+=2;
+		int16_t surface = *((uint16_t*)cursor);cursor+=2;
+		if (surface < 0)
+		{
+			surface *= -1;
+
+			// there are detail polygons
+			uint16_t numPolygons = *((uint16_t*)cursor);cursor+=2;
+			if (cursor < end)CopyFaceIndices(it,cursor,end,numPolygons);
+		}
+		face.surfaceIndex = surface-1;
+	}
+}
+// ------------------------------------------------------------------------------------------------
+void LWOImporter::LoadLWOBSurface(unsigned int size)
+{
+	uint32_t iCursor = 0;
+	mSurfaces.push_back( LWO::Surface () );
+	LWO::Surface& surf = mSurfaces.back();
+	LWO::Texture* pTex = NULL;
+
+	// at first we'll need to read the name of the surface
+	const uint8_t* sz = mFileBuffer;
+	while (*mFileBuffer)
+	{
+		if (++iCursor > size)throw new ImportErrorException("LWOB: Invalid file, surface name is too long");
+		++mFileBuffer;
+	}
+	unsigned int len = unsigned int (mFileBuffer-sz);
+	surf.mName = std::string((const char*)sz,len);
+	mFileBuffer += 1-(len & 1); // skip one byte if the length of the string is odd
+	while (true)
+	{
+		if ((iCursor += sizeof(IFF::ChunkHeader)) > size)break;
+		LE_NCONST IFF::ChunkHeader* head = (LE_NCONST IFF::ChunkHeader*)mFileBuffer;
+		AI_LSWAP4(head->length);
+		AI_LSWAP4(head->type);
+		if ((iCursor += head->length) > size)
+		{
+			throw new ImportErrorException("LWOB: Invalid file, the size attribute of "
+				"a surface sub chunk points behind the end of the file");
+		}
+		mFileBuffer += sizeof(IFF::ChunkHeader);
+		switch (head->type)
+		{
+			// diffuse color
+		case AI_LWO_COLR:
+			{
+				if (head->length < 3)
+				{
+					DefaultLogger::get()->warn("LWO: COLR chunk is expected to be at least 3 bytes in size");
+					break;
+				}
+				surf.mColor.r = *mFileBuffer++ / 255.0f;
+				surf.mColor.g = *mFileBuffer++ / 255.0f;
+				surf.mColor.b = *mFileBuffer   / 255.0f;
+				break;
+			}
+			// diffuse strength ... hopefully
+		case AI_LWO_DIFF:
+			{
+				AI_LSWAP2(mFileBuffer);
+				surf.mDiffuseValue = *((int16_t*)mFileBuffer) / 255.0f;
+				break;
+			}
+			// specular strength ... hopefully
+		case AI_LWO_SPEC:
+			{
+				AI_LSWAP2(mFileBuffer);
+				surf.mSpecularValue = *((int16_t*)mFileBuffer) / 255.0f;
+				break;
+			}
+		// transparency
+		case AI_LWO_TRAN:
+			{
+				AI_LSWAP2(mFileBuffer);
+				surf.mTransparency = *((int16_t*)mFileBuffer) / 255.0f;
+				break;
+			}
+		// glossiness
+		case AI_LWO_GLOS:
+			{
+				AI_LSWAP2(mFileBuffer);
+				surf.mGlossiness = float(*((int16_t*)mFileBuffer));
+				break;
+			}
+		// color texture
+		case AI_LWO_CTEX:
+			{
+				pTex = &surf.mColorTexture;
+				break;
+			}
+		// diffuse texture
+		case AI_LWO_DTEX:
+			{
+				pTex = &surf.mDiffuseTexture;
+				break;
+			}
+		// specular texture
+		case AI_LWO_STEX:
+			{
+				pTex = &surf.mSpecularTexture;
+				break;
+			}
+		// bump texture
+		case AI_LWO_BTEX:
+			{
+				pTex = &surf.mBumpTexture;
+				break;
+			}
+		// transparency texture
+		case AI_LWO_TTEX:
+			{
+				pTex = &surf.mTransparencyTexture;
+				break;
+			}
+			// texture path
+		case AI_LWO_TIMG:
+			{
+				if (pTex)
+				{
+					unsigned int iCursor = 0;
+					while (*mFileBuffer)
+					{
+						if (++iCursor > head->length)
+						{
+							DefaultLogger::get()->warn("LWOB: Invalid file, texture name (TIMG) is too long");
+							break;
+						}
+						++mFileBuffer;
+					}
+					unsigned int len = unsigned int (mFileBuffer-sz);
+					pTex->mFileName = std::string((const char*)sz,len);
+				}
+				else DefaultLogger::get()->warn("LWOB: TIMG tag was encuntered although "
+					"there was no xTEX tag before");
+				break;
+			}
+		// texture strength
+		case AI_LWO_TVAL:
+			{
+				if (pTex)pTex->mStrength = *mFileBuffer / 255.0f;
+				else DefaultLogger::get()->warn("LWOB: TVAL tag was encuntered "
+					"although there was no xTEX tag before");
+				break;
+			}
+		}
+		mFileBuffer += head->length;
+	}
+}
+// ------------------------------------------------------------------------------------------------
+void LWOImporter::LoadLWOBFile()
+{
+	uint32_t iCursor = 0;
+	while (true)
+	{
+		if ((iCursor += sizeof(IFF::ChunkHeader)) > this->fileSize)break;
+		LE_NCONST IFF::ChunkHeader* head = (LE_NCONST IFF::ChunkHeader*)mFileBuffer;
+		AI_LSWAP4(head->length);
+		AI_LSWAP4(head->type);
+		if ((iCursor += head->length) > this->fileSize)
+		{
+			//throw new ImportErrorException("LWOB: Invalid file, the size attribute of "
+			//	"a chunk points behind the end of the file");
+			break;
+		}
+		mFileBuffer += sizeof(IFF::ChunkHeader);
+		switch (head->type)
+		{
+			// vertex list
+		case AI_LWO_PNTS:
+			{
+				mTempPoints.resize( head->length / 12 );
+#ifndef AI_BUILD_BIG_ENDIAN
+				for (unsigned int i = 0; i < head->length>>2;++i)
+					ByteSwap::Swap4( mFileBuffer + (i << 2));
+#endif
+				::memcpy(&mTempPoints[0],mFileBuffer,head->length);
+				break;
+			}
+			// face list
+		case AI_LWO_POLS:
+			{
+				// first find out how many faces and vertices we'll finally need
+				const uint8_t* const end = mFileBuffer + head->length;
+				LE_NCONST uint8_t* cursor = mFileBuffer;
+
+#ifndef AI_BUILD_BIG_ENDIAN
+				while (cursor < end)ByteSwap::Swap2(cursor++);
+				cursor = mFileBuffer;
+#endif
+
+				unsigned int iNumFaces = 0,iNumVertices = 0;
+				CountVertsAndFaces(iNumVertices,iNumFaces,cursor,end);
+
+				// allocate the output array and copy face indices
+				if (iNumFaces)
+				{
+					this->mTempPoints.resize(iNumVertices);
+					this->mFaces.resize(iNumFaces);
+					FaceList::iterator it = this->mFaces.begin();
+					CopyFaceIndices(it,mFileBuffer,end);
+				}
+				break;
+			}
+			// surface chunk
+		case AI_LWO_SURF:
+			{
+				LoadLWOBSurface(head->length);
+				break;
+			}
+		}
+		mFileBuffer += head->length;
+	}
+}
+// ------------------------------------------------------------------------------------------------
+void LWOImporter::LoadLWO2File()
+{
+}

+ 158 - 0
code/LWOLoader.h

@@ -0,0 +1,158 @@
+/*
+Open Asset Import Library (ASSIMP)
+----------------------------------------------------------------------
+
+Copyright (c) 2006-2008, ASSIMP Development 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 Development 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 Declaration of the LWO importer class. */
+#ifndef AI_LWOLOADER_H_INCLUDED
+#define AI_LWOLOADER_H_INCLUDED
+
+#include "../include/aiTypes.h"
+
+#include "BaseImporter.h"
+#include "LWOFileData.h"
+
+#include <vector>
+
+namespace Assimp	{
+using namespace LWO;
+
+// ---------------------------------------------------------------------------
+/** Clas to load LWO files
+*/
+class LWOImporter : public BaseImporter
+{
+	friend class Importer;
+
+protected:
+	/** Constructor to be privately used by Importer */
+	LWOImporter();
+
+	/** Destructor, private as well */
+	~LWOImporter();
+
+public:
+
+	// -------------------------------------------------------------------
+	/** Returns whether the class can handle the format of the given file. 
+	* See BaseImporter::CanRead() for details.	*/
+	bool CanRead( const std::string& pFile, IOSystem* pIOHandler) const;
+
+protected:
+
+	// -------------------------------------------------------------------
+	/** Called by Importer::GetExtensionList() for each loaded importer.
+	 * See BaseImporter::GetExtensionList() for details
+	 */
+	void GetExtensionList(std::string& append)
+	{
+		append.append("*.lwo");
+	}
+
+	// -------------------------------------------------------------------
+	/** Imports the given file into the given scene structure. 
+	* See BaseImporter::InternReadFile() for details
+	*/
+	void InternReadFile( const std::string& pFile, aiScene* pScene, 
+		IOSystem* pIOHandler);
+
+
+	// -------------------------------------------------------------------
+	/** Loads a LWO file in the older LWOB format (LW < 6)
+	*/
+	void LoadLWOBFile();
+
+	// -------------------------------------------------------------------
+	/** Loads a LWO file in the newer LWO2 format (LW >= 6)
+	*/
+	void LoadLWO2File();
+
+	// -------------------------------------------------------------------
+	/** Loads a surface chunk from an LWOB file
+	*/
+	void LoadLWOBSurface(unsigned int size);
+
+
+	typedef std::vector<aiVector3D> PointList;
+	typedef std::vector<LWO::Face> FaceList;
+	typedef std::vector<LWO::Surface> SurfaceList;
+
+private:
+
+	// -------------------------------------------------------------------
+	/** Count vertices and faces in a LWOB file
+	*/
+	void CountVertsAndFaces(unsigned int& verts, 
+		unsigned int& faces,
+		LE_NCONST uint8_t*& cursor, 
+		const uint8_t* const end,
+		unsigned int max = 0xffffffff);
+
+	// -------------------------------------------------------------------
+	/** Read vertices and faces in a LWOB file
+	*/
+	void CopyFaceIndices(FaceList::iterator& it,
+		LE_NCONST uint8_t*& cursor, 
+		const uint8_t* const end, 
+		unsigned int max = 0xffffffff);
+
+protected:
+
+	/** Temporary point list from the file */
+	PointList mTempPoints;
+
+	/** Temporary face list from the file*/
+	FaceList mFaces;
+
+	/** Temporary surface list from the file */
+	SurfaceList mSurfaces;
+
+	/** file buffer */
+	LE_NCONST uint8_t* mFileBuffer;
+
+	/** Size of the file, in bytes */
+	unsigned int fileSize;
+
+	/** Output scene */
+	aiScene* pScene;
+
+};
+
+} // end of namespace Assimp
+
+#endif // AI_LWOIMPORTER_H_INCLUDED

+ 1 - 0
code/STLLoader.cpp

@@ -347,6 +347,7 @@ bool STLImporter::LoadBinaryFile()
 		sz += sizeof(aiVector3D);
 		*(vn+1) = *vn;
 		*(vn+2) = *vn;
+		vn += 3;
 
 		*vp++ = *((aiVector3D*)sz);
 		sz += sizeof(aiVector3D);

+ 24 - 0
workspaces/vc8/assimp.vcproj

@@ -734,6 +734,10 @@
 				RelativePath="..\..\code\Hash.h"
 				>
 			</File>
+			<File
+				RelativePath="..\..\code\IFF.h"
+				>
+			</File>
 			<File
 				RelativePath="..\..\code\ImproveCacheLocality.h"
 				>
@@ -1042,6 +1046,18 @@
 					>
 				</File>
 			</Filter>
+			<Filter
+				Name="LWO"
+				>
+				<File
+					RelativePath="..\..\code\LWOFileData.h"
+					>
+				</File>
+				<File
+					RelativePath="..\..\code\LWOLoader.h"
+					>
+				</File>
+			</Filter>
 		</Filter>
 		<Filter
 			Name="sources"
@@ -1318,6 +1334,14 @@
 					>
 				</File>
 			</Filter>
+			<Filter
+				Name="LWO"
+				>
+				<File
+					RelativePath="..\..\code\LWOLoader.cpp"
+					>
+				</File>
+			</Filter>
 		</Filter>
 		<Filter
 			Name="doc"