/* ================ ParseEntity ================ */ qboolean ParseEntity( void ) { epair_t *e; entity_t *mapent; if ( !GetToken (qtrue) ) { return qfalse; } if ( strcmp (token, "{") ) { Error ("ParseEntity: { not found"); } if ( num_entities == MAX_MAP_ENTITIES ) { Error ("num_entities == MAX_MAP_ENTITIES"); } mapent = &entities[num_entities]; num_entities++; do { if ( !GetToken (qtrue) ) { Error ("ParseEntity: EOF without closing brace"); } if ( !strcmp (token, "}") ) { break; } e = ParseEpair (); e->next = mapent->epairs; mapent->epairs = e; } while (1); return qtrue; }
/** * @sa ParseEntities */ static entity_t* ParseEntity (void) { entity_t* mapent; if (Q_strnull(GetToken())) return nullptr; if (parsedToken[0] != '{') Sys_Error("ParseEntity: { not found"); if (num_entities >= MAX_MAP_ENTITIES) Sys_Error("num_entities >= MAX_MAP_ENTITIES (%i)", num_entities); mapent = &entities[num_entities]; num_entities++; do { if (Q_strnull(GetToken())) Sys_Error("ParseEntity: EOF without closing brace"); if (*parsedToken == '}') { break; } else { epair_t* e = ParseEpair(num_entities); e->next = mapent->epairs; mapent->epairs = e; } } while (1); return mapent; }
/* ================ ParseEntity ================ */ qboolean ParseEntity(script_t *script) { epair_t *e; entity_t *mapent; token_t token; if (!PS_ReadToken(script, &token)) return false; if (strcmp(token.string, "{")) Error ("ParseEntity: { not found"); if (num_entities == MAX_MAP_ENTITIES) Error ("num_entities == MAX_MAP_ENTITIES"); mapent = &entities[num_entities]; num_entities++; do { if (!PS_ReadToken(script, &token)) Error ("ParseEntity: EOF without closing brace"); if (!strcmp(token.string, "}") ) break; PS_UnreadLastToken(script); e = ParseEpair(script); e->next = mapent->epairs; mapent->epairs = e; } while (1); return true; } //end of the function ParseEntity
/* ================ ParseEntity ================ */ qboolean ParseEntity (void) { if (!GetToken (true)) return false; if (strcmp (token, "{") ) Error ("ParseEntity: { not found"); if (num_entities == MAX_MAP_ENTITIES) Error ("num_entities == MAX_MAP_ENTITIES"); mapent = &entities[num_entities]; num_entities++; do { fflush(stdout); if (!GetToken (true)) Error ("ParseEntity: EOF without closing brace"); if (!strcmp (token, "}") ) break; if (!strcmp (token, "{") ) ParseBrush (); else ParseEpair (); } while (1); GetVectorForKey (mapent, "origin", mapent->origin); return true; }
static bool ParseEntity(mapentity_t *e) { if (!ParseToken(PARSE_NORMAL)) return false; if (strcmp(token, "{")) Message(msgError, errParseEntity, linenum); if (map.iEntities >= map.cEntities) Message(msgError, errLowEntCount); e->iBrushEnd = map.iBrushes + 1; do { if (!ParseToken(PARSE_NORMAL)) Message(msgError, errUnexpectedEOF); if (!strcmp(token, "}")) break; else if (!strcmp(token, "{")) ParseBrush(); else ParseEpair(); } while (1); // Allocate some model memory while we're here e->iBrushStart = map.iBrushes + 1; if (e->iBrushStart != e->iBrushEnd) { e->lumps[BSPMODEL].data = AllocMem(BSPMODEL, 1, true); e->lumps[BSPMODEL].count = 1; } return true; }
static bool ParseEntity(parser_t *parser, mapentity_t *ent) { mapbrush_t *brush; if (!ParseToken(parser, PARSE_NORMAL)) return false; if (strcmp(parser->token, "{")) Error(errParseEntity, parser->linenum); if (map.numentities == map.maxentities) Error(errLowEntCount); ent->mapbrushes = brush = map.brushes + map.numbrushes; do { if (!ParseToken(parser, PARSE_NORMAL)) Error(errUnexpectedEOF); if (!strcmp(parser->token, "}")) break; else if (!strcmp(parser->token, "{")) { if (map.numbrushes == map.maxbrushes) Error(errLowMapbrushCount); ParseBrush(parser, brush++); map.numbrushes++; } else ParseEpair(parser, ent); } while (1); ent->nummapbrushes = brush - ent->mapbrushes; if (!ent->nummapbrushes) ent->mapbrushes = NULL; return true; }
/* ======================================================================================================================= Entity_Parse If onlypairs is set, the classname info will not be looked up, and the entity will not be added to the global list. Used for parsing the project. ======================================================================================================================= */ entity_t *Entity_Parse(bool onlypairs, brush_t *pList) { entity_t *ent; if (!GetToken(true)) { return NULL; } if (strcmp(token, "{")) { Error("ParseEntity: { not found"); } ent = Entity_New(); ent->brushes.onext = ent->brushes.oprev = &ent->brushes; ent->origin.Zero(); int n = 0; do { if (!GetToken(true)) { Warning("ParseEntity: EOF without closing brace"); return NULL; } if (!strcmp(token, "}")) { break; } if (!strcmp(token, "{")) { GetVectorForKey(ent, "origin", ent->origin); brush_t *b = Brush_Parse(ent->origin); if (b != NULL) { b->owner = ent; // add to the end of the entity chain b->onext = &ent->brushes; b->oprev = ent->brushes.oprev; ent->brushes.oprev->onext = b; ent->brushes.oprev = b; } else { break; } } else { ParseEpair(&ent->epairs); } } while (1); if (onlypairs) { return ent; } return Entity_PostParse(ent, pList); }
/* ================ ParseEntity ================ */ qboolean ParseEntity (void) { epair_t *e, *next; entity_t *ent; if( !GetToken( true ) ) return false; if (!strcmp(token, "Version")) { GetToken(true); mapversion = atof(token); GetToken(true); } if( strcmp( token, "{" ) ) Error( "ParseEntity: line %i: { not found", scriptline ); if( num_entities == MAX_MAP_ENTITIES ) Error( "num_entities == MAX_MAP_ENTITIES" ); ent = &entities[num_entities++]; ent->epairs = NULL; ent->scriptline = scriptline; // LordHavoc: better error reporting do { fflush( stdout ); if( !GetToken( true ) ) Error( "ParseEntity: line %i: EOF without closing brace", scriptline ); if( !strcmp (token, "}") ) break; else if( !strcmp( token, "{" ) ) { ParseBrush( ent ); } else { e = ParseEpair (); e->next = ent->epairs; ent->epairs = e; } } while( 1 ); if( !strcmp( ValueForKey( ent, "classname" ), "func_group" ) ) { MoveEntityBrushesIntoWorld( ent ); for( e = ent->epairs; e; e = next ) { next = e->next; qfree( e ); } num_entities--; } return true; }
/* ================ ParseEntity ================ */ qboolean ParseEntity (void) { if (!GetToken (true)) return false; if (strcmp (token, "{") ) Error ("ParseEntity: { not found"); if (num_entities == MAX_MAP_ENTITIES) Error ("num_entities == MAX_MAP_ENTITIES"); mapent = &entities[num_entities]; num_entities++; do { fflush(stdout); if (!GetToken (true)) Error ("ParseEntity: EOF without closing brace"); if (!strcmp (token, "}") ) break; if (!strcmp (token, "{") ) ParseBrush (); else ParseEpair (); } while (1); // all fields have been parsed if (!strncmp (mapent->classname, "light", 5)) { if (!mapent->light) { mapent->color[0] = mapent->color[1] = mapent->color[2] = 1; mapent->light = DEFAULTLIGHTLEVEL; } // LordHavoc: added falloff and color if (!mapent->falloff) mapent->falloff = DEFAULTFALLOFF * DEFAULTFALLOFF; } if (!strcmp (mapent->classname, "light")) if (mapent->targetname[0] && !mapent->style) { char s[16]; mapent->style = LightStyleForTargetname (mapent->targetname, true); sprintf (s,"%i", mapent->style); SetKeyValue (mapent, "style", s); } GetVectorForKey (mapent, "origin", mapent->origin); return true; }
/* ================ ParseEntity ================ */ static qboolean ParseEntity (void) { if (!GetToken (true)) return false; if (strcmp (token, "{") ) Error ("%s: { not found", __thisfunc__); if (num_entities == MAX_MAP_ENTITIES) Error ("num_entities == MAX_MAP_ENTITIES"); mapent = &entities[num_entities]; num_entities++; do { if (!GetToken (true)) Error ("%s: EOF without closing brace", __thisfunc__); if (!strcmp (token, "}") ) break; if (!strcmp (token, "{") ) ParseBrush (); else ParseEpair (); } while (1); GetVectorForKey (mapent, "origin", mapent->origin); // JDC 8/8/97: adjust for origin brush if (mapent->origin[0] || mapent->origin[1] || mapent->origin[2]) { mbrush_t *b; mface_t *f; for (b = mapent->brushes ; b ; b = b->next) { for (f = b->faces ; f ; f = f->next) f->plane.dist -= DotProduct (mapent->origin, f->plane.normal); } } return true; }
/** * @brief Parsed map entites and brushes * @sa ParseBrush * @param[in] filename The map filename * @param[in] entityString The body of the entity we are parsing */ static bool ParseMapEntity (const char* filename, const char* entityString) { entity_t* mapent; const char* entName; static int worldspawnCount = 0; int notCheckOrFix = !(config.performMapCheck || config.fixMap); if (Q_strnull(GetToken())) return false; if (*parsedToken != '{') Sys_Error("ParseMapEntity: { not found"); if (num_entities == MAX_MAP_ENTITIES) Sys_Error("num_entities == MAX_MAP_ENTITIES (%i)", num_entities); mapent = &entities[num_entities++]; OBJZERO(*mapent); mapent->firstbrush = nummapbrushes; mapent->numbrushes = 0; do { if (Q_strnull(GetToken())) Sys_Error("ParseMapEntity: EOF without closing brace"); if (*parsedToken == '}') break; if (*parsedToken == '{') ParseBrush(mapent, filename); else { epair_t* e = ParseEpair(num_entities); e->next = mapent->epairs; mapent->epairs = e; } } while (true); GetVectorForKey(mapent, "origin", mapent->origin); entName = ValueForKey(mapent, "classname"); /* offset all of the planes and texinfo if needed */ if (IsInlineModelEntity(entName) && VectorNotEmpty(mapent->origin)) AdjustBrushesForOrigin(mapent); if (num_entities == 1 && !Q_streq("worldspawn", entName)) Sys_Error("The first entity must be worldspawn, it is: %s", entName); if (notCheckOrFix && Q_streq("func_group", entName)) { /* group entities are just for editor convenience * toss all brushes into the world entity */ MoveBrushesToWorld(mapent); num_entities--; } else if (IsInlineModelEntity(entName)) { if (mapent->numbrushes == 0 && notCheckOrFix) { Com_Printf("Warning: %s has no brushes assigned (entnum: %i)\n", entName, num_entities); num_entities--; } } else if (Q_streq("worldspawn", entName)) { worldspawnCount++; if (worldspawnCount > 1) Com_Printf("Warning: more than one %s in one map\n", entName); const char* text = entityString; do { const char* token = Com_Parse(&text); if (Q_strnull(token)) break; const char* key = Mem_StrDup(token); token = Com_Parse(&text); if (Q_strnull(token)) break; const char* value = Mem_StrDup(token); epair_t* e = AddEpair(key, value, num_entities); e->next = mapent->epairs; mapent->epairs = e; } while (true); } return true; }
/* ================= ParseMapEntity parses a single entity out of a map file ================= */ static bool ParseMapEntity( bool onlyLights ) { epair_t *ep; token_t token; const char *classname, *value; float lightmapScale; char shader[ MAX_SHADERPATH ]; shaderInfo_t *celShader = NULL; brush_t *brush; parseMesh_t *patch; bool funcGroup; int castShadows, recvShadows; static bool map_type = false; if( !Com_ReadToken( mapfile, SC_ALLOW_NEWLINES|SC_COMMENT_SEMICOLON, &token )) return false; // end of .map file if( com.stricmp( token.string, "{" )) Sys_Break( "ParseEntity: found %s instead {\n", token.string ); if( numEntities >= MAX_MAP_ENTITIES ) Sys_Break( "MAX_MAP_ENTITIES limit exceeded\n" ); entitySourceBrushes = 0; mapEnt = &entities[numEntities]; numEntities++; memset( mapEnt, 0, sizeof( *mapEnt )); mapEnt->mapEntityNum = numMapEntities; numMapEntities++; while( 1 ) { if( !Com_ReadToken( mapfile, SC_ALLOW_NEWLINES|SC_COMMENT_SEMICOLON, &token )) Sys_Break( "ParseEntity: EOF without closing brace\n" ); if( !com.stricmp( token.string, "}" )) break; if( !com.stricmp( token.string, "{" )) { // parse a brush or patch if( !Com_ReadToken( mapfile, SC_ALLOW_NEWLINES, &token )) break; if( !com.stricmp( token.string, "patchDef2" )) { numMapPatches++; ParsePatch( onlyLights ); g_bBrushPrimit = BRUSH_RADIANT; } else if( !com.stricmp( token.string, "terrainDef" )) { MsgDev( D_WARN, "Terrain entity parsing not supported in this build.\n" ); Com_SkipBracedSection( mapfile, 0 ); g_bBrushPrimit = BRUSH_RADIANT; } else if( !com.stricmp( token.string, "brushDef" )) { // parse brush primitive g_bBrushPrimit = BRUSH_RADIANT; ParseBrush( onlyLights ); } else { if( g_bBrushPrimit == BRUSH_RADIANT ) Sys_Break( "mixed brush primitive with another format\n" ); if( g_bBrushPrimit == BRUSH_UNKNOWN ) g_bBrushPrimit = BRUSH_WORLDCRAFT_21; // QuArK or WorldCraft map (unknown at this point) Com_SaveToken( mapfile, &token ); ParseBrush( onlyLights ); } entitySourceBrushes++; } else { // parse a key / value pair ep = ParseEpair( mapfile, &token ); if( !com.strcmp( ep->key, "mapversion" )) { if( com.atoi( ep->value ) == VALVE_FORMAT ) { Msg( "Valve Format Map detected\n" ); g_bBrushPrimit = BRUSH_WORLDCRAFT_22; } else if( com.atoi( ep->value ) == GEARBOX_FORMAT ) { Msg( "Gearcraft Format Map detected\n" ); g_bBrushPrimit = BRUSH_GEARCRAFT_40; } else g_bBrushPrimit = BRUSH_WORLDCRAFT_21; } if( ep->key[0] != '\0' && ep->value[0] != '\0' ) { ep->next = mapEnt->epairs; mapEnt->epairs = ep; } } } if( !map_type && g_bBrushPrimit != BRUSH_UNKNOWN ) { MAPTYPE(); map_type = true; } classname = ValueForKey( mapEnt, "classname" ); if( onlyLights && com.strnicmp( classname, "light", 5 )) { numEntities--; return true; } if( !com.stricmp( "func_group", classname )) funcGroup = true; else funcGroup = false; // worldspawn (and func_groups) default to cast/recv shadows in worldspawn group if( funcGroup || mapEnt->mapEntityNum == 0 ) { castShadows = WORLDSPAWN_CAST_SHADOWS; recvShadows = WORLDSPAWN_RECV_SHADOWS; } else // other entities don't cast any shadows, but recv worldspawn shadows { castShadows = ENTITY_CAST_SHADOWS; recvShadows = ENTITY_RECV_SHADOWS; } // get explicit shadow flags GetEntityShadowFlags( mapEnt, NULL, &castShadows, &recvShadows ); // get lightmap scaling value for this entity if( com.strcmp( "", ValueForKey( mapEnt, "lightmapscale" )) || com.strcmp( "", ValueForKey( mapEnt, "_lightmapscale" ))) { // get lightmap scale from entity lightmapScale = FloatForKey( mapEnt, "lightmapscale" ); if( lightmapScale <= 0.0f ) lightmapScale = FloatForKey( mapEnt, "_lightmapscale" ); if( lightmapScale > 0.0f ) Msg( "Entity %d (%s) has lightmap scale of %.4f\n", mapEnt->mapEntityNum, classname, lightmapScale ); } else lightmapScale = 0.0f; // get cel shader :) for this entity value = ValueForKey( mapEnt, "_celshader" ); if( value[0] == '\0' ) value = ValueForKey( &entities[0], "_celshader" ); if( value[0] != '\0' ) { com.snprintf( shader, sizeof( shader ), "textures/%s", value ); celShader = ShaderInfoForShader( shader ); Msg( "Entity %d (%s) has cel shader %s\n", mapEnt->mapEntityNum, classname, celShader->shader ); } else celShader = NULL; // attach stuff to everything in the entity for( brush = mapEnt->brushes; brush != NULL; brush = brush->next ) { brush->entityNum = mapEnt->mapEntityNum; brush->castShadows = castShadows; brush->recvShadows = recvShadows; brush->lightmapScale = lightmapScale; brush->celShader = celShader; } for( patch = mapEnt->patches; patch != NULL; patch = patch->next ) { patch->entityNum = mapEnt->mapEntityNum; patch->castShadows = castShadows; patch->recvShadows = recvShadows; patch->lightmapScale = lightmapScale; patch->celShader = celShader; } SetEntityBounds( mapEnt ); // load shader index map (equivalent to old terrain alphamap) LoadEntityIndexMap( mapEnt ); // get entity origin and adjust brushes GetVectorForKey( mapEnt, "origin", mapEnt->origin ); if( mapEnt->origin[0] || mapEnt->origin[1] || mapEnt->origin[2] ) AdjustBrushesForOrigin( mapEnt ); // group_info entities are just for editor grouping if( !com.stricmp( "group_info", classname )) { numEntities--; return true; } // group entities are just for editor convenience, toss all brushes into worldspawn if( funcGroup ) { MoveBrushesToWorld( mapEnt ); numEntities--; return true; } return true; }
/* ================ Entity_Parse If onlypairs is set, the classname info will not be looked up, and the entity will not be added to the global list. Used for parsing the project. ================ */ entity_t *Entity_Parse (qboolean onlypairs, brush_t* pList) { entity_t *ent; eclass_t *e; brush_t *b; vec3_t mins, maxs; epair_t *ep; qboolean has_brushes; #ifdef SOF float scale; #endif if (!GetToken (true)) return NULL; if (strcmp (token, "{") ) Error ("ParseEntity: { not found"); ent = (entity_t*)qmalloc (sizeof(*ent)); ent->brushes.onext = ent->brushes.oprev = &ent->brushes; do { if (!GetToken (true)) { Warning ("ParseEntity: EOF without closing brace"); return NULL; } if (!strcmp (token, "}") ) break; if (!strcmp (token, "{") ) { b = Brush_Parse (); if (b != NULL) { b->owner = ent; // add to the end of the entity chain b->onext = &ent->brushes; b->oprev = ent->brushes.oprev; ent->brushes.oprev->onext = b; ent->brushes.oprev = b; } else { break; } } else { ep = ParseEpair (); { // update: the original code here may have been simple, but it meant that every map load/save // the key/value pair fields were reversed in the save file, which messes up SourceSafe when it // tries to delta the two versions during check-in... -slc #if 0 ep->next = ent->epairs; ent->epairs = ep; #else // join this onto the END of the chain instead... // if (ent->epairs == NULL) // special case for if there isn't a chain yet... :-) { ep->next = ent->epairs; ent->epairs = ep; } else { for (epair_t* ep2 = ent->epairs ; ep2 ; ep2=ep2->next) { if (ep2->next == NULL) { // found the end, so... // ep2->next = ep; ep->next = NULL; break; } } } #endif } } } while (1); if (onlypairs) return ent; if (ent->brushes.onext == &ent->brushes) has_brushes = false; else has_brushes = true; GetVectorForKey (ent, "origin", ent->origin); e = Eclass_ForName (ValueForKey (ent, "classname"), has_brushes); ent->eclass = e; if (e->fixedsize) { // fixed size entity if (ent->brushes.onext != &ent->brushes) { printf ("Warning: Fixed size entity with brushes\n"); #if 0 while (ent->brushes.onext != &ent->brushes) { // FIXME: this will free the entity and crash! Brush_Free (b); } #endif ent->brushes.next = ent->brushes.prev = &ent->brushes; } // create a custom brush VectorAdd (e->mins, ent->origin, mins); VectorAdd (e->maxs, ent->origin, maxs); float a = 0; if (strnicmp(e->name, "misc_model",10) == 0) { char* p = ValueForKey(ent, "model"); if (p != NULL && strlen(p) > 0) { vec3_t vMin, vMax; a = FloatForKey (ent, "angle"); gEntityToSetBoundsOf = ent; if (GetCachedModel(ent, p, vMin, vMax)) { // create a custom brush VectorAdd (ent->md3Class->mins, ent->origin, mins); VectorAdd (ent->md3Class->maxs, ent->origin, maxs); } } } #ifdef SOF if (strnicmp(e->name, "misc_", 5) == 0 || strnicmp(e->name, "light_", 6) == 0 || strnicmp(e->name, "m_", 2) == 0 || strnicmp(e->name, "item_weapon_", 12)== 0 || strnicmp(e->name, "item_ammo_", 10)== 0 ) a = FloatForKey (ent, "angle"); #endif b = Brush_Create (mins, maxs, &e->texdef); /////// b->owner = ent; b->onext = ent->brushes.onext; b->oprev = &ent->brushes; ent->brushes.onext->oprev = b; ent->brushes.onext = b; /////// Brush_Build(b); #ifdef SOF scale = FloatForKey (ent, "scale"); if (scale) { Brush_Scale2(e, b, scale, ent->origin,false); } #endif // if (a) // { // vec3_t vAngle; // vAngle[0] = vAngle[1] = 0; // vAngle[2] = a; // Brush_Rotate(b, vAngle, ent->origin, false); // } /* b->owner = ent; b->onext = ent->brushes.onext; b->oprev = &ent->brushes; ent->brushes.onext->oprev = b; ent->brushes.onext = b; */ // do this AFTER doing the brush stuff just above, so don't join to the other "if (a)"... // if (a) { // pick any old value to rotate away to, then back from, to avoid 0/360 weirdness on key-compares // SetKeyValue(ent, "angle", "0", false); // false = no tracking, ie just set the angle and nothing else SetKeyValue(ent, "angle", va("%g",a), true); // true = do tracking, ie actually do the brush rotate } } else { // brush entity if (ent->brushes.next == &ent->brushes) printf ("Warning: Brush entity with no brushes\n"); } // add all the brushes to the main list if (pList) { for (b=ent->brushes.onext ; b != &ent->brushes ; b=b->onext) { b->next = pList->next; pList->next->prev = b; b->prev = pList; pList->next = b; } } return ent; }
/* ================ ParseEntity ================ */ qboolean ParseEntity (void) { epair_t *ep; entity_t *world; mbrush_t *b, *next; int Line, i; char *Classname; static int WorldSpawns = 0; if (!GetToken (true)) return false; Line = scriptline; if (strcmp (token, "{") ) Message (MSGERR, "Invalid entity format, { not found on line %d", Line); ExtendArray(entities, num_entities); mapent = &entities[num_entities]; mapent->Line = Line; num_entities++; do { if (!GetToken (true)) Message (MSGERR, "ParseEntity: EOF without closing brace"); if (!strcmp (token, "}") ) break; if (!strcmp (token, "{") ) ParseBrush (); else ParseEpair (); } while (1); Classname = ValueForKey(mapent, "classname"); if (strlen(Classname) == 0) Message (MSGERR, "No classname in entity on line %d", Line); // Missing classname if (!stricmp(Classname, "worldspawn")) { if (++WorldSpawns > 1) Message (MSGERR, "Multiple world entities on line %d", Line); // Multiple worlds if (!options.onlyents && !mapent->brushes) Message (MSGERR, "No world brushes on line %d", Line); // No world brushes // Get map title strcpy(MapTitle, ValueForKey(mapent, "message")); // Translate into simplified Quake character set for (i = 0; MapTitle[i] != '\0'; ++i) { MapTitle[i] &= 0x7F; // Ignore colour bit if (MapTitle[i] >= 0x12 && MapTitle[i] <= 0x1B) MapTitle[i] += 0x1E; // Extra 0-9 area else if (MapTitle[i] == 0x10) MapTitle[i] = '['; // Extra bracket else if (MapTitle[i] == 0x11) MapTitle[i] = ']'; // Extra bracket if (!isprint(MapTitle[i] & 0xFF)) MapTitle[i] = ' '; } } else if (options.noents && strnicmp(Classname, "info_player_", 12)) { // Only world and players allowed; drop entity for (ep = mapent->epairs; ep; ep = ep->next) FreeOther (ep->value); memset (mapent, 0, sizeof(entity_t)); --num_entities; return true; } else if (options.group && !stricmp(Classname, "func_group")) { // Move entity brushes into world world = &entities[0]; for (b = mapent->brushes; b; b = next) { next = b->next; b->next = world->brushes; world->brushes = b; } for (ep = mapent->epairs; ep; ep = ep->next) FreeOther (ep->value); memset (mapent, 0, sizeof(entity_t)); --num_entities; return true; } if (num_entities == 1 && WorldSpawns == 0) Message (MSGERR, "World is not first entity on line %d", Line); // World is not first entity GetVectorForKey (mapent, "origin", mapent->origin); return true; }
/* ================ ParseMapEntity ================ */ qboolean ParseMapEntity (void) { entity_t *mapent; epair_t *e; side_t *s; int i, j; int startbrush, startsides; vec_t newdist; mapbrush_t *b; if (!GetToken (true)) return false; if (strcmp (token, "{") ) Error ("ParseEntity: { not found"); if (num_entities == MAX_MAP_ENTITIES) Error ("num_entities == MAX_MAP_ENTITIES"); startbrush = nummapbrushes; startsides = nummapbrushsides; mapent = &entities[num_entities]; num_entities++; memset (mapent, 0, sizeof(*mapent)); mapent->firstbrush = nummapbrushes; mapent->numbrushes = 0; // mapent->portalareas[0] = -1; // mapent->portalareas[1] = -1; do { if (!GetToken (true)) Error ("ParseEntity: EOF without closing brace"); if (!strcmp (token, "}") ) break; if (!strcmp (token, "{") ) ParseBrush (mapent); else { e = ParseEpair (); e->next = mapent->epairs; mapent->epairs = e; } } while (1); GetVectorForKey (mapent, "origin", mapent->origin); // // if there was an origin brush, offset all of the planes and texinfo // if (mapent->origin[0] || mapent->origin[1] || mapent->origin[2]) { for (i=0 ; i<mapent->numbrushes ; i++) { b = &mapbrushes[mapent->firstbrush + i]; for (j=0 ; j<b->numsides ; j++) { s = &b->original_sides[j]; newdist = mapplanes[s->planenum].dist - DotProduct (mapplanes[s->planenum].normal, mapent->origin); s->planenum = FindFloatPlane (mapplanes[s->planenum].normal, newdist); s->texinfo = TexinfoForBrushTexture (&mapplanes[s->planenum], &side_brushtextures[s-brushsides], mapent->origin); } MakeBrushWindings (b); } } // group entities are just for editor convenience // toss all brushes into the world entity if (!strcmp ("func_group", ValueForKey (mapent, "classname"))) { MoveBrushesToWorld (mapent); mapent->numbrushes = 0; return true; } // areaportal entities move their brushes, but don't eliminate // the entity if (!strcmp ("func_areaportal", ValueForKey (mapent, "classname"))) { char str[128]; if (mapent->numbrushes != 1) Error ("Entity %i: func_areaportal can only be a single brush", num_entities-1); b = &mapbrushes[nummapbrushes-1]; b->contents = CONTENTS_AREAPORTAL; c_areaportals++; mapent->areaportalnum = c_areaportals; // set the portal number as "style" sprintf (str, "%i", c_areaportals); SetKeyValue (mapent, "style", str); MoveBrushesToWorld (mapent); return true; } return true; }
// // ======================================================================================================================= // parse a brush in brush primitive format // ======================================================================================================================= // void BrushPrimit_Parse(brush_t *b, bool newFormat, const idVec3 origin) { face_t *f; int i, j; GetToken(true); if (strcmp(token, "{")) { Warning("parsing brush primitive"); return; } do { if (!GetToken(true)) { break; } if (!strcmp(token, "}")) { break; } // reading of b->epairs if any if (strcmp(token, "(")) { ParseEpair(&b->epairs); } else { // it's a face f = Face_Alloc(); f->next = NULL; if (!b->brush_faces) { b->brush_faces = f; } else { face_t *scan; for (scan = b->brush_faces; scan->next; scan = scan->next) ; scan->next = f; } if (newFormat) { // read the three point plane definition idPlane plane; for (j = 0; j < 4; j++) { GetToken(false); plane[j] = atof(token); } f->plane = plane; f->originalPlane = plane; f->dirty = false; //idWinding *w = Brush_MakeFaceWinding(b, f, true); idWinding w; w.BaseForPlane( plane ); for (j = 0; j < 3; j++) { f->planepts[j].x = w[j].x + origin.x; f->planepts[j].y = w[j].y + origin.y; f->planepts[j].z = w[j].z + origin.z; } GetToken(false); } else { for (i = 0; i < 3; i++) { if (i != 0) { GetToken(true); } if (strcmp(token, "(")) { Warning("parsing brush"); return; } for (j = 0; j < 3; j++) { GetToken(false); f->planepts[i][j] = atof(token); } GetToken(false); if (strcmp(token, ")")) { Warning("parsing brush"); return; } } } // texture coordinates GetToken(false); if (strcmp(token, "(")) { Warning("parsing brush primitive"); return; } GetToken(false); if (strcmp(token, "(")) { Warning("parsing brush primitive"); return; } for (j = 0; j < 3; j++) { GetToken(false); f->brushprimit_texdef.coords[0][j] = atof(token); } GetToken(false); if (strcmp(token, ")")) { Warning("parsing brush primitive"); return; } GetToken(false); if (strcmp(token, "(")) { Warning("parsing brush primitive"); return; } for (j = 0; j < 3; j++) { GetToken(false); f->brushprimit_texdef.coords[1][j] = atof(token); } GetToken(false); if (strcmp(token, ")")) { Warning("parsing brush primitive"); return; } GetToken(false); if (strcmp(token, ")")) { Warning("parsing brush primitive"); return; } // read the texturedef GetToken(false); // strcpy(f->texdef.name, token); if (g_qeglobals.mapVersion < 2.0) { f->texdef.SetName(va("textures/%s", token)); } else { f->texdef.SetName(token); } if (TokenAvailable()) { GetToken(false); GetToken(false); GetToken(false); f->texdef.value = atoi(token); } } } while (1); }
/* * @brief */ static _Bool ParseMapEntity(void) { entity_t *mapent; epair_t *e; side_t *s; int32_t i, j; vec_t newdist; map_brush_t *b; if (!GetToken(true)) return false; if (g_strcmp0(token, "{")) Com_Error(ERR_FATAL, "\"{\" not found\n"); if (num_entities == MAX_BSP_ENTITIES) Com_Error(ERR_FATAL, "MAX_BSP_ENTITIES\n"); mapent = &entities[num_entities]; num_entities++; memset(mapent, 0, sizeof(*mapent)); mapent->first_brush = num_map_brushes; mapent->num_brushes = 0; do { if (!GetToken(true)) Com_Error(ERR_FATAL, "EOF without closing brace\n"); if (!g_strcmp0(token, "}")) break; if (!g_strcmp0(token, "{")) ParseBrush(mapent); else { e = ParseEpair(); e->next = mapent->epairs; mapent->epairs = e; } } while (true); VectorForKey(mapent, "origin", mapent->origin); // if there was an origin brush, offset all of the planes and texinfo if (mapent->origin[0] || mapent->origin[1] || mapent->origin[2]) { for (i = 0; i < mapent->num_brushes; i++) { b = &map_brushes[mapent->first_brush + i]; for (j = 0; j < b->num_sides; j++) { s = &b->original_sides[j]; newdist = map_planes[s->plane_num].dist - DotProduct(map_planes[s->plane_num].normal, mapent->origin); s->plane_num = FindPlane(map_planes[s->plane_num].normal, newdist); s->texinfo = TexinfoForBrushTexture(&map_planes[s->plane_num], &map_brush_textures[s - map_brush_sides], mapent->origin); } MakeBrushWindings(b); } } // group entities are just for editor convenience // toss all brushes into the world entity if (!g_strcmp0("func_group", ValueForKey(mapent, "classname"))) { MoveBrushesToWorld(mapent); mapent->num_brushes = 0; return true; } // areaportal entities move their brushes, but don't eliminate the entity if (!g_strcmp0("func_areaportal", ValueForKey(mapent, "classname"))) { char str[128]; if (mapent->num_brushes != 1) Com_Error( ERR_FATAL, "ParseMapEntity: %i func_areaportal can only be a single brush\n", num_entities - 1); b = &map_brushes[num_map_brushes - 1]; b->contents = CONTENTS_AREA_PORTAL; c_area_portals++; mapent->area_portal_num = c_area_portals; // set the portal number as "style" sprintf(str, "%i", c_area_portals); SetKeyValue(mapent, "areaportal", str); MoveBrushesToWorld(mapent); return true; } return true; }
/* ================= ParsePatch Creates a mapDrawSurface_t from the patch text ================= */ void ParsePatch( void ) { vec_t info[5]; int i, j; parseMesh_t *pm; char texture[MAX_QPATH]; char shader[MAX_QPATH]; mesh_t m; drawVert_t *verts; epair_t *ep; MatchToken( "{" ); // get texture GetToken (qtrue); strcpy( texture, token ); // save the shader name for retexturing if ( numMapIndexedShaders == MAX_MAP_BRUSHSIDES ) { Error( "MAX_MAP_BRUSHSIDES" ); } strcpy( mapIndexedShaders[numMapIndexedShaders], texture ); numMapIndexedShaders++; Parse1DMatrix( 5, info ); m.width = info[0]; m.height = info[1]; m.verts = verts = malloc( m.width * m.height * sizeof( m.verts[0] ) ); if ( m.width < 0 || m.width > MAX_PATCH_SIZE || m.height < 0 || m.height > MAX_PATCH_SIZE ) { Error("ParsePatch: bad size"); } MatchToken( "(" ); for ( j = 0 ; j < m.width ; j++ ) { MatchToken( "(" ); for ( i = 0 ; i < m.height ; i++ ) { Parse1DMatrix( 5, verts[i*m.width+j].xyz ); } MatchToken( ")" ); } MatchToken( ")" ); // if brush primitives format, we may have some epairs to ignore here GetToken(qtrue); if (g_bBrushPrimit!=BPRIMIT_OLDBRUSHES && strcmp(token,"}")) { // NOTE: we leak that! ep = ParseEpair(); } else UnGetToken(); MatchToken( "}" ); MatchToken( "}" ); if ( noCurveBrushes ) { return; } // find default flags and values pm = malloc( sizeof( *pm ) ); memset( pm, 0, sizeof( *pm ) ); sprintf( shader, "textures/%s", texture ); pm->shaderInfo = ShaderInfoForShader( shader ); pm->mesh = m; // link to the entity pm->next = mapent->patches; mapent->patches = pm; }