/* ================ SkipUnknown ================ */ static bool SkipUnknown( Lexer &lexer ) { const Token *token; const char *p; int line = lexer.GetLine(); while ( (token = lexer.ReadToken()) != OG_NULL ) { p = token->GetString(); if ( !p || !*p ) continue; if ( line != lexer.GetLine() ) { lexer.UnreadToken(); return true; } if ( String::Icmp( p, "{" ) == 0 ) { if ( !lexer.GotoNextLine() ) return false; while( lexer.CheckToken("*") ) { if ( !SkipUnknown(lexer) ) return false; } lexer.FindToken("}"); return lexer.GotoNextLine(); } } return false; }
/* ================ ReadGeoMObject ================ */ static void ReadGeoMObject( Lexer &lexer, ListEx<aseMesh> &myMeshList ) { lexer.ExpectToken("{"); const char *p; const Token *token; String name; while ( (token = lexer.ReadToken()) != OG_NULL ) { p = token->GetString(); if ( !p || !*p ) continue; if ( String::Icmp( p, "}" ) == 0 ) return; if ( String::Icmp( p, "*" ) != 0 ) lexer.Error( Format("expected *, got '$*'") << p ); if ( lexer.CheckToken( "NODE_NAME" ) ) name = lexer.ReadString(); else if ( lexer.CheckToken( "MESH" ) ) { aseMesh *inMesh = &myMeshList.Alloc(); inMesh->name = name; ReadMesh( lexer, inMesh ); } else if ( !SkipUnknown(lexer) ) break; } }
/* ================ DeclParser::Parse ================ */ void DeclParser::Parse( Lexer &lexer ) { Dict *resultDict = OG_NULL; bool getKeyValue = false; int index; const Token *token; String key, value; const char *p; while ( (token = lexer.ReadToken()) != OG_NULL ) { p = token->GetString(); if ( p ) { if ( *p == '\0' ) lexer.Error("Unexpected Empty Token"); if ( !getKeyValue ) { index = declTypes.Find(p); if ( index != -1 ) { value = lexer.ReadString(); if ( value.IsEmpty() ) lexer.Error("Empty name!"); DictEx<Dict> &result = declTypes[index]->declList; index = result.Find(p); if ( index == -1 ) resultDict = &result[p]; else { resultDict = &result[index]; resultDict->Clear(); } } else { resultDict = OG_NULL; lexer.Warning( Format("Unknown decl Type '$*'") << p ); } lexer.ExpectToken("{"); getKeyValue = true; } else { if ( *p == '}' ) getKeyValue = false; else if ( resultDict ) { key = p; (*resultDict).Set( key.c_str(), lexer.ReadString() ); } } } } if ( getKeyValue ) throw LexerError( LexerError::END_OF_FILE ); }
/* ================ ReadMaterial ================ */ static void ReadMaterial( Lexer &lexer ) { lexer.ReadInt(); lexer.ExpectToken("{"); const char *p; const Token *token; while ( (token = lexer.ReadToken()) != OG_NULL ) { p = token->GetString(); if ( !p || !*p ) continue; if ( String::Icmp( p, "}" ) == 0 ) return; if ( String::Icmp( p, "*" ) != 0 ) lexer.Error( Format("expected *, got '$*'") << p ); //! @todo Finish this if ( !SkipUnknown(lexer) ) break; } }
/* ================ ReadMaterialList ================ */ static void ReadMaterialList( Lexer &lexer ) { lexer.ExpectToken("{"); const char *p; const Token *token; int numMaterials; while ( (token = lexer.ReadToken()) != OG_NULL ) { p = token->GetString(); if ( !p || !*p ) continue; if ( String::Icmp( p, "}" ) == 0 ) return; if ( String::Icmp( p, "*" ) != 0 ) lexer.Error( Format("expected *, got '$*'") << p ); if ( lexer.CheckToken( "MATERIAL_COUNT" ) ) numMaterials = lexer.ReadInt(); else if ( lexer.CheckToken( "MATERIAL" ) ) ReadMaterial( lexer ); else if ( !SkipUnknown(lexer) ) break; } }
/* ================ DeclParser::MakeBinary ================ */ bool DeclParser::MakeBinary( const char *filename ) { if ( commonFS == OG_NULL ) return false; Lexer lexer; if ( !lexer.LoadFile( filename ) ) return false; File *f = commonFS->OpenWrite( Format( "$*.bin" ) << filename ); if ( !f ) return false; try { f->Write( DECL_DESCRIPTOR_STR, DECL_DESCRIPTOR_LENGTH ); Dict dict; bool getKeyValue = false; const Token *token; String key, value; String str; const char *p; while ( (token = lexer.ReadToken()) != OG_NULL ) { //! @todo maybe token should be stored as String, so we don't have to recalc len/bytelen p = token->GetString(); if ( p ) { if ( *p == '\0' ) { lexer.Error("Unexpected Empty Token"); return false; } if ( !getKeyValue ) { str = p; str.WriteToFile( f ); value = lexer.ReadString(); if ( value.IsEmpty() ) { lexer.Error("Empty name!"); return false; } value.WriteToFile( f ); lexer.ExpectToken("{"); getKeyValue = true; } else { if ( *p == '}' ) { getKeyValue = false; dict.WriteToFile( f ); dict.Clear(); } else { key = p; dict.Set( key.c_str(), lexer.ReadString() ); } } } } if ( getKeyValue ) { lexer.Error("Unexpected End Of File"); return false; } return true; } catch( FileReadWriteError &err ) { f->Close(); User::Error( ERR_FILE_WRITEFAIL, Format("Binary Decl: $*.bin" ) << err.ToString(), filename ); return false; } catch( LexerError &err ) { f->Close(); String errStr; err.ToString( errStr ); User::Error( ERR_LEXER_FAILURE, errStr.c_str(), filename ); return false; } }
/* ================ ReadMesh ================ */ static void ReadMesh( Lexer &lexer, aseMesh *inMesh ) { int idx; Vec3 temp; lexer.ExpectToken("{"); const char *p; const Token *token; while ( (token = lexer.ReadToken()) != OG_NULL ) { p = token->GetString(); if ( !p || !*p ) continue; if ( String::Icmp( p, "}" ) == 0 ) return; if ( String::Icmp( p, "*" ) != 0 ) lexer.Error( Format("expected *, got '$*'") << p ); if ( lexer.CheckToken( "MESH_NUMVERTEX" ) ) { inMesh->numVerts = lexer.ReadInt(); inMesh->vertices = new aseVertex[inMesh->numVerts]; } else if ( lexer.CheckToken( "MESH_NUMFACES" ) ) { inMesh->numTris = lexer.ReadInt(); inMesh->triangles = new aseTriangle[inMesh->numTris]; } else if ( lexer.CheckToken( "MESH_VERTEX_LIST" ) ) { lexer.ExpectToken("{"); for( int i=0; i<inMesh->numVerts; i++ ) { lexer.ExpectToken("*"); lexer.ExpectToken("MESH_VERTEX"); idx = lexer.ReadInt(); inMesh->vertices[idx].origin.x = lexer.ReadFloat() * ASE_MODEL_SCALE; inMesh->vertices[idx].origin.y = lexer.ReadFloat() * ASE_MODEL_SCALE; inMesh->vertices[idx].origin.z = lexer.ReadFloat() * ASE_MODEL_SCALE; } lexer.ExpectToken("}"); } else if ( lexer.CheckToken( "MESH_NORMALS" ) ) { lexer.ExpectToken("{"); for( ;; ) { if ( lexer.CheckToken("}") ) break; lexer.ExpectToken("*"); // don't need the face normal if ( lexer.CheckToken("MESH_FACENORMAL") ) { lexer.GotoNextLine(); continue; } lexer.ExpectToken("MESH_VERTEXNORMAL"); idx = lexer.ReadInt(); inMesh->vertices[idx].normal.x = lexer.ReadFloat(); inMesh->vertices[idx].normal.y = lexer.ReadFloat(); inMesh->vertices[idx].normal.z = lexer.ReadFloat(); } } else if ( lexer.CheckToken( "MESH_FACE_LIST" ) ) { lexer.ExpectToken("{"); for( int i=0; i<inMesh->numTris; i++ ) { lexer.ExpectToken("*"); lexer.ExpectToken("MESH_FACE"); idx = lexer.ReadInt(); lexer.CheckToken(":"); // might or might not be there lexer.ExpectToken("A"); lexer.ExpectToken(":"); inMesh->triangles[idx].v[0] = lexer.ReadInt(); lexer.ExpectToken("B"); lexer.ExpectToken(":"); inMesh->triangles[idx].v[1] = lexer.ReadInt(); lexer.ExpectToken("C"); lexer.ExpectToken(":"); inMesh->triangles[idx].v[2] = lexer.ReadInt(); lexer.GotoNextLine(); } lexer.ExpectToken("}"); } else if ( lexer.CheckToken( "MESH_NUMTVERTEX" ) ) { inMesh->numTVerts = lexer.ReadInt(); inMesh->texCoords = new Vec2[inMesh->numTVerts]; } else if ( lexer.CheckToken( "MESH_TVERTLIST" ) ) { lexer.ExpectToken("{"); for( int i=0; i<inMesh->numTVerts; i++ ) { lexer.ExpectToken("*"); lexer.ExpectToken("MESH_TVERT"); idx = lexer.ReadInt(); inMesh->texCoords[idx].x = lexer.ReadFloat(); inMesh->texCoords[idx].y = 1.0f-lexer.ReadFloat(); lexer.ReadFloat();// don't need 3rd component } lexer.ExpectToken("}"); } else if ( lexer.CheckToken( "MESH_NUMTVFACES" ) ) lexer.ExpectToken( Format() << inMesh->numTris ); else if ( lexer.CheckToken( "MESH_TFACELIST" ) ) { lexer.ExpectToken("{"); for( int i=0; i<inMesh->numTris; i++ ) { lexer.ExpectToken("*"); lexer.ExpectToken("MESH_TFACE"); idx = lexer.ReadInt(); inMesh->triangles[idx].t[0] = lexer.ReadInt(); inMesh->triangles[idx].t[1] = lexer.ReadInt(); inMesh->triangles[idx].t[2] = lexer.ReadInt(); } lexer.ExpectToken("}"); } else if ( lexer.CheckToken( "MATERIAL_REF" ) ) inMesh->materialId = lexer.ReadInt(); else if ( !SkipUnknown(lexer) ) break; } }
/* ================ XDeclParser::Parse ================ */ void XDeclParser::Parse( Lexer &lexer ) { const Token *token; String name, value; XDeclNode *currentNode = &rootNode; XDeclNode *newNode; bool getKeyValue = false; bool addNode; Stack<XDeclNode *> nodeStack; const char *p; while ( (token = lexer.ReadToken()) != NULL ) { p = token->GetString(); if ( p ) { if ( *p == '\0' ) lexer.Error("Unexpected Empty Token"); if ( !getKeyValue ) { if ( String::Cmp( p, "}" ) == 0 ) { currentNode = nodeStack.Top(); nodeStack.Pop(); } else { name = p; addNode = false; if ( lexer.CheckToken("=") ) { currentNode->dict.Set( name.c_str(), lexer.ReadString() ); lexer.ExpectToken(";"); } else if ( lexer.CheckToken("(") ) { addNode = true; getKeyValue = true; } else if ( lexer.CheckToken("{") ) { addNode = true; } else { lexer.Error("Syntax Error, was expecting '(', '=' or '{'"); } if ( addNode ) { newNode = allocator.Alloc(); newNode->name = name; currentNode->numChildren++; if ( currentNode->firstChild == NULL ) currentNode->firstChild = newNode; else currentNode->lastChild->next = newNode; currentNode->lastChild= newNode; nodeStack.Push( currentNode ); currentNode = newNode; } } } else { name = p; lexer.ExpectToken("="); currentNode->dict.Set( name.c_str(), lexer.ReadString() ); if ( !lexer.CheckToken(",") ) { lexer.ExpectToken(")"); if ( lexer.CheckToken(";") ) { currentNode = nodeStack.Top(); nodeStack.Pop(); getKeyValue = false; } else if ( lexer.CheckToken("{") ) { getKeyValue = false; } else { lexer.Error("Syntax Error, was expecting ';' or '{'"); } } } } } if ( getKeyValue || nodeStack.Num() ) throw LexerError( LexerError::END_OF_FILE ); }