[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [49795] branches/soc-2012-bratwurst/extern /assimp: - bf_assimp: merge https://github.com/acgessler/ assimp-gsoc2012-fbx - support for binary fbx files, arbitrary rotation orders, more supported camera and light options, improved error reporting, lots of bugfixes.
Alexander Gessler
alexander.gessler at gmx.net
Sat Aug 11 05:22:22 CEST 2012
Revision: 49795
http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=49795
Author: aramis_acg
Date: 2012-08-11 03:22:18 +0000 (Sat, 11 Aug 2012)
Log Message:
-----------
- bf_assimp: merge https://github.com/acgessler/assimp-gsoc2012-fbx - support for binary fbx files, arbitrary rotation orders, more supported camera and light options, improved error reporting, lots of bugfixes.
Modified Paths:
--------------
branches/soc-2012-bratwurst/extern/assimp/CMakeLists.txt
branches/soc-2012-bratwurst/extern/assimp/code/FBXAnimation.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXConverter.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXDeformer.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXDocument.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXDocument.h
branches/soc-2012-bratwurst/extern/assimp/code/FBXDocumentUtil.h
branches/soc-2012-bratwurst/extern/assimp/code/FBXImporter.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXMeshGeometry.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXModel.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXNodeAttribute.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXParser.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXParser.h
branches/soc-2012-bratwurst/extern/assimp/code/FBXProperties.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXTokenizer.h
branches/soc-2012-bratwurst/extern/assimp/code/FBXUtil.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXUtil.h
Added Paths:
-----------
branches/soc-2012-bratwurst/extern/assimp/code/FBXBinaryTokenizer.cpp
branches/soc-2012-bratwurst/extern/assimp/code/FBXDocumentUtil.cpp
Modified: branches/soc-2012-bratwurst/extern/assimp/CMakeLists.txt
===================================================================
--- branches/soc-2012-bratwurst/extern/assimp/CMakeLists.txt 2012-08-11 01:17:16 UTC (rev 49794)
+++ branches/soc-2012-bratwurst/extern/assimp/CMakeLists.txt 2012-08-11 03:22:18 UTC (rev 49795)
@@ -306,6 +306,8 @@
code/FBXNodeAttribute.cpp
code/FBXDeformer.cpp
code/FBXAnimation.cpp
+ code/FBXBinaryTokenizer.cpp
+ code/FBXDocumentUtil.cpp
)
Modified: branches/soc-2012-bratwurst/extern/assimp/code/FBXAnimation.cpp
===================================================================
--- branches/soc-2012-bratwurst/extern/assimp/code/FBXAnimation.cpp 2012-08-11 01:17:16 UTC (rev 49794)
+++ branches/soc-2012-bratwurst/extern/assimp/code/FBXAnimation.cpp 2012-08-11 03:22:18 UTC (rev 49795)
@@ -66,8 +66,8 @@
const Element& KeyTime = GetRequiredElement(sc,"KeyTime");
const Element& KeyValueFloat = GetRequiredElement(sc,"KeyValueFloat");
- ReadVectorDataArray(keys, KeyTime);
- ReadVectorDataArray(values, KeyValueFloat);
+ ParseVectorDataArray(keys, KeyTime);
+ ParseVectorDataArray(values, KeyValueFloat);
if(keys.size() != values.size()) {
DOMError("the number of key times does not match the number of keyframe values",&KeyTime);
@@ -80,12 +80,12 @@
const Element* KeyAttrDataFloat = sc["KeyAttrDataFloat"];
if(KeyAttrDataFloat) {
- ReadVectorDataArray(attributes, *KeyAttrDataFloat);
+ ParseVectorDataArray(attributes, *KeyAttrDataFloat);
}
const Element* KeyAttrFlags = sc["KeyAttrFlags"];
if(KeyAttrFlags) {
- ReadVectorDataArray(flags, *KeyAttrFlags);
+ ParseVectorDataArray(flags, *KeyAttrFlags);
}
}
Added: branches/soc-2012-bratwurst/extern/assimp/code/FBXBinaryTokenizer.cpp
===================================================================
--- branches/soc-2012-bratwurst/extern/assimp/code/FBXBinaryTokenizer.cpp (rev 0)
+++ branches/soc-2012-bratwurst/extern/assimp/code/FBXBinaryTokenizer.cpp 2012-08-11 03:22:18 UTC (rev 49795)
@@ -0,0 +1,385 @@
+/*
+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 FBXBinaryTokenizer.cpp
+ * @brief Implementation of a fake lexer for binary fbx files -
+ * we emit tokens so the parser needs almost no special handling
+ * for binary files.
+ */
+#include "AssimpPCH.h"
+
+#ifndef ASSIMP_BUILD_NO_FBX_IMPORTER
+
+#include "FBXTokenizer.h"
+#include "FBXUtil.h"
+
+namespace Assimp {
+namespace FBX {
+
+
+// ------------------------------------------------------------------------------------------------
+Token::Token(const char* sbegin, const char* send, TokenType type, unsigned int offset)
+ : sbegin(sbegin)
+ , send(send)
+ , type(type)
+ , line(offset)
+ , column(BINARY_MARKER)
+#ifdef DEBUG
+ , contents(sbegin, static_cast<size_t>(send-sbegin))
+#endif
+{
+ ai_assert(sbegin);
+ ai_assert(send);
+
+ // binary tokens may have zero length because they are sometimes dummies
+ // inserted by TokenizeBinary()
+ ai_assert(send >= sbegin);
+}
+
+
+namespace {
+
+// ------------------------------------------------------------------------------------------------
+// signal tokenization error, this is always unrecoverable. Throws DeadlyImportError.
+void TokenizeError(const std::string& message, unsigned int offset)
+{
+ throw DeadlyImportError(Util::AddOffset("FBX-Tokenize",message,offset));
+}
+
+
+// ------------------------------------------------------------------------------------------------
+uint32_t Offset(const char* begin, const char* cursor)
+{
+ ai_assert(begin <= cursor);
+ return static_cast<unsigned int>(cursor - begin);
+}
+
+
+// ------------------------------------------------------------------------------------------------
+void TokenizeError(const std::string& message, const char* begin, const char* cursor)
+{
+ TokenizeError(message, Offset(begin, cursor));
+}
+
+
+// ------------------------------------------------------------------------------------------------
+uint32_t ReadWord(const char* input, const char*& cursor, const char* end)
+{
+ if(Offset(cursor, end) < 4) {
+ TokenizeError("cannot ReadWord, out of bounds",input, cursor);
+ }
+
+ uint32_t word = *reinterpret_cast<const uint32_t*>(cursor);
+ AI_SWAP4(word);
+
+ cursor += 4;
+
+ return word;
+}
+
+
+// ------------------------------------------------------------------------------------------------
+uint8_t ReadByte(const char* input, const char*& cursor, const char* end)
+{
+ if(Offset(cursor, end) < 1) {
+ TokenizeError("cannot ReadByte, out of bounds",input, cursor);
+ }
+
+ uint8_t word = *reinterpret_cast<const uint8_t*>(cursor);
+ ++cursor;
+
+ return word;
+}
+
+
+// ------------------------------------------------------------------------------------------------
+unsigned int ReadString(const char*& sbegin_out, const char*& send_out, const char* input, const char*& cursor, const char* end,
+ bool long_length = false,
+ bool allow_null = false)
+{
+ const uint32_t len_len = long_length ? 4 : 1;
+ if(Offset(cursor, end) < len_len) {
+ TokenizeError("cannot ReadString, out of bounds reading length",input, cursor);
+ }
+
+ const uint32_t length = long_length ? ReadWord(input, cursor, end) : ReadByte(input, cursor, end);
+
+ if (Offset(cursor, end) < length) {
+ TokenizeError("cannot ReadString, length is out of bounds",input, cursor);
+ }
+
+ sbegin_out = cursor;
+ cursor += length;
+
+ send_out = cursor;
+
+ if(!allow_null) {
+ for (unsigned int i = 0; i < length; ++i) {
+ if(sbegin_out[i] == '\0') {
+ TokenizeError("failed ReadString, unexpected NUL character in string",input, cursor);
+ }
+ }
+ }
+
+ return length;
+}
+
+
+
+// ------------------------------------------------------------------------------------------------
+void ReadData(const char*& sbegin_out, const char*& send_out, const char* input, const char*& cursor, const char* end)
+{
+ if(Offset(cursor, end) < 1) {
+ TokenizeError("cannot ReadData, out of bounds reading length",input, cursor);
+ }
+
+ const char type = *cursor;
+ sbegin_out = cursor++;
+
+ switch(type)
+ {
+ // 1 bit bool flag (yes/no)
+ case 'C':
+ cursor += 1;
+ break;
+
+ // 32 bit int
+ case 'I':
+ // <- fall thru
+
+ // float
+ case 'F':
+ cursor += 4;
+ break;
+
+ // double
+ case 'D':
+ cursor += 8;
+ break;
+
+ // 64 bit int
+ case 'L':
+ cursor += 8;
+ break;
+
+ // note: do not write cursor += ReadWord(...cursor) as this would be UB
+
+ // raw binary data
+ case 'R': {
+ const uint32_t length = ReadWord(input, cursor, end);
+ cursor += length;
+ break;
+ }
+
+ // array of *
+ case 'f':
+ case 'd':
+ case 'l':
+ case 'i': {
+
+ const uint32_t length = ReadWord(input, cursor, end);
+ const uint32_t encoding = ReadWord(input, cursor, end);
+
+ const uint32_t comp_len = ReadWord(input, cursor, end);
+
+ // compute length based on type and check against the stored value
+ if(encoding == 0) {
+ uint32_t stride;
+ switch(type)
+ {
+ case 'f':
+ case 'i':
+ stride = 4;
+ break;
+
+ case 'd':
+ case 'l':
+ stride = 8;
+ break;
+
+ default:
+ ai_assert(false);
+ };
+ if(length * stride != comp_len) {
+ TokenizeError("cannot ReadData, calculated data stride differs from what the file claims",input, cursor);
+ }
+ }
+ // zip/deflate algorithm (encoding==1)? take given length. anything else? die
+ else if (encoding != 1) {
+ TokenizeError("cannot ReadData, unknown encoding",input, cursor);
+ }
+ cursor += comp_len;
+ break;
+ }
+
+ // string
+ case 'S': {
+ const char* sb, *se;
+ // 0 characters can legally happen in such strings
+ ReadString(sb, se, input, cursor, end, true, true);
+ break;
+ }
+ default:
+ TokenizeError("cannot ReadData, unexpected type code: " + std::string(&type, 1),input, cursor);
+ }
+
+ if(cursor > end) {
+ TokenizeError("cannot ReadData, the remaining size is too small for the data type: " + std::string(&type, 1),input, cursor);
+ }
+
+ // the type code is contained in the returned range
+ send_out = cursor;
+}
+
+
+// ------------------------------------------------------------------------------------------------
+bool ReadScope(TokenList& output_tokens, const char* input, const char*& cursor, const char* end)
+{
+ // the first word contains the offset at which this block ends
+ const uint32_t end_offset = ReadWord(input, cursor, end);
+
+ // we may get 0 if reading reached the end of the file -
+ // fbx files have a mysterious extra footer which I don't know
+ // how to extract any information from, but at least it always
+ // starts with a 0.
+ if(!end_offset) {
+ return false;
+ }
+
+ if(end_offset > Offset(input, end)) {
+ TokenizeError("block offset is out of range",input, cursor);
+ }
+ else if(end_offset < Offset(input, cursor)) {
+ TokenizeError("block offset is negative out of range",input, cursor);
+ }
+
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list