/* ============ ProcessModels ============ */ void ProcessModels (void) { BeginBSPFile (); // Mark sides that have no dynamic shadows. MarkNoDynamicShadowSides(); // emit the displacement surfaces EmitInitialDispInfos(); // Clip occluder brushes against each other, // Remove them from the list of models to process below EmitOccluderBrushes( ); for ( entity_num=0; entity_num < num_entities; ++entity_num ) { entity_t *pEntity = &entities[entity_num]; if ( !pEntity->numbrushes ) continue; qprintf ("############### model %i ###############\n", nummodels); BeginModel (); if (entity_num == 0) { ProcessWorldModel(); } else { ProcessSubModel( ); } EndModel (); if (!verboseentities) { verbose = false; // don't bother printing submodels } } // Turn the skybox into a cubemap in case we don't build env_cubemap textures. Cubemap_CreateDefaultCubemaps(); EndBSPFile (); }
/* * @brief */ static void ProcessModels(void) { BeginBSPFile(); for (entity_num = 0; entity_num < num_entities; entity_num++) { if (!entities[entity_num].num_brushes) continue; Com_Verbose("############### model %i ###############\n", d_bsp.num_models); BeginModel(); if (entity_num == 0) ProcessWorldModel(); else ProcessSubModel(); EndModel(); } EndBSPFile(); }
/* ============ ProcessModels ============ */ void ProcessModels (void) { BeginBSPFile (); for (entity_num=0 ; entity_num< num_entities ; entity_num++) { if (!entities[entity_num].numbrushes) continue; qprintf ("############### model %i ###############\n", nummodels); BeginModel (); if (entity_num == 0) ProcessWorldModel (); else ProcessSubModel (); EndModel (); if (!verboseentities) verbose = false; // don't bother printing submodels } EndBSPFile (); }
/** * @sa ProcessWorldModel * @sa ProcessSubModel */ void ProcessModels (const char* filename) { int entity_num; BeginBSPFile(); for (entity_num = 0; entity_num < num_entities; entity_num++) { if (!entities[entity_num].numbrushes) continue; Verb_Printf(VERB_EXTRA, "############### model %i ###############\n", curTile->nummodels); if (entity_num == 0) ProcessWorldModel(entity_num); else ProcessSubModel(entity_num); if (!config.verboseentities) config.verbose = false; /* don't bother printing submodels */ } EndBSPFile(filename); }
int BSPMain( int argc, char **argv ) { int i; char path[ 1024 ], tempSource[ 1024 ]; qboolean onlyents = qfalse; /* note it */ Sys_Printf( "--- BSP ---\n" ); SetDrawSurfacesBuffer(); mapDrawSurfs = safe_malloc( sizeof( mapDrawSurface_t ) * MAX_MAP_DRAW_SURFS ); memset( mapDrawSurfs, 0, sizeof( mapDrawSurface_t ) * MAX_MAP_DRAW_SURFS ); numMapDrawSurfs = 0; tempSource[ 0 ] = '\0'; /* set standard game flags */ maxSurfaceVerts = game->maxSurfaceVerts; maxSurfaceIndexes = game->maxSurfaceIndexes; emitFlares = game->emitFlares; /* process arguments */ for( i = 1; i < (argc - 1); i++ ) { if( !strcmp( argv[ i ], "-onlyents" ) ) { Sys_Printf( "Running entity-only compile\n" ); onlyents = qtrue; } else if( !strcmp( argv[ i ], "-tempname" ) ) strcpy( tempSource, argv[ ++i ] ); else if( !strcmp( argv[ i ], "-tmpout" ) ) strcpy( outbase, "/tmp" ); else if( !strcmp( argv[ i ], "-nowater" ) ) { Sys_Printf( "Disabling water\n" ); nowater = qtrue; } else if( !strcmp( argv[ i ], "-nodetail" ) ) { Sys_Printf( "Ignoring detail brushes\n") ; nodetail = qtrue; } else if( !strcmp( argv[ i ], "-fulldetail" ) ) { Sys_Printf( "Turning detail brushes into structural brushes\n" ); fulldetail = qtrue; } else if( !strcmp( argv[ i ], "-nofog" ) ) { Sys_Printf( "Fog volumes disabled\n" ); nofog = qtrue; } else if( !strcmp( argv[ i ], "-nosubdivide" ) ) { Sys_Printf( "Disabling brush face subdivision\n" ); nosubdivide = qtrue; } else if( !strcmp( argv[ i ], "-leaktest" ) ) { Sys_Printf( "Leaktest enabled\n" ); leaktest = qtrue; } else if( !strcmp( argv[ i ], "-verboseentities" ) ) { Sys_Printf( "Verbose entities enabled\n" ); verboseEntities = qtrue; } else if( !strcmp( argv[ i ], "-nocurves" ) ) { Sys_Printf( "Ignoring curved surfaces (patches)\n" ); noCurveBrushes = qtrue; } else if( !strcmp( argv[ i ], "-notjunc" ) ) { Sys_Printf( "T-junction fixing disabled\n" ); notjunc = qtrue; } else if( !strcmp( argv[ i ], "-fakemap" ) ) { Sys_Printf( "Generating fakemap.map\n" ); fakemap = qtrue; } else if( !strcmp( argv[ i ], "-samplesize" ) ) { sampleSize = atoi( argv[ i + 1 ] ); if( sampleSize < 1 ) sampleSize = 1; i++; Sys_Printf( "Lightmap sample size set to %dx%d units\n", sampleSize, sampleSize ); } else if( !strcmp( argv[ i ], "-custinfoparms") ) { Sys_Printf( "Custom info parms enabled\n" ); useCustomInfoParms = qtrue; } /* sof2 args */ else if( !strcmp( argv[ i ], "-rename" ) ) { Sys_Printf( "Appending _bsp suffix to misc_model shaders (SOF2)\n" ); renameModelShaders = qtrue; } /* ydnar args */ else if( !strcmp( argv[ i ], "-ne" ) ) { normalEpsilon = atof( argv[ i + 1 ] ); i++; Sys_Printf( "Normal epsilon set to %f\n", normalEpsilon ); } else if( !strcmp( argv[ i ], "-de" ) ) { distanceEpsilon = atof( argv[ i + 1 ] ); i++; Sys_Printf( "Distance epsilon set to %f\n", distanceEpsilon ); } else if( !strcmp( argv[ i ], "-mv" ) ) { maxLMSurfaceVerts = atoi( argv[ i + 1 ] ); if( maxLMSurfaceVerts < 3 ) maxLMSurfaceVerts = 3; if( maxLMSurfaceVerts > maxSurfaceVerts ) maxSurfaceVerts = maxLMSurfaceVerts; i++; Sys_Printf( "Maximum lightmapped surface vertex count set to %d\n", maxLMSurfaceVerts ); } else if( !strcmp( argv[ i ], "-mi" ) ) { maxSurfaceIndexes = atoi( argv[ i + 1 ] ); if( maxSurfaceIndexes < 3 ) maxSurfaceIndexes = 3; i++; Sys_Printf( "Maximum per-surface index count set to %d\n", maxSurfaceIndexes ); } else if( !strcmp( argv[ i ], "-np" ) ) { npDegrees = atof( argv[ i + 1 ] ); if( npDegrees < 0.0f ) shadeAngleDegrees = 0.0f; else if( npDegrees > 0.0f ) Sys_Printf( "Forcing nonplanar surfaces with a breaking angle of %f degrees\n", npDegrees ); i++; } else if( !strcmp( argv[ i ], "-snap" ) ) { bevelSnap = atoi( argv[ i + 1 ]); if( bevelSnap < 0 ) bevelSnap = 0; i++; if( bevelSnap > 0 ) Sys_Printf( "Snapping brush bevel planes to %d units\n", bevelSnap ); } else if( !strcmp( argv[ i ], "-texrange" ) ) { texRange = atoi( argv[ i + 1 ]); if( texRange < 0 ) texRange = 0; i++; Sys_Printf( "Limiting per-surface texture range to %d texels\n", texRange ); } else if( !strcmp( argv[ i ], "-nohint" ) ) { Sys_Printf( "Hint brushes disabled\n" ); noHint = qtrue; } else if( !strcmp( argv[ i ], "-flat" ) ) { Sys_Printf( "Flatshading enabled\n" ); flat = qtrue; } else if( !strcmp( argv[ i ], "-meta" ) ) { Sys_Printf( "Creating meta surfaces from brush faces\n" ); meta = qtrue; } else if( !strcmp( argv[ i ], "-patchmeta" ) ) { Sys_Printf( "Creating meta surfaces from patches\n" ); patchMeta = qtrue; } else if( !strcmp( argv[ i ], "-flares" ) ) { Sys_Printf( "Flare surfaces enabled\n" ); emitFlares = qtrue; } else if( !strcmp( argv[ i ], "-noflares" ) ) { Sys_Printf( "Flare surfaces disabled\n" ); emitFlares = qfalse; } else if( !strcmp( argv[ i ], "-skyfix" ) ) { Sys_Printf( "GL_CLAMP sky fix/hack/workaround enabled\n" ); skyFixHack = qtrue; } else if( !strcmp( argv[ i ], "-debugsurfaces" ) ) { Sys_Printf( "emitting debug surfaces\n" ); debugSurfaces = qtrue; } else if( !strcmp( argv[ i ], "-debuginset" ) ) { Sys_Printf( "Debug surface triangle insetting enabled\n" ); debugInset = qtrue; } else if( !strcmp( argv[ i ], "-debugportals" ) ) { Sys_Printf( "Debug portal surfaces enabled\n" ); debugPortals = qtrue; } else if( !strcmp( argv[ i ], "-bsp" ) ) Sys_Printf( "-bsp argument unnecessary\n" ); else Sys_Printf( "WARNING: Unknown option \"%s\"\n", argv[ i ] ); } /* fixme: print more useful usage here */ if( i != (argc - 1) ) Error( "usage: q3map [options] mapfile" ); /* copy source name */ strcpy( source, ExpandArg( argv[ i ] ) ); StripExtension( source ); /* ydnar: set default sample size */ SetDefaultSampleSize( sampleSize ); /* delete portal, line and surface files */ sprintf( path, "%s.prt", source ); remove( path ); sprintf( path, "%s.lin", source ); remove( path ); //% sprintf( path, "%s.srf", source ); /* ydnar */ //% remove( path ); /* expand mapname */ strcpy( name, ExpandArg( argv[ i ] ) ); if( strcmp( name + strlen( name ) - 4, ".reg" ) ) { /* if we are doing a full map, delete the last saved region map */ sprintf( path, "%s.reg", source ); remove( path ); DefaultExtension( name, ".map" ); /* might be .reg */ } /* if onlyents, just grab the entites and resave */ if( onlyents ) { OnlyEnts(); return 0; } /* load shaders */ LoadShaderInfo(); /* load original file from temp spot in case it was renamed by the editor on the way in */ if( strlen( tempSource ) > 0 ) LoadMapFile( tempSource, qfalse ); else LoadMapFile( name, qfalse ); /* ydnar: decal setup */ ProcessDecals(); /* ydnar: cloned brush model entities */ SetCloneModelNumbers(); /* process world and submodels */ ProcessModels(); /* set light styles from targetted light entities */ SetLightStyles(); /* finish and write bsp */ EndBSPFile(); /* remove temp map source file if appropriate */ if( strlen( tempSource ) > 0) remove( tempSource ); /* return to sender */ return 0; }
int main (int argc, char **argv) { int i; double start, end; char path[1024]; _printf ("Q3Map v1.0s (c) 1999 Id Software Inc.\n"); _printf ("OMmap (su44) - v0.1\n"); if ( argc < 2 ) { Error ("usage: q3map [options] mapfile"); } // check for general program options if (!strcmp(argv[1], "-info")) { Bspinfo( argc - 2, argv + 2 ); return 0; } if (!strcmp(argv[1], "-light")) { LightMain( argc - 1, argv + 1 ); return 0; } if (!strcmp(argv[1], "-vlight")) { VLightMain( argc - 1, argv + 1 ); return 0; } if (!strcmp(argv[1], "-vsound")) { VSoundMain( argc - 1, argv + 1 ); return 0; } if (!strcmp(argv[1], "-vis")) { VisMain( argc - 1, argv + 1 ); return 0; } // do a bsp if nothing else was specified _printf ("---- q3map ----\n"); tempsource[0] = '\0'; for (i=1 ; i<argc ; i++) { if (!strcmp(argv[i],"-tempname")) { strcpy(tempsource, argv[++i]); } else if (!strcmp(argv[i],"-threads")) { numthreads = atoi (argv[i+1]); i++; } else if (!strcmp(argv[i],"-glview")) { glview = qtrue; } else if (!strcmp(argv[i], "-v")) { _printf ("verbose = true\n"); verbose = qtrue; } else if (!strcmp(argv[i], "-draw")) { _printf ("drawflag = true\n"); drawflag = qtrue; } else if (!strcmp(argv[i], "-nowater")) { _printf ("nowater = true\n"); nowater = qtrue; } else if (!strcmp(argv[i], "-noopt")) { _printf ("noopt = true\n"); noopt = qtrue; } else if (!strcmp(argv[i], "-nofill")) { _printf ("nofill = true\n"); nofill = qtrue; } else if (!strcmp(argv[i], "-nodetail")) { _printf ("nodetail = true\n"); nodetail = qtrue; } else if (!strcmp(argv[i], "-fulldetail")) { _printf ("fulldetail = true\n"); fulldetail = qtrue; } else if (!strcmp(argv[i], "-onlyents")) { _printf ("onlyents = true\n"); onlyents = qtrue; } else if (!strcmp(argv[i], "-onlytextures")) { _printf ("onlytextures = true\n"); // FIXME: make work again! onlytextures = qtrue; } else if (!strcmp(argv[i], "-micro")) { microvolume = atof(argv[i+1]); _printf ("microvolume = %f\n", microvolume); i++; } else if (!strcmp(argv[i], "-nofog")) { _printf ("nofog = true\n"); nofog = qtrue; } else if (!strcmp(argv[i], "-nosubdivide")) { _printf ("nosubdivide = true\n"); nosubdivide = qtrue; } else if (!strcmp(argv[i], "-leaktest")) { _printf ("leaktest = true\n"); leaktest = qtrue; } else if (!strcmp(argv[i], "-verboseentities")) { _printf ("verboseentities = true\n"); verboseentities = qtrue; } else if (!strcmp(argv[i], "-nocurves")) { noCurveBrushes = qtrue; _printf ("no curve brushes\n"); } else if (!strcmp(argv[i], "-notjunc")) { notjunc = qtrue; _printf ("no tjunction fixing\n"); } else if (!strcmp(argv[i], "-expand")) { testExpand = qtrue; _printf ("Writing expanded.map.\n"); } else if (!strcmp(argv[i], "-showseams")) { showseams = qtrue; _printf ("Showing seams on terrain.\n"); } else if (!strcmp (argv[i],"-tmpout")) { strcpy (outbase, "/tmp"); } else if (!strcmp (argv[i],"-fakemap")) { fakemap = qtrue; _printf( "will generate fakemap.map\n"); } else if (!strcmp(argv[i], "-samplesize")) { samplesize = atoi(argv[i+1]); if (samplesize < 1) samplesize = 1; i++; _printf("lightmap sample size is %dx%d units\n", samplesize, samplesize); } else if (argv[i][0] == '-') Error ("Unknown option \"%s\"", argv[i]); else break; } if (i != argc - 1) Error ("usage: q3map [options] mapfile"); start = I_FloatTime (); ThreadSetDefault (); //numthreads = 1; // multiple threads aren't helping because of heavy malloc use SetQdirFromPath (argv[i]); #ifdef _WIN32 InitPakFile(gamedir, NULL); #endif strcpy (source, ExpandArg (argv[i])); StripExtension (source); // delete portal and line files sprintf (path, "%s.prt", source); remove (path); sprintf (path, "%s.lin", source); remove (path); strcpy (name, ExpandArg (argv[i])); if ( strcmp(name + strlen(name) - 4, ".reg" ) ) { // if we are doing a full map, delete the last saved region map sprintf (path, "%s.reg", source); remove (path); DefaultExtension (name, ".map"); // might be .reg } // // if onlyents, just grab the entites and resave // if ( onlyents ) { OnlyEnts(); return 0; } // // if onlytextures, just grab the textures and resave // if ( onlytextures ) { OnlyTextures(); return 0; } // // start from scratch // LoadShaderInfo(); // load original file from temp spot in case it was renamed by the editor on the way in if (strlen(tempsource) > 0) { LoadMapFile (tempsource); } else { LoadMapFile (name); } SetModelNumbers (); SetLightStyles (); ProcessModels (); EndBSPFile(); end = I_FloatTime (); _printf ("%5.0f seconds elapsed\n", end-start); // remove temp name if appropriate if (strlen(tempsource) > 0) { remove(tempsource); } return 0; }
int BspMain(int argc, char **argv) { int i; double start, end; char path[1024]; Sys_Printf("---- bsp ----\n"); for(i = 1; i < argc; i++) { if(!strcmp(argv[i], "-threads")) { numthreads = atoi(argv[i + 1]); i++; } else if(!strcmp(argv[i], "-glview")) { glview = qtrue; } else if(!strcmp(argv[i], "-v")) { Sys_Printf("verbose = true\n"); verbose = qtrue; } else if(!strcmp(argv[i], "-draw")) { Sys_Printf("drawflag = true\n"); drawFlag = qtrue; } else if(!strcmp(argv[i], "-debugsurfaces")) { Sys_Printf("emitting debug surfaces\n"); debugSurfaces = qtrue; } else if(!strcmp(argv[i], "-nowater")) { Sys_Printf("nowater = true\n"); noliquids = qtrue; } else if(!strcmp(argv[i], "-nodetail")) { Sys_Printf("nodetail = true\n"); nodetail = qtrue; } else if(!strcmp(argv[i], "-fulldetail")) { Sys_Printf("fulldetail = true\n"); fulldetail = qtrue; } else if(!strcmp(argv[i], "-onlyents")) { Sys_Printf("onlyents = true\n"); onlyents = qtrue; } else if(!strcmp(argv[i], "-onlytextures")) { Sys_Printf("onlytextures = true\n"); // FIXME: make work again! onlytextures = qtrue; } else if(!strcmp(argv[i], "-micro")) { microvolume = atof(argv[i + 1]); Sys_Printf("microvolume = %f\n", microvolume); i++; } else if(!strcmp(argv[i], "-nofog")) { Sys_Printf("nofog = true\n"); nofog = qtrue; } else if(!strcmp(argv[i], "-nosubdivide")) { Sys_Printf("nosubdivide = true\n"); nosubdivide = qtrue; } else if(!strcmp(argv[i], "-leaktest")) { Sys_Printf("leaktest = true\n"); leaktest = qtrue; } else if(!strcmp(argv[i], "-nocurves")) { nocurves = qtrue; Sys_Printf("no curve brushes\n"); } else if(!strcmp(argv[i], "-nodoors")) { nodoors = qtrue; Sys_Printf("no door entities\n"); } else if(!strcmp(argv[i], "-notjunc")) { notjunc = qtrue; Sys_Printf("no tjunction fixing\n"); } else if(!strcmp(argv[i], "-expand")) { testExpand = qtrue; Sys_Printf("Writing expanded.map.\n"); } else if(!strcmp(argv[i], "-showseams")) { showseams = qtrue; Sys_Printf("Showing seams on terrain.\n"); } else if(!strcmp(argv[i], "-tmpout")) { strcpy(outbase, "/tmp"); } else if(!strcmp(argv[i], "-fakemap")) { fakemap = qtrue; Sys_Printf("will generate fakemap.map\n"); } else if(!strcmp(argv[i], "-samplesize")) { samplesize = atoi(argv[i + 1]); if(samplesize < 1) samplesize = 1; i++; Sys_Printf("lightmap sample size is %dx%d units\n", samplesize, samplesize); } else if(!strcmp(argv[i], "-connect")) { Broadcast_Setup(argv[++i]); } else if(argv[i][0] == '-') Error("Unknown option \"%s\"", argv[i]); else break; } if(i != argc - 1) { Error("usage: xmap -map2bsp [-<switch> [-<switch> ...]] <mapname.map>\n" "\n" "Switches:\n" " v = verbose output\n" " threads <X> = set number of threads to X\n" " nocurves = don't emit bezier surfaces\n" " nodoors = disable door entities\n" //" breadthfirst = breadth first bsp building\n" //" nobrushmerge = don't merge brushes\n" " noliquids = don't write liquids to map\n" //" nocsg = disables brush chopping\n" //" glview = output a GL view\n" " draw = enables mini BSP viewer\n" //" noweld = disables weld\n" //" noshare = disables sharing\n" " notjunc = disables juncs\n" " nowater = disables water brushes\n" //" noprune = disables node prunes\n" //" nomerge = disables face merging\n" " nofog = disables fogs\n" " nosubdivide = disables subdivision of draw surfaces\n" " nodetail = disables detail brushes\n" " fulldetail = enables full detail\n" " onlyents = only compile entities with bsp\n" " micro <volume>\n" " = sets the micro volume to the given float\n" " leaktest = perform a leak test\n" //" chop <subdivide_size>\n" //" = sets the subdivide size to the given float\n" " samplesize <N> = set the lightmap pixel size to NxN units\n"); } start = I_FloatTime(); ThreadSetDefault(); SetQdirFromPath(argv[i]); strcpy(source, ExpandArg(argv[i])); StripExtension(source); // delete portal and line files sprintf(path, "%s.prt", source); remove(path); sprintf(path, "%s.lin", source); remove(path); strcpy(name, ExpandArg(argv[i])); if(strcmp(name + strlen(name) - 4, ".reg")) { // if we are doing a full map, delete the last saved region map sprintf(path, "%s.reg", source); remove(path); DefaultExtension(name, ".map"); // might be .reg } // if onlyents, just grab the entites and resave if(onlyents) { OnlyEnts(); // shut down connection Broadcast_Shutdown(); return 0; } // if onlytextures, just grab the textures and resave if(onlytextures) { OnlyTextures(); // shut down connection Broadcast_Shutdown(); return 0; } // start from scratch LoadShaderInfo(); LoadMapFile(name); ProcessModels(); SetModelNumbers(); EndBSPFile(); end = I_FloatTime(); Sys_Printf("%5.0f seconds elapsed\n", end - start); // shut down connection Broadcast_Shutdown(); return 0; }
/* PseudoCompileBSP() a stripped down ProcessModels */ void PseudoCompileBSP( qboolean need_tree, const char *BSPFilePath, const char *surfaceFilePath ){ int models; char modelValue[10]; entity_t *entity; face_t *faces; tree_t *tree; node_t *node; brush_t *brush; side_t *side; int i; SetDrawSurfacesBuffer(); mapDrawSurfs = safe_malloc( sizeof( mapDrawSurface_t ) * MAX_MAP_DRAW_SURFS ); memset( mapDrawSurfs, 0, sizeof( mapDrawSurface_t ) * MAX_MAP_DRAW_SURFS ); numMapDrawSurfs = 0; BeginBSPFile(); models = 1; for ( mapEntityNum = 0; mapEntityNum < numEntities; mapEntityNum++ ) { /* get entity */ entity = &entities[ mapEntityNum ]; if ( entity->brushes == NULL && entity->patches == NULL ) { continue; } if ( mapEntityNum != 0 ) { sprintf( modelValue, "*%d", models++ ); SetKeyValue( entity, "model", modelValue ); } /* process the model */ Sys_FPrintf( SYS_VRB, "############### model %i ###############\n", numBSPModels ); BeginModel(); entity->firstDrawSurf = numMapDrawSurfs; ClearMetaTriangles(); PatchMapDrawSurfs( entity ); if ( mapEntityNum == 0 && need_tree ) { faces = MakeStructuralBSPFaceList( entities[0].brushes ); tree = FaceBSP( faces ); node = tree->headnode; } else { node = AllocNode(); node->planenum = PLANENUM_LEAF; tree = AllocTree(); tree->headnode = node; } /* a minimized ClipSidesIntoTree */ for ( brush = entity->brushes; brush; brush = brush->next ) { /* walk the brush sides */ for ( i = 0; i < brush->numsides; i++ ) { /* get side */ side = &brush->sides[ i ]; if ( side->winding == NULL ) { continue; } /* shader? */ if ( side->shaderInfo == NULL ) { continue; } /* save this winding as a visible surface */ DrawSurfaceForSide( entity, brush, side, side->winding ); } } if ( meta ) { ClassifyEntitySurfaces( entity ); MakeEntityDecals( entity ); MakeEntityMetaTriangles( entity ); SmoothMetaTriangles(); MergeMetaTriangles(); } FilterDrawsurfsIntoTree( entity, tree ); FilterStructuralBrushesIntoTree( entity, tree ); FilterDetailBrushesIntoTree( entity, tree ); EmitBrushes( entity->brushes, &entity->firstBrush, &entity->numBrushes ); EndModel( entity, node ); } EndBSPFile( qfalse, BSPFilePath, surfaceFilePath ); }