int GetUniqueTargetId(int iHint) { int iMin, iMax, i; bool fFound; entity_t *pe; fFound = FALSE; pe = entities.next; iMin = 0; iMax = 0; for (; pe != NULL && pe != &entities ; pe = pe->next) { i = IntForKey(pe, "target"); if (i) { iMin = MIN(i, iMin); iMax = MAX(i, iMax); if (i == iHint) fFound = TRUE; } } if (fFound) return iMax + 1; else return iHint; }
/* ======================================================================================================================= ======================================================================================================================= */ entity_t *FindEntityInt(const char *pszKey, int iValue) { entity_t *pe; pe = entities.next; for (; pe != NULL && pe != &entities; pe = pe->next) { if (IntForKey(pe, pszKey) == iValue) { return pe; } } return NULL; }
void UpdateTarget(vec3_t origin, vec3_t dir) { trace_t t; entity_t *pe; int i; char sz[128]; t = Test_Ray (origin, dir, 0); if (!t.brush) return; pe = t.brush->owner; if (pe == NULL) return; // is this the first? if (peLink != NULL) { // Get the target id from out current target // if there is no id, make one i = IntForKey(pe, "target"); if (i <= 0) { i = GetUniqueTargetId(1); sprintf(sz, "%d", i); SetKeyValue(pe, "target", sz); } // set the target # into our src sprintf(sz, "%d", i); SetKeyValue(peLink, "targetname", sz); Sys_UpdateWindows(W_ENTITY); } // promote the target to the src peLink = pe; }
void CEntityMiscModel::BuildCacheRequestString( const char *name ){ bool hasRemaps = false; m_cachereq.Format( "%s:%i", name, IntForKey( m_entity,"_frame" ) ); for ( epair_t* ep = m_entity->epairs ; ep ; ep = ep->next ) { if ( strncmp( ep->key,"_remap",6 ) == 0 ) { if ( !hasRemaps ) { hasRemaps = true; m_cachereq += "?"; } else { m_cachereq += "&"; } m_cachereq += ep->value; } } }
/* ======================================================================================================================= QE_LoadProject ======================================================================================================================= */ bool QE_LoadProject(char *projectfile) { char *data; ID_TIME_T time; common->Printf("QE_LoadProject (%s)\n", projectfile); if ( fileSystem->ReadFile( projectfile, reinterpret_cast < void ** > (&data), &time) <= 0 ) { return false; } g_strProject = projectfile; g_PrefsDlg.m_strLastProject = projectfile; g_PrefsDlg.SavePrefs(); CString strData = data; fileSystem->FreeFile( data ); StartTokenParsing(strData.GetBuffer(0)); g_qeglobals.d_project_entity = Entity_Parse(true); if (!g_qeglobals.d_project_entity) { Error("Couldn't parse %s", projectfile); } // set here some default project settings you need if (strlen(ValueForKey(g_qeglobals.d_project_entity, "brush_primit")) == 0) { SetKeyValue(g_qeglobals.d_project_entity, "brush_primit", "0"); } g_qeglobals.m_bBrushPrimitMode = IntForKey(g_qeglobals.d_project_entity, "brush_primit"); Eclass_InitForSourceDirectory(ValueForKey(g_qeglobals.d_project_entity, "entitypath")); g_Inspectors->FillClassList(); // list in entity window Map_New(); // FillTextureMenu(); FillBSPMenu(); return true; }
void ProcessWorldModel( void ) { int i, s; entity_t *e; tree_t *tree; face_t *faces; qboolean ignoreLeaks, leaked; xmlNodePtr polyline, leaknode; char level[ 2 ], shader[ 1024 ]; const char *value; /* sets integer blockSize from worldspawn "_blocksize" key if it exists */ value = ValueForKey( &entities[ 0 ], "_blocksize" ); if( value[ 0 ] == '\0' ) value = ValueForKey( &entities[ 0 ], "blocksize" ); if( value[ 0 ] == '\0' ) value = ValueForKey( &entities[ 0 ], "chopsize" ); /* sof2 */ if( value[ 0 ] != '\0' ) { /* scan 3 numbers */ s = sscanf( value, "%d %d %d", &blockSize[ 0 ], &blockSize[ 1 ], &blockSize[ 2 ] ); /* handle legacy case */ if( s == 1 ) { blockSize[ 1 ] = blockSize[ 0 ]; blockSize[ 2 ] = blockSize[ 0 ]; } } Sys_Printf( "block size = { %d %d %d }\n", blockSize[ 0 ], blockSize[ 1 ], blockSize[ 2 ] ); /* sof2: ignore leaks? */ value = ValueForKey( &entities[ 0 ], "_ignoreleaks" ); /* ydnar */ if( value[ 0 ] == '\0' ) value = ValueForKey( &entities[ 0 ], "ignoreleaks" ); if( value[ 0 ] == '1' ) ignoreLeaks = qtrue; else ignoreLeaks = qfalse; /* begin worldspawn model */ BeginModel(); e = &entities[ 0 ]; e->firstDrawSurf = 0; /* ydnar: gs mods */ ClearMetaTriangles(); /* check for patches with adjacent edges that need to lod together */ PatchMapDrawSurfs( e ); /* build an initial bsp tree using all of the sides of all of the structural brushes */ faces = MakeStructuralBSPFaceList( entities[ 0 ].brushes ); tree = FaceBSP( faces ); MakeTreePortals( tree ); FilterStructuralBrushesIntoTree( e, tree ); /* see if the bsp is completely enclosed */ if( FloodEntities( tree ) || ignoreLeaks ) { /* rebuild a better bsp tree using only the sides that are visible from the inside */ FillOutside( tree->headnode ); /* chop the sides to the convex hull of their visible fragments, giving us the smallest polygons */ ClipSidesIntoTree( e, tree ); /* build a visible face tree */ faces = MakeVisibleBSPFaceList( entities[ 0 ].brushes ); FreeTree( tree ); tree = FaceBSP( faces ); MakeTreePortals( tree ); FilterStructuralBrushesIntoTree( e, tree ); leaked = qfalse; /* ydnar: flood again for skybox */ if( skyboxPresent ) FloodEntities( tree ); } else { Sys_FPrintf( SYS_NOXML, "**********************\n" ); Sys_FPrintf( SYS_NOXML, "******* leaked *******\n" ); Sys_FPrintf( SYS_NOXML, "**********************\n" ); polyline = LeakFile( tree ); leaknode = xmlNewNode( NULL, "message" ); xmlNodeSetContent( leaknode, "MAP LEAKED\n" ); xmlAddChild( leaknode, polyline ); level[0] = (int) '0' + SYS_ERR; level[1] = 0; xmlSetProp( leaknode, "level", (char*) &level ); xml_SendNode( leaknode ); if( leaktest ) { Sys_Printf ("--- MAP LEAKED, ABORTING LEAKTEST ---\n"); exit( 0 ); } leaked = qtrue; /* chop the sides to the convex hull of their visible fragments, giving us the smallest polygons */ ClipSidesIntoTree( e, tree ); } /* save out information for visibility processing */ NumberClusters( tree ); if( !leaked ) WritePortalFile( tree ); /* flood from entities */ FloodAreas( tree ); /* create drawsurfs for triangle models */ AddTriangleModels( e ); /* create drawsurfs for surface models */ AddEntitySurfaceModels( e ); /* generate bsp brushes from map brushes */ EmitBrushes( e->brushes, &e->firstBrush, &e->numBrushes ); /* add references to the detail brushes */ FilterDetailBrushesIntoTree( e, tree ); /* drawsurfs that cross fog boundaries will need to be split along the fog boundary */ if( !nofog ) FogDrawSurfaces( e ); /* subdivide each drawsurf as required by shader tesselation */ if( !nosubdivide ) SubdivideFaceSurfaces( e, tree ); /* add in any vertexes required to fix t-junctions */ if( !notjunc ) FixTJunctions( e ); /* ydnar: classify the surfaces */ ClassifyEntitySurfaces( e ); /* ydnar: project decals */ MakeEntityDecals( e ); /* ydnar: meta surfaces */ MakeEntityMetaTriangles( e ); SmoothMetaTriangles(); FixMetaTJunctions(); MergeMetaTriangles(); /* ydnar: debug portals */ if( debugPortals ) MakeDebugPortalSurfs( tree ); /* ydnar: fog hull */ value = ValueForKey( &entities[ 0 ], "_foghull" ); if( value[ 0 ] != '\0' ) { sprintf( shader, "textures/%s", value ); MakeFogHullSurfs( e, tree, shader ); } /* ydnar: bug 645: do flares for lights */ for( i = 0; i < numEntities && emitFlares; i++ ) { entity_t *light, *target; const char *value, *flareShader; vec3_t origin, targetOrigin, normal, color; int lightStyle; /* get light */ light = &entities[ i ]; value = ValueForKey( light, "classname" ); if( !strcmp( value, "light" ) ) { /* get flare shader */ flareShader = ValueForKey( light, "_flareshader" ); value = ValueForKey( light, "_flare" ); if( flareShader[ 0 ] != '\0' || value[ 0 ] != '\0' ) { /* get specifics */ GetVectorForKey( light, "origin", origin ); GetVectorForKey( light, "_color", color ); lightStyle = IntForKey( light, "_style" ); if( lightStyle == 0 ) lightStyle = IntForKey( light, "style" ); /* handle directional spotlights */ value = ValueForKey( light, "target" ); if( value[ 0 ] != '\0' ) { /* get target light */ target = FindTargetEntity( value ); if( target != NULL ) { GetVectorForKey( target, "origin", targetOrigin ); VectorSubtract( targetOrigin, origin, normal ); VectorNormalize( normal, normal ); } } else //% VectorClear( normal ); VectorSet( normal, 0, 0, -1 ); /* create the flare surface (note shader defaults automatically) */ DrawSurfaceForFlare( mapEntityNum, origin, normal, color, (char*) flareShader, lightStyle ); } } } /* add references to the final drawsurfs in the apropriate clusters */ FilterDrawsurfsIntoTree( e, tree ); /* match drawsurfaces back to original brushsides (sof2) */ FixBrushSides( e ); /* finish */ EndModel( e, tree->headnode ); FreeTree( tree ); }
static void PopulateTraceNodes(void) { int i, m, frame, castShadows; float temp; entity_t *e; const char *value; picoModel_t *model; vec3_t origin, scale, angles; matrix_t rotation; matrix_t transform; /* add worldspawn triangles */ MatrixIdentity(transform); PopulateWithBSPModel(&bspModels[0], transform); /* walk each entity list */ for(i = 1; i < numEntities; i++) { /* get entity */ e = &entities[i]; /* get shadow flags */ castShadows = ENTITY_CAST_SHADOWS; GetEntityShadowFlags(e, NULL, &castShadows, NULL); /* early out? */ if(!castShadows) continue; /* get entity origin */ GetVectorForKey(e, "origin", origin); /* get "angle" (yaw) or "angles" (pitch yaw roll) */ MatrixIdentity(rotation); angles[0] = angles[1] = angles[2] = 0.0f; value = ValueForKey(e, "angle"); if(value[0] != '\0') { angles[1] = atof(value); MatrixFromAngles(rotation, angles[PITCH], angles[YAW], angles[ROLL]); } value = ValueForKey(e, "angles"); if(value[0] != '\0') { sscanf(value, "%f %f %f", &angles[0], &angles[1], &angles[2]); MatrixFromAngles(rotation, angles[PITCH], angles[YAW], angles[ROLL]); } value = ValueForKey(e, "rotation"); if(value[0] != '\0') { sscanf(value, "%f %f %f %f %f %f %f %f %f", &rotation[0], &rotation[1], &rotation[2], &rotation[4], &rotation[5], &rotation[6], &rotation[8], &rotation[9], &rotation[10]); } /* get scale */ scale[0] = scale[1] = scale[2] = 1.0f; temp = FloatForKey(e, "modelscale"); if(temp != 0.0f) scale[0] = scale[1] = scale[2] = temp; value = ValueForKey(e, "modelscale_vec"); if(value[0] != '\0') sscanf(value, "%f %f %f", &scale[0], &scale[1], &scale[2]); MatrixMultiplyScale(rotation, scale[0], scale[1], scale[2]); /* set transform matrix */ MatrixIdentity(transform); MatrixSetupTransformFromRotation(transform, rotation, origin); //% m4x4_pivoted_transform_by_vec3(transform, origin, angles, eXYZ, scale, vec3_origin); /* get model */ value = ValueForKey(e, "model"); /* switch on model type */ switch (value[0]) { /* no model */ case '\0': break; /* bsp model */ case '*': m = atoi(&value[1]); if(m <= 0 || m >= numBSPModels) continue; PopulateWithBSPModel(&bspModels[m], transform); break; /* external model */ default: frame = IntForKey(e, "_frame"); model = LoadModel((char *)value, frame); if(model == NULL) continue; PopulateWithPicoModel(castShadows, model, transform); continue; } /* get model2 */ value = ValueForKey(e, "model2"); /* switch on model type */ switch (value[0]) { /* no model */ case '\0': break; /* bsp model */ case '*': m = atoi(&value[1]); if(m <= 0 || m >= numBSPModels) continue; PopulateWithBSPModel(&bspModels[m], transform); break; /* external model */ default: frame = IntForKey(e, "_frame2"); model = LoadModel((char *)value, frame); if(model == NULL) continue; PopulateWithPicoModel(castShadows, model, transform); continue; } } }
// AJM: addded in // ===================================================================================== // GetParamsFromEnt // this function is called from parseentity when it encounters the // info_compile_parameters entity. each tool should have its own version of this // to handle its own specific settings. // ===================================================================================== void GetParamsFromEnt(entity_t* mapent) { int iTmp; Log("\nCompile Settings detected from info_compile_parameters entity\n"); // verbose(choices) : "Verbose compile messages" : 0 = [ 0 : "Off" 1 : "On" ] iTmp = IntForKey(mapent, "verbose"); if (iTmp == 1) { g_verbose = true; } else if (iTmp == 0) { g_verbose = false; } Log("%30s [ %-9s ]\n", "Compile Option", "setting"); Log("%30s [ %-9s ]\n", "Verbose Compile Messages", g_verbose ? "on" : "off"); // estimate(choices) :"Estimate Compile Times?" : 0 = [ 0: "Yes" 1: "No" ] if (IntForKey(mapent, "estimate")) { g_estimate = true; } else { g_estimate = false; } Log("%30s [ %-9s ]\n", "Estimate Compile Times", g_estimate ? "on" : "off"); // priority(choices) : "Priority Level" : 0 = [ 0 : "Normal" 1 : "High" -1 : "Low" ] if (!strcmp(ValueForKey(mapent, "priority"), "1")) { g_threadpriority = eThreadPriorityHigh; Log("%30s [ %-9s ]\n", "Thread Priority", "high"); } else if (!strcmp(ValueForKey(mapent, "priority"), "-1")) { g_threadpriority = eThreadPriorityLow; Log("%30s [ %-9s ]\n", "Thread Priority", "low"); } /* hlvis(choices) : "HLVIS" : 2 = [ 0 : "Off" 1 : "Fast" 2 : "Normal" 3 : "Full" ] */ iTmp = IntForKey(mapent, "hlvis"); if (iTmp == 0) { Fatal(assume_TOOL_CANCEL, "%s flag was not checked in info_compile_parameters entity, execution of %s cancelled", g_Program, g_Program); CheckFatal(); } else if (iTmp == 1) { g_fastvis = true; g_fullvis = false; } else if (iTmp == 2) { g_fastvis = false; g_fullvis = false; } else if (iTmp == 3) { g_fullvis = true; g_fastvis = false; } Log("%30s [ %-9s ]\n", "Fast VIS", g_fastvis ? "on" : "off"); Log("%30s [ %-9s ]\n", "Full VIS", g_fullvis ? "on" : "off" ); /////////////////// Log("\n"); }
//----------------------------------------------------------------------------- //----------------------------------------------------------------------------- int Overlay_GetFromEntity( entity_t *pMapEnt ) { int iAccessorID = -1; // Allocate the new overlay. int iOverlay = g_aMapOverlays.AddToTail(); mapoverlay_t *pMapOverlay = &g_aMapOverlays[iOverlay]; // Get the overlay data. pMapOverlay->nId = g_aMapOverlays.Count() - 1; if ( ValueForKey( pMapEnt, "targetname" )[ 0 ] != '\0' ) { // Overlay has a name, remember it's ID for accessing iAccessorID = pMapOverlay->nId; } pMapOverlay->flU[0] = FloatForKey( pMapEnt, "StartU" ); pMapOverlay->flU[1] = FloatForKey( pMapEnt, "EndU" ); pMapOverlay->flV[0] = FloatForKey( pMapEnt, "StartV" ); pMapOverlay->flV[1] = FloatForKey( pMapEnt, "EndV" ); pMapOverlay->flFadeDistMinSq = FloatForKey( pMapEnt, "fademindist" ); if ( pMapOverlay->flFadeDistMinSq > 0 ) { pMapOverlay->flFadeDistMinSq *= pMapOverlay->flFadeDistMinSq; } pMapOverlay->flFadeDistMaxSq = FloatForKey( pMapEnt, "fademaxdist" ); if ( pMapOverlay->flFadeDistMaxSq > 0 ) { pMapOverlay->flFadeDistMaxSq *= pMapOverlay->flFadeDistMaxSq; } GetVectorForKey( pMapEnt, "BasisOrigin", pMapOverlay->vecOrigin ); pMapOverlay->m_nRenderOrder = IntForKey( pMapEnt, "RenderOrder" ); if ( pMapOverlay->m_nRenderOrder < 0 || pMapOverlay->m_nRenderOrder >= OVERLAY_NUM_RENDER_ORDERS ) Error( "Overlay (%s) at %f %f %f has invalid render order (%d).\n", ValueForKey( pMapEnt, "material" ), pMapOverlay->vecOrigin ); GetVectorForKey( pMapEnt, "uv0", pMapOverlay->vecUVPoints[0] ); GetVectorForKey( pMapEnt, "uv1", pMapOverlay->vecUVPoints[1] ); GetVectorForKey( pMapEnt, "uv2", pMapOverlay->vecUVPoints[2] ); GetVectorForKey( pMapEnt, "uv3", pMapOverlay->vecUVPoints[3] ); GetVectorForKey( pMapEnt, "BasisU", pMapOverlay->vecBasis[0] ); GetVectorForKey( pMapEnt, "BasisV", pMapOverlay->vecBasis[1] ); GetVectorForKey( pMapEnt, "BasisNormal", pMapOverlay->vecBasis[2] ); const char *pMaterialName = ValueForKey( pMapEnt, "material" ); Assert( strlen( pMaterialName ) < OVERLAY_MAP_STRLEN ); if ( strlen( pMaterialName ) >= OVERLAY_MAP_STRLEN ) { Error( "Overlay Material Name (%s) too long! > OVERLAY_MAP_STRLEN (%d)", pMaterialName, OVERLAY_MAP_STRLEN ); return -1; } strcpy( pMapOverlay->szMaterialName, pMaterialName ); // Convert the sidelist to side id(s). const char *pSideList = ValueForKey( pMapEnt, "sides" ); char *pTmpList = ( char* )_alloca( strlen( pSideList ) + 1 ); strcpy( pTmpList, pSideList ); const char *pScan = strtok( pTmpList, " " ); if ( !pScan ) return iAccessorID; pMapOverlay->aSideList.Purge(); pMapOverlay->aFaceList.Purge(); do { int nSideId; if ( sscanf( pScan, "%d", &nSideId ) == 1 ) { pMapOverlay->aSideList.AddToTail( nSideId ); } } while ( ( pScan = strtok( NULL, " " ) ) ); return iAccessorID; }
/* =========== QE_LoadProject NOTE: rather than bumping "version", consider bumping "template_version" (see above) NOTE: when QE_LoadProject is called, the prefs are updated with path to the latest project and saved on disk =========== */ bool QE_LoadProject( const char *projectfile ){ char buf[1024]; xmlDocPtr doc; xmlNodePtr node, project; Sys_Printf( "Loading project file: \"%s\"\n", projectfile ); doc = ParseXMLFile( projectfile, true ); if ( doc == NULL ) { return false; } node = doc->children; while ( node != NULL && node->type != XML_DTD_NODE ) node = node->next; if ( node == NULL || strcmp( (char*)node->name, "project" ) != 0 ) { Sys_FPrintf( SYS_ERR, "ERROR: invalid file type\n" ); return false; } while ( node->type != XML_ELEMENT_NODE ) node = node->next; // <project> project = node; if ( g_qeglobals.d_project_entity != NULL ) { Entity_Free( g_qeglobals.d_project_entity ); } g_qeglobals.d_project_entity = Entity_Alloc(); for ( node = project->children; node != NULL; node = node->next ) { if ( node->type != XML_ELEMENT_NODE ) { continue; } // <key> ReplaceTemplates( buf, (char*)node->properties->next->children->content ); SetKeyValue( g_qeglobals.d_project_entity, (char*)node->properties->children->content, buf ); } xmlFreeDoc( doc ); // project file version checking // add a version checking to avoid people loading later versions of the project file and bitching int ver = IntForKey( g_qeglobals.d_project_entity, "version" ); if ( ver > PROJECT_VERSION ) { char strMsg[1024]; sprintf( strMsg, "This is a version %d project file. This build only supports <=%d project files.\n" "Please choose another project file or upgrade your version of Radiant.", ver, PROJECT_VERSION ); gtk_MessageBox( g_pParentWnd->m_pWidget, strMsg, "Can't load project file", MB_ICONERROR | MB_OK ); // set the project file to nothing so we are sure we'll ask next time? g_PrefsDlg.m_strLastProject = ""; g_PrefsDlg.SavePrefs(); return false; } // set here some default project settings you need if ( strlen( ValueForKey( g_qeglobals.d_project_entity, "brush_primit" ) ) == 0 ) { SetKeyValue( g_qeglobals.d_project_entity, "brush_primit", "0" ); } g_qeglobals.m_bBrushPrimitMode = IntForKey( g_qeglobals.d_project_entity, "brush_primit" ); g_qeglobals.m_strHomeMaps = g_qeglobals.m_strHomeGame; const char* str = ValueForKey( g_qeglobals.d_project_entity, "gamename" ); if ( str[0] == '\0' ) { str = g_pGameDescription->mBaseGame.GetBuffer(); } g_qeglobals.m_strHomeMaps += str; g_qeglobals.m_strHomeMaps += '/'; // don't forget to create the dirs Q_mkdir( g_qeglobals.m_strHomeGame.GetBuffer(), 0775 ); Q_mkdir( g_qeglobals.m_strHomeMaps.GetBuffer(), 0775 ); // usefull for the log file and debuggin f****d up configurations from users: // output the basic information of the .qe4 project file // SPoG // all these paths should be unix format, with a trailing slash at the end // if not.. to debug, check that the project file paths are set up correctly Sys_Printf( "basepath : %s\n", ValueForKey( g_qeglobals.d_project_entity, "basepath" ) ); Sys_Printf( "entitypath : %s\n", ValueForKey( g_qeglobals.d_project_entity, "entitypath" ) ); // check whether user_project key exists.. // if not, save the current project under a new name if ( ValueForKey( g_qeglobals.d_project_entity, "user_project" )[0] == '\0' ) { Sys_Printf( "Loaded a template project file\n" ); // create the user_project key SetKeyValue( g_qeglobals.d_project_entity, "user_project", "1" ); if ( IntForKey( g_qeglobals.d_project_entity, "version" ) != PROJECT_VERSION ) { char strMsg[2048]; sprintf( strMsg, "The template project '%s' has version %d. The editor binary is configured for version %d.\n" "This indicates a problem in your setup.\n" "I will keep going with this project till you fix this", projectfile, IntForKey( g_qeglobals.d_project_entity, "version" ), PROJECT_VERSION ); gtk_MessageBox( g_pParentWnd->m_pWidget, strMsg, "Can't load project file", MB_ICONERROR | MB_OK ); } // create the writable project file path strcpy( buf, g_qeglobals.m_strHomeGame.GetBuffer() ); strcat( buf, g_pGameDescription->mBaseGame.GetBuffer() ); strcat( buf, "/scripts/" ); // while the filename is already in use, increment the number we add to the end int counter = 0; char pUser[PATH_MAX]; while ( 1 ) { sprintf( pUser, "%suser%d." PROJECT_FILETYPE, buf, counter ); counter++; if ( access( pUser, R_OK ) != 0 ) { // this is the one strcpy( buf, pUser ); break; } } // saving project will cause a save prefs g_PrefsDlg.m_strLastProject = buf; g_PrefsDlg.m_nLastProjectVer = IntForKey( g_qeglobals.d_project_entity, "version" ); QE_SaveProject( buf ); } else { // update preferences::LastProject with path of this successfully-loaded project // save preferences Sys_Printf( "Setting current project in prefs to \"%s\"\n", g_PrefsDlg.m_strLastProject.GetBuffer() ); g_PrefsDlg.m_strLastProject = projectfile; g_PrefsDlg.SavePrefs(); } return true; }
/* =========== QE_LoadProject FIXME: the BuildShortPathName calls should be removed, it would get much more cleaner I don't have time to modify something so deep in the system, but this lead to a bug when loading .md3 see Win_ent.cpp AssignModel =========== */ qboolean QE_LoadProject (char *projectfile) { char *data; Sys_Printf ("QE_LoadProject (%s)\n", projectfile); if ( LoadFileNoCrash (projectfile, (void **)&data) == -1) return false; g_strProject = projectfile; CString strData = data; free(data); CString strQ2Path = g_PrefsDlg.m_strQuake2; CString strQ2File; ExtractPath_and_Filename(g_PrefsDlg.m_strQuake2, strQ2Path, strQ2File); AddSlash(strQ2Path); char* pBuff = new char[1024]; //BuildShortPathName(strQ2Path, pBuff, 1024); strcpy_s(pBuff, 1024,strQ2Path); // Jonathan: strcpy_s replaces BuildShortPathName FindReplace(strData, "__Q2PATH", pBuff); //BuildShortPathName(g_strAppPath, pBuff, 1024); strcpy_s(pBuff, 1024,g_strAppPath); // Jonathan: strcpy_s replaces BuildShortPathName FindReplace(strData, "__QERPATH", pBuff); char* pFile; if (GetFullPathName(projectfile, 1024, pBuff, &pFile)) { g_PrefsDlg.m_strLastProject = pBuff; //BuildShortPathName(g_PrefsDlg.m_strLastProject, pBuff, 1024); g_PrefsDlg.m_strLastProject = pBuff; g_PrefsDlg.SavePrefs(); ExtractPath_and_Filename(pBuff, strQ2Path, strQ2File); int nLen = strQ2Path.GetLength(); if (nLen > 0) { if (strQ2Path[nLen - 1] == '\\') strQ2Path.SetAt(nLen-1,'\0'); char* pBuffer = strQ2Path.GetBufferSetLength(_MAX_PATH + 1); int n = strQ2Path.ReverseFind('\\'); if (n >=0 ) pBuffer[n + 1] = '\0'; strQ2Path.ReleaseBuffer(); FindReplace(strData, "__QEPROJPATH", strQ2Path); } } StartTokenParsing (strData.GetBuffer(0)); g_qeglobals.d_project_entity = Entity_Parse (true); if (!g_qeglobals.d_project_entity) Error ("Couldn't parse project file: %s", projectfile); // add a version checking to avoid people loading later versions of the project file and bitching against me int ver = IntForKey( g_qeglobals.d_project_entity, "version" ); if (ver != 0) { char strMsg[1024]; sprintf( strMsg, "This is a version %d project file. This build only supports <=0 project files.\n" "Please choose another project file or upgrade your version of Radiant.", ver ); MessageBox( NULL, strMsg, "Can't load project file", MB_ICONERROR | MB_OK ); return false; } for (int i = 0; i < g_nPathFixupCount; i++) { char *pPath = ValueForKey (g_qeglobals.d_project_entity, g_pPathFixups[i]); if (pPath[0] != '\\' && pPath[0] != '/') { if (GetFullPathName(pPath, 1024, pBuff, &pFile)) { SetKeyValue(g_qeglobals.d_project_entity, g_pPathFixups[i], pBuff); } } } delete []pBuff; // set here some default project settings you need if ( strlen( ValueForKey( g_qeglobals.d_project_entity, "brush_primit" ) ) == 0 ) { SetKeyValue( g_qeglobals.d_project_entity, "brush_primit", "0" ); } g_qeglobals.m_bBrushPrimitMode = IntForKey( g_qeglobals.d_project_entity, "brush_primit" ); // usefull for the log file and debuggin f****d up configurations from users: // output the basic information of the .qe4 project file Sys_Printf("basepath : %s\n", ValueForKey( g_qeglobals.d_project_entity, "basepath") ); Sys_Printf("mapspath : %s\n", ValueForKey( g_qeglobals.d_project_entity, "mapspath") ); // the rsh command code is probably broken in these builds .. I would need ppl that actually use it .. // Sys_Printf("rshcmd : %s\n", ValueForKey( g_qeglobals.d_project_entity, "rshcmd" ) ); // Sys_Printf("remotebasepath : %s\n", ValueForKey( g_qeglobals.d_project_entity, "remotebasepath" ) ); Sys_Printf("entitypath : %s\n", ValueForKey( g_qeglobals.d_project_entity, "entitypath" ) ); Sys_Printf("texturepath : %s\n", ValueForKey( g_qeglobals.d_project_entity, "texturepath" ) ); Eclass_InitForSourceDirectory (ValueForKey (g_qeglobals.d_project_entity, "entitypath")); FillClassList(); // list in entity window Map_New(); FillTextureMenu(); FillBSPMenu(); return true; }
//----------------------------------------------------------------------------- // Places Detail Objects in the level //----------------------------------------------------------------------------- void EmitDetailModels() { StartPacifier("Placing detail props : "); // Place stuff on each face dface_t* pFace = dfaces; for (int j = 0; j < numfaces; ++j) { UpdatePacifier( (float)j / (float)numfaces ); // Get at the material associated with this face texinfo_t* pTexInfo = &texinfo[pFace[j].texinfo]; dtexdata_t* pTexData = GetTexData( pTexInfo->texdata ); // Try to get at the material bool found; MaterialSystemMaterial_t handle = FindOriginalMaterial( TexDataStringTable_GetString( pTexData->nameStringTableID ), &found, false ); if (!found) continue; // See if its got any detail objects on it const char* pDetailType = GetMaterialVar( handle, "%detailtype" ); if (!pDetailType) continue; // Get the detail type... DetailObject_t search; search.m_Name = pDetailType; int objectType = s_DetailObjectDict.Find(search); if (objectType < 0) { Warning("Material %s uses unknown detail object type %s!\n", TexDataStringTable_GetString( pTexData->nameStringTableID ), pDetailType); continue; } // Emit objects on a particular face DetailObject_t& detail = s_DetailObjectDict[objectType]; if (pFace[j].dispinfo < 0) { EmitDetailObjectsOnFace( &pFace[j], detail ); } else { // Get a CCoreDispInfo. All we need is the triangles and lightmap texture coordinates. mapdispinfo_t *pMapDisp = &mapdispinfo[pFace[j].dispinfo]; CCoreDispInfo coreDispInfo; DispMapToCoreDispInfo( pMapDisp, &coreDispInfo, &pFace[j] ); EmitDetailObjectsOnDisplacementFace( &pFace[j], detail, coreDispInfo ); } } // Emit specifically specified detail props Vector origin; QAngle angles; Vector2D pos[2]; Vector2D tex[2]; for (int i = 0; i < num_entities; ++i) { char* pEntity = ValueForKey(&entities[i], "classname"); if (!strcmp(pEntity, "detail_prop") || !strcmp(pEntity, "prop_detail")) { GetVectorForKey( &entities[i], "origin", origin ); GetAnglesForKey( &entities[i], "angles", angles ); char* pModelName = ValueForKey( &entities[i], "model" ); int nOrientation = IntForKey( &entities[i], "detailOrientation" ); AddDetailToLump( pModelName, origin, angles, nOrientation ); // strip this ent from the .bsp file entities[i].epairs = 0; continue; } if (!strcmp(pEntity, "prop_detail_sprite")) { GetVectorForKey( &entities[i], "origin", origin ); GetAnglesForKey( &entities[i], "angles", angles ); int nOrientation = IntForKey( &entities[i], "detailOrientation" ); GetVector2DForKey( &entities[i], "position_ul", pos[0] ); GetVector2DForKey( &entities[i], "position_lr", pos[1] ); GetVector2DForKey( &entities[i], "tex_ul", tex[0] ); GetVector2DForKey( &entities[i], "tex_size", tex[1] ); float flTextureSize = FloatForKey( &entities[i], "tex_total_size" ); tex[1].x += tex[0].x - 0.5f; tex[1].y += tex[0].y - 0.5f; tex[0].x += 0.5f; tex[0].y += 0.5f; tex[0] /= flTextureSize; tex[1] /= flTextureSize; AddDetailSpriteToLump( origin, angles, nOrientation, pos, tex, 1.0f ); // strip this ent from the .bsp file entities[i].epairs = 0; continue; } } EndPacifier( true ); }
static void PopulateTraceNodes( void ){ int i, m, frame, castShadows; float temp; entity_t *e; const char *value; picoModel_t *model; vec3_t origin, scale, angles; m4x4_t transform; /* add worldspawn triangles */ m4x4_identity( transform ); PopulateWithBSPModel( &bspModels[ 0 ], transform ); /* walk each entity list */ for ( i = 1; i < numEntities; i++ ) { /* get entity */ e = &entities[ i ]; /* get shadow flags */ castShadows = ENTITY_CAST_SHADOWS; GetEntityShadowFlags( e, NULL, &castShadows, NULL ); /* early out? */ if ( !castShadows ) { continue; } /* get entity origin */ GetVectorForKey( e, "origin", origin ); /* get scale */ scale[ 0 ] = scale[ 1 ] = scale[ 2 ] = 1.0f; temp = FloatForKey( e, "modelscale" ); if ( temp != 0.0f ) { scale[ 0 ] = scale[ 1 ] = scale[ 2 ] = temp; } value = ValueForKey( e, "modelscale_vec" ); if ( value[ 0 ] != '\0' ) { sscanf( value, "%f %f %f", &scale[ 0 ], &scale[ 1 ], &scale[ 2 ] ); } /* get "angle" (yaw) or "angles" (pitch yaw roll) */ angles[ 0 ] = angles[ 1 ] = angles[ 2 ] = 0.0f; angles[ 2 ] = FloatForKey( e, "angle" ); value = ValueForKey( e, "angles" ); if ( value[ 0 ] != '\0' ) { sscanf( value, "%f %f %f", &angles[ 1 ], &angles[ 2 ], &angles[ 0 ] ); } /* set transform matrix (thanks spog) */ m4x4_identity( transform ); m4x4_pivoted_transform_by_vec3( transform, origin, angles, eXYZ, scale, vec3_origin ); /* hack: Stable-1_2 and trunk have differing row/column major matrix order this transpose is necessary with Stable-1_2 uncomment the following line with old m4x4_t (non 1.3/spog_branch) code */ //% m4x4_transpose( transform ); /* get model */ value = ValueForKey( e, "model" ); /* switch on model type */ switch ( value[ 0 ] ) { /* no model */ case '\0': break; /* bsp model */ case '*': m = atoi( &value[ 1 ] ); if ( m <= 0 || m >= numBSPModels ) { continue; } PopulateWithBSPModel( &bspModels[ m ], transform ); break; /* external model */ default: frame = 0; if ( strcmp( "", ValueForKey( e, "_frame" ) ) ) { frame = IntForKey( e, "_frame" ); } else if ( strcmp( "", ValueForKey( e, "frame" ) ) ) { frame = IntForKey( e, "frame" ); } model = LoadModel( value, frame ); if ( model == NULL ) { continue; } PopulateWithPicoModel( castShadows, model, transform ); continue; } /* get model2 */ value = ValueForKey( e, "model2" ); /* switch on model type */ switch ( value[ 0 ] ) { /* no model */ case '\0': break; /* bsp model */ case '*': m = atoi( &value[ 1 ] ); if ( m <= 0 || m >= numBSPModels ) { continue; } PopulateWithBSPModel( &bspModels[ m ], transform ); break; /* external model */ default: frame = IntForKey( e, "_frame2" ); model = LoadModel( value, frame ); if ( model == NULL ) { continue; } PopulateWithPicoModel( castShadows, model, transform ); continue; } } }
void AddTriangleModels(entity_t * e) { int num, frame, castShadows, recvShadows, spawnFlags; entity_t *e2; const char *targetName; const char *target, *model, *value; char shader[MAX_QPATH]; shaderInfo_t *celShader; float temp, baseLightmapScale, lightmapScale; float shadeAngle; int lightmapSampleSize; vec3_t origin, scale, angles; matrix_t rotation, rotationScaled, transform; epair_t *ep; remap_t *remap, *remap2; char *split; /* note it */ Sys_FPrintf(SYS_VRB, "--- AddTriangleModels ---\n"); /* get current brush entity targetname */ if(e == entities) targetName = ""; else { targetName = ValueForKey(e, "name"); /* misc_model entities target non-worldspawn brush model entities */ if(targetName[0] == '\0') return; } /* get lightmap scale */ /* vortex: added _ls key (short name of lightmapscale) */ baseLightmapScale = 0.0f; if(strcmp("", ValueForKey(e, "lightmapscale")) || strcmp("", ValueForKey(e, "_lightmapscale")) || strcmp("", ValueForKey(e, "_ls"))) { baseLightmapScale = FloatForKey(e, "lightmapscale"); if(baseLightmapScale <= 0.0f) baseLightmapScale = FloatForKey(e, "_lightmapscale"); if(baseLightmapScale <= 0.0f) baseLightmapScale = FloatForKey(e, "_ls"); if(baseLightmapScale < 0.0f) baseLightmapScale = 0.0f; if(baseLightmapScale > 0.0f) Sys_Printf("World Entity has lightmap scale of %.4f\n", baseLightmapScale); } /* walk the entity list */ for(num = 1; num < numEntities; num++) { /* get e2 */ e2 = &entities[num]; /* convert misc_models into raw geometry */ if(Q_stricmp("misc_model", ValueForKey(e2, "classname"))) continue; /* ydnar: added support for md3 models on non-worldspawn models */ target = ValueForKey(e2, "target"); if(strcmp(target, targetName)) continue; /* get model name */ model = ValueForKey(e2, "model"); if(model[0] == '\0') { Sys_Printf("WARNING: misc_model at %i %i %i without a model key\n", (int)origin[0], (int)origin[1], (int)origin[2]); continue; } /* get model frame */ frame = IntForKey(e2, "_frame"); /* worldspawn (and func_groups) default to cast/recv shadows in worldspawn group */ if(e == entities) { castShadows = WORLDSPAWN_CAST_SHADOWS; recvShadows = WORLDSPAWN_RECV_SHADOWS; } /* other entities don't cast any shadows, but recv worldspawn shadows */ else { castShadows = ENTITY_CAST_SHADOWS; recvShadows = ENTITY_RECV_SHADOWS; } /* get explicit shadow flags */ GetEntityShadowFlags(e2, e, &castShadows, &recvShadows); /* get spawnflags */ spawnFlags = IntForKey(e2, "spawnflags"); /* Tr3B: added clipModel option */ spawnFlags |= (IntForKey(e2, "clipModel") > 0) ? 2 : 0; /* Tr3B: added forceMeta option */ spawnFlags |= (IntForKey(e2, "forceMeta") > 0) ? 4 : 0; /* get origin */ GetVectorForKey(e2, "origin", origin); VectorSubtract(origin, e->origin, origin); /* offset by parent */ /* get "angle" (yaw) or "angles" (pitch yaw roll) */ MatrixIdentity(rotation); angles[0] = angles[1] = angles[2] = 0.0f; value = ValueForKey(e2, "angle"); if(value[0] != '\0') { angles[1] = atof(value); MatrixFromAngles(rotation, angles[PITCH], angles[YAW], angles[ROLL]); } value = ValueForKey(e2, "angles"); if(value[0] != '\0') { sscanf(value, "%f %f %f", &angles[0], &angles[1], &angles[2]); MatrixFromAngles(rotation, angles[PITCH], angles[YAW], angles[ROLL]); } value = ValueForKey(e2, "rotation"); if(value[0] != '\0') { sscanf(value, "%f %f %f %f %f %f %f %f %f", &rotation[0], &rotation[1], &rotation[2], &rotation[4], &rotation[5], &rotation[6], &rotation[8], &rotation[9], &rotation[10]); } /* get scale */ scale[0] = scale[1] = scale[2] = 1.0f; temp = FloatForKey(e2, "modelscale"); if(temp != 0.0f) scale[0] = scale[1] = scale[2] = temp; value = ValueForKey(e2, "modelscale_vec"); if(value[0] != '\0') sscanf(value, "%f %f %f", &scale[0], &scale[1], &scale[2]); MatrixCopy(rotation, rotationScaled); MatrixMultiplyScale(rotationScaled, scale[0], scale[1], scale[2]); /* set transform matrix */ MatrixIdentity(transform); MatrixSetupTransformFromRotation(transform, rotationScaled, origin); /* get shader remappings */ remap = NULL; for(ep = e2->epairs; ep != NULL; ep = ep->next) { /* look for keys prefixed with "_remap" */ if(ep->key != NULL && ep->value != NULL && ep->key[0] != '\0' && ep->value[0] != '\0' && !Q_strncasecmp(ep->key, "_remap", 6)) { /* create new remapping */ remap2 = remap; remap = safe_malloc(sizeof(*remap)); remap->next = remap2; strcpy(remap->from, ep->value); /* split the string */ split = strchr(remap->from, ';'); if(split == NULL) { Sys_Printf("WARNING: Shader _remap key found in misc_model without a ; character\n"); free(remap); remap = remap2; continue; } /* store the split */ *split = '\0'; strcpy(remap->to, (split + 1)); /* note it */ //% Sys_FPrintf( SYS_VRB, "Remapping %s to %s\n", remap->from, remap->to ); } } /* ydnar: cel shader support */ value = ValueForKey(e2, "_celshader"); if(value[0] == '\0') value = ValueForKey(&entities[0], "_celshader"); if(value[0] != '\0') { sprintf(shader, "textures/%s", value); celShader = ShaderInfoForShader(shader); } else celShader = NULL; /* jal : entity based _samplesize */ lightmapSampleSize = 0; if(strcmp("", ValueForKey(e2, "_lightmapsamplesize"))) lightmapSampleSize = IntForKey(e2, "_lightmapsamplesize"); else if(strcmp("", ValueForKey(e2, "_samplesize"))) lightmapSampleSize = IntForKey(e2, "_samplesize"); if(lightmapSampleSize < 0) lightmapSampleSize = 0; if(lightmapSampleSize > 0.0f) Sys_Printf("misc_model has lightmap sample size of %.d\n", lightmapSampleSize); /* get lightmap scale */ /* vortex: added _ls key (short name of lightmapscale) */ lightmapScale = 0.0f; if(strcmp("", ValueForKey(e2, "lightmapscale")) || strcmp("", ValueForKey(e2, "_lightmapscale")) || strcmp("", ValueForKey(e2, "_ls"))) { lightmapScale = FloatForKey(e2, "lightmapscale"); if(lightmapScale <= 0.0f) lightmapScale = FloatForKey(e2, "_lightmapscale"); if(lightmapScale <= 0.0f) lightmapScale = FloatForKey(e2, "_ls"); if(lightmapScale < 0.0f) lightmapScale = 0.0f; if(lightmapScale > 0.0f) Sys_Printf("misc_model has lightmap scale of %.4f\n", lightmapScale); } /* jal : entity based _shadeangle */ shadeAngle = 0.0f; if(strcmp("", ValueForKey(e2, "_shadeangle"))) shadeAngle = FloatForKey(e2, "_shadeangle"); /* vortex' aliases */ else if(strcmp("", ValueForKey(mapEnt, "_smoothnormals"))) shadeAngle = FloatForKey(mapEnt, "_smoothnormals"); else if(strcmp("", ValueForKey(mapEnt, "_sn"))) shadeAngle = FloatForKey(mapEnt, "_sn"); else if(strcmp("", ValueForKey(mapEnt, "_smooth"))) shadeAngle = FloatForKey(mapEnt, "_smooth"); if(shadeAngle < 0.0f) shadeAngle = 0.0f; if(shadeAngle > 0.0f) Sys_Printf("misc_model has shading angle of %.4f\n", shadeAngle); /* insert the model */ InsertModel((char *)model, frame, transform, rotation, remap, celShader, mapEntityNum, castShadows, recvShadows, spawnFlags, lightmapScale, lightmapSampleSize, shadeAngle); /* free shader remappings */ while(remap != NULL) { remap2 = remap->next; free(remap); remap = remap2; } } }
void AddTriangleModel(entity_t * e) { int frame, castShadows, recvShadows, spawnFlags; const char *name, *model, *value; char shader[MAX_QPATH]; shaderInfo_t *celShader; float temp, baseLightmapScale, lightmapScale; float shadeAngle; int lightmapSampleSize; vec3_t scale; matrix_t rotation, transform; epair_t *ep; remap_t *remap, *remap2; char *split; /* note it */ Sys_FPrintf(SYS_VRB, "--- AddTriangleModel ---\n"); /* get current brush entity name */ name = ValueForKey(e, "name"); /* misc_model entities target non-worldspawn brush model entities */ if(name[0] == '\0') return; /* get model name */ model = ValueForKey(e, "model"); if(model[0] == '\0') return; /* Tr3B: skip triggers and other entities */ if(!Q_stricmp(name, model)) return; /* get model frame */ frame = IntForKey(e, "_frame"); /* worldspawn (and func_groups) default to cast/recv shadows in worldspawn group */ if(e == entities) { castShadows = WORLDSPAWN_CAST_SHADOWS; recvShadows = WORLDSPAWN_RECV_SHADOWS; } /* other entities don't cast any shadows, but recv worldspawn shadows */ else { castShadows = ENTITY_CAST_SHADOWS; recvShadows = ENTITY_RECV_SHADOWS; } /* get explicit shadow flags */ GetEntityShadowFlags(NULL, e, &castShadows, &recvShadows); /* get spawnflags */ spawnFlags = IntForKey(e, "spawnflags"); /* Tr3B: added clipModel option */ spawnFlags |= (IntForKey(e, "clipModel") > 0) ? 2 : 0; /* Tr3B: added forceMeta option */ spawnFlags |= (IntForKey(e, "forceMeta") > 0) ? 4 : 0; /* get scale */ scale[0] = scale[1] = scale[2] = 1.0f; temp = FloatForKey(e, "modelscale"); if(temp != 0.0f) scale[0] = scale[1] = scale[2] = temp; value = ValueForKey(e, "modelscale_vec"); if(value[0] != '\0') sscanf(value, "%f %f %f", &scale[0], &scale[1], &scale[2]); /* set transform matrix */ MatrixIdentity(transform); MatrixMultiplyScale(transform, scale[0], scale[1], scale[2]); MatrixIdentity(rotation); /* get shader remappings */ remap = NULL; for(ep = e->epairs; ep != NULL; ep = ep->next) { /* look for keys prefixed with "_remap" */ if(ep->key != NULL && ep->value != NULL && ep->key[0] != '\0' && ep->value[0] != '\0' && !Q_strncasecmp(ep->key, "_remap", 6)) { /* create new remapping */ remap2 = remap; remap = safe_malloc(sizeof(*remap)); remap->next = remap2; strcpy(remap->from, ep->value); /* split the string */ split = strchr(remap->from, ';'); if(split == NULL) { Sys_Printf("WARNING: Shader _remap key found in misc_model without a ; character\n"); free(remap); remap = remap2; continue; } /* store the split */ *split = '\0'; strcpy(remap->to, (split + 1)); /* note it */ //% Sys_FPrintf( SYS_VRB, "Remapping %s to %s\n", remap->from, remap->to ); } } /* ydnar: cel shader support */ value = ValueForKey(e, "_celshader"); if(value[0] == '\0') value = ValueForKey(&entities[0], "_celshader"); if(value[0] != '\0') { sprintf(shader, "textures/%s", value); celShader = ShaderInfoForShader(shader); } else celShader = NULL; /* get lightmap scale */ /* jal : entity based _samplesize */ lightmapSampleSize = 0; if(strcmp("", ValueForKey(e, "_lightmapsamplesize"))) lightmapSampleSize = IntForKey(e, "_lightmapsamplesize"); else if(strcmp("", ValueForKey(e, "_samplesize"))) lightmapSampleSize = IntForKey(e, "_samplesize"); if(lightmapSampleSize < 0) lightmapSampleSize = 0; if(lightmapSampleSize > 0.0f) Sys_Printf(" has lightmap sample size of %.d\n", lightmapSampleSize); /* get lightmap scale */ /* vortex: added _ls key (short name of lightmapscale) */ lightmapScale = 0.0f; if(strcmp("", ValueForKey(e, "lightmapscale")) || strcmp("", ValueForKey(e, "_lightmapscale")) || strcmp("", ValueForKey(e, "_ls"))) { lightmapScale = FloatForKey(e, "lightmapscale"); if(lightmapScale <= 0.0f) lightmapScale = FloatForKey(e, "_lightmapscale"); if(lightmapScale <= 0.0f) lightmapScale = FloatForKey(e, "_ls"); if(lightmapScale < 0.0f) lightmapScale = 0.0f; if(lightmapScale > 0.0f) Sys_Printf("misc_model has lightmap scale of %.4f\n", lightmapScale); } /* jal : entity based _shadeangle */ shadeAngle = 0.0f; if(strcmp("", ValueForKey(e, "_shadeangle"))) shadeAngle = FloatForKey(e, "_shadeangle"); /* vortex' aliases */ else if(strcmp("", ValueForKey(e, "_smoothnormals"))) shadeAngle = FloatForKey(e, "_smoothnormals"); else if(strcmp("", ValueForKey(e, "_sn"))) shadeAngle = FloatForKey(e, "_sn"); else if(strcmp("", ValueForKey(e, "_smooth"))) shadeAngle = FloatForKey(e, "_smooth"); if(shadeAngle < 0.0f) shadeAngle = 0.0f; if(shadeAngle > 0.0f) Sys_Printf("misc_model has shading angle of %.4f\n", shadeAngle); /* insert the model */ InsertModel((char *)model, frame, transform, rotation, remap, celShader, mapEntityNum, castShadows, recvShadows, spawnFlags, lightmapScale, lightmapSampleSize, shadeAngle); /* free shader remappings */ while(remap != NULL) { remap2 = remap->next; free(remap); remap = remap2; } }
void SetLightStyles( void ) { int i, j, style, numStyles; qboolean keepLights; const char *t; entity_t *e; epair_t *ep, *next; char value[ 10 ]; char lightTargets[ MAX_SWITCHED_LIGHTS ][ 64 ]; int lightStyles[ MAX_SWITCHED_LIGHTS ]; /* ydnar: determine if we keep lights in the bsp */ t = ValueForKey( &entities[ 0 ], "_keepLights" ); keepLights = (t[ 0 ] == '1') ? qtrue : qfalse; /* any light that is controlled (has a targetname) must have a unique style number generated for it */ numStyles = 0; for( i = 1; i < numEntities; i++ ) { e = &entities[ i ]; t = ValueForKey( e, "classname" ); if( Q_strncasecmp( t, "light", 5 ) ) continue; t = ValueForKey( e, "targetname" ); if( t[ 0 ] == '\0' ) { /* ydnar: strip the light from the BSP file */ if( keepLights == qfalse ) { ep = e->epairs; while( ep != NULL ) { next = ep->next; free( ep->key ); free( ep->value ); free( ep ); ep = next; } e->epairs = NULL; numStrippedLights++; } /* next light */ continue; } /* get existing style */ style = IntForKey( e, "style" ); if( style < LS_NORMAL || style > LS_NONE ) Error( "Invalid lightstyle (%d) on entity %d", style, i ); /* find this targetname */ for( j = 0; j < numStyles; j++ ) if( lightStyles[ j ] == style && !strcmp( lightTargets[ j ], t ) ) break; /* add a new style */ if( j >= numStyles ) { if( numStyles == MAX_SWITCHED_LIGHTS ) Error( "MAX_SWITCHED_LIGHTS (%d) exceeded, reduce the number of lights with targetnames", MAX_SWITCHED_LIGHTS ); strcpy( lightTargets[ j ], t ); lightStyles[ j ] = style; numStyles++; } /* set explicit style */ sprintf( value, "%d", 32 + j ); SetKeyValue( e, "style", value ); /* set old style */ if( style != LS_NORMAL ) { sprintf( value, "%d", style ); SetKeyValue( e, "switch_style", value ); } } /* emit some statistics */ Sys_FPrintf( SYS_VRB, "%9d light entities stripped\n", numStrippedLights ); }
static void ProcessAdvertisements( void ) { int i; const char* className; const char* modelKey; int modelNum; bspModel_t* adModel; bspDrawSurface_t* adSurface; Sys_FPrintf( SYS_VRB, "--- ProcessAdvertisements ---\n" ); for ( i = 0; i < numEntities; i++ ) { /* is an advertisement? */ className = ValueForKey( &entities[ i ], "classname" ); if ( !Q_stricmp( "advertisement", className ) ) { modelKey = ValueForKey( &entities[ i ], "model" ); if ( strlen( modelKey ) > MAX_QPATH - 1 ) { Error( "Model Key for entity exceeds ad struct string length." ); } else { if ( numBSPAds < MAX_MAP_ADVERTISEMENTS ) { bspAds[numBSPAds].cellId = IntForKey( &entities[ i ], "cellId" ); strncpy( bspAds[numBSPAds].model, modelKey, sizeof( bspAds[numBSPAds].model ) ); modelKey++; modelNum = atoi( modelKey ); adModel = &bspModels[modelNum]; if ( adModel->numBSPSurfaces != 1 ) { Error( "Ad cell id %d has more than one surface.", bspAds[numBSPAds].cellId ); } adSurface = &bspDrawSurfaces[adModel->firstBSPSurface]; // store the normal for use at run time.. all ad verts are assumed to // have identical normals (because they should be a simple rectangle) // so just use the first vert's normal VectorCopy( bspDrawVerts[adSurface->firstVert].normal, bspAds[numBSPAds].normal ); // store the ad quad for quick use at run time if ( adSurface->surfaceType == MST_PATCH ) { int v0 = adSurface->firstVert + adSurface->patchHeight - 1; int v1 = adSurface->firstVert + adSurface->numVerts - 1; int v2 = adSurface->firstVert + adSurface->numVerts - adSurface->patchWidth; int v3 = adSurface->firstVert; VectorCopy( bspDrawVerts[v0].xyz, bspAds[numBSPAds].rect[0] ); VectorCopy( bspDrawVerts[v1].xyz, bspAds[numBSPAds].rect[1] ); VectorCopy( bspDrawVerts[v2].xyz, bspAds[numBSPAds].rect[2] ); VectorCopy( bspDrawVerts[v3].xyz, bspAds[numBSPAds].rect[3] ); } else { Error( "Ad cell %d has an unsupported Ad Surface type.", bspAds[numBSPAds].cellId ); } numBSPAds++; } else { Error( "Maximum number of map advertisements exceeded." ); } } } } Sys_FPrintf( SYS_VRB, "%9d in-game advertisements\n", numBSPAds ); }
void EmitStaticProps() { CreateInterfaceFn physicsFactory = GetPhysicsFactory(); if ( physicsFactory ) { s_pPhysCollision = (IPhysicsCollision *)physicsFactory( VPHYSICS_COLLISION_INTERFACE_VERSION, NULL ); if( !s_pPhysCollision ) return; } // Generate a list of lighting origins, and strip them out int i; for ( i = 0; i < num_entities; ++i) { char* pEntity = ValueForKey(&entities[i], "classname"); if (!Q_strcmp(pEntity, "info_lighting")) { s_LightingInfo.AddToTail(i); } } // Emit specifically specified static props for ( i = 0; i < num_entities; ++i) { char* pEntity = ValueForKey(&entities[i], "classname"); if (!strcmp(pEntity, "static_prop") || !strcmp(pEntity, "prop_static")) { StaticPropBuild_t build; GetVectorForKey( &entities[i], "origin", build.m_Origin ); GetAnglesForKey( &entities[i], "angles", build.m_Angles ); build.m_pModelName = ValueForKey( &entities[i], "model" ); build.m_Solid = IntForKey( &entities[i], "solid" ); build.m_Skin = IntForKey( &entities[i], "skin" ); build.m_FadeMaxDist = FloatForKey( &entities[i], "fademaxdist" ); build.m_Flags = 0;//IntForKey( &entities[i], "spawnflags" ) & STATIC_PROP_WC_MASK; if (IntForKey( &entities[i], "disableshadows" ) == 1) { build.m_Flags |= STATIC_PROP_NO_SHADOW; } if (IntForKey( &entities[i], "disablevertexlighting" ) == 1) { build.m_Flags |= STATIC_PROP_NO_PER_VERTEX_LIGHTING; } if (IntForKey( &entities[i], "disableselfshadowing" ) == 1) { build.m_Flags |= STATIC_PROP_NO_SELF_SHADOWING; } if (IntForKey( &entities[i], "screenspacefade" ) == 1) { build.m_Flags |= STATIC_PROP_SCREEN_SPACE_FADE; } const char *pKey = ValueForKey( &entities[i], "fadescale" ); if ( pKey && pKey[0] ) { build.m_flForcedFadeScale = FloatForKey( &entities[i], "fadescale" ); } else { build.m_flForcedFadeScale = 1; } build.m_FadesOut = (build.m_FadeMaxDist > 0); build.m_pLightingOrigin = ValueForKey( &entities[i], "lightingorigin" ); if (build.m_FadesOut) { build.m_FadeMinDist = FloatForKey( &entities[i], "fademindist" ); if (build.m_FadeMinDist < 0) { build.m_FadeMinDist = build.m_FadeMaxDist; } } else { build.m_FadeMinDist = 0; } AddStaticPropToLump( build ); // strip this ent from the .bsp file entities[i].epairs = 0; } } // Strip out lighting origins; has to be done here because they are used when // static props are made for ( i = s_LightingInfo.Count(); --i >= 0; ) { // strip this ent from the .bsp file entities[s_LightingInfo[i]].epairs = 0; } SetLumpData( ); }