Code Search for Developers
 
 
  

bspc.c from Nxabega at Krugle


Show bspc.c syntax highlighted

/*
===========================================================================
Copyright (C) 1999-2005 Id Software, Inc.

This file is part of Quake III Arena source code.

Quake III Arena source code is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License as
published by the Free Software Foundation; either version 2 of the License,
or (at your option) any later version.

Quake III Arena source code is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with Foobar; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
===========================================================================
*/

#if defined(WIN32) || defined(_WIN32)
#include <direct.h>
#include <windows.h>
#include <sys/types.h>
#include <sys/stat.h>
#else
#include <unistd.h>
#include <glob.h>
#include <sys/stat.h>
#include <unistd.h>
#endif
#include "qbsp.h"
#include "l_mem.h"
#include "../botlib/aasfile.h"
#include "../botlib/be_aas_cluster.h"
#include "../botlib/be_aas_optimize.h"
#include "aas_create.h"
#include "aas_store.h"
#include "aas_file.h"
#include "aas_cfg.h"
#include "be_aas_bspc.h"

extern int      use_nodequeue;	//brushbsp.c
extern int      calcgrapplereach;	//be_aas_reach.c

float           subdivide_size = 240;
char            source[1024];
char            name[1024];
vec_t           microvolume = 1.0;
char            outbase[32];
int             entity_num;
aas_settings_t  aassettings;

qboolean        noprune;		//don't prune nodes (bspc.c)
qboolean        glview;			//create a gl view
qboolean        nodetail;		//don't use detail brushes (map.c)
qboolean        fulldetail;		//use but don't mark detail brushes (map.c)
qboolean        onlyents;		//only process the entities (bspc.c)
qboolean        nomerge;		//don't merge bsp node faces (faces.c)
qboolean        nowater;		//don't use the water brushes (map.c)
qboolean        nocsg;			//don't carve intersecting brushes (bspc.c)
qboolean        noweld;			//use unique face vertexes (faces.c)
qboolean        noshare;		//don't share bsp edges (faces.c)
qboolean        nosubdiv;		//don't subdivide bsp node faces (faces.c)
qboolean        notjunc;		//don't create tjunctions (edge melting) (faces.c)
qboolean        optimize;		//enable optimisation
qboolean        leaktest;		//perform a leak test
qboolean        verboseentities;
qboolean        freetree;		//free the bsp tree when not needed anymore
qboolean        create_aas;		//create an .AAS file
qboolean        nobrushmerge;	//don't merge brushes
qboolean        lessbrushes;	//create less brushes instead of correct texture placement
qboolean        cancelconversion;	//true if the conversion is being cancelled
qboolean        noliquids;		//no liquids when writing map file
qboolean        forcesidesvisible;	//force all brush sides to be visible when loaded from bsp
qboolean        capsule_collision = 0;

/*
//===========================================================================
//
// Parameter:			-
// Returns:				-
// Changes Globals:		-
//===========================================================================
void ProcessWorldModel (void)
{
	entity_t	*e;
	tree_t *tree;
	qboolean	leaked;
	int brush_start, brush_end;

	e = &entities[entity_num];

	brush_start = e->firstbrush;
	brush_end = brush_start + e->numbrushes;
	leaked = false;

	//process the whole world in one time
	tree = ProcessWorldBrushes(brush_start, brush_end);
	//create the bsp tree portals
	MakeTreePortals(tree);
	//mark all leafs that can be reached by entities
	if (FloodEntities(tree))
	{
		FillOutside(tree->headnode);
	} //end if
	else
	{
		Log_Print("**** leaked ****\n");
		leaked = true;
		LeakFile(tree);
		if (leaktest)
		{
			Log_Print("--- MAP LEAKED ---\n");
			exit(0);
		} //end if
	} //end else

	MarkVisibleSides (tree, brush_start, brush_end);

	FloodAreas (tree);

#ifndef ME
	if (glview) WriteGLView(tree, source);
#endif
	MakeFaces(tree->headnode);
	FixTjuncs(tree->headnode);

	//NOTE: Never prune the nodes because the portals
	//		are screwed when prunning is done and as
	//		a result portal writing will crash
	//if (!noprune) PruneNodes(tree->headnode);

	WriteBSP(tree->headnode);

	if (!leaked) WritePortalFile(tree);

	Tree_Free(tree);
} //end of the function ProcessWorldModel
//===========================================================================
//
// Parameter:			-
// Returns:				-
// Changes Globals:		-
//===========================================================================
void ProcessSubModel (void)
{
	entity_t	*e;
	int start, end;
	tree_t *tree;
	bspbrush_t *list;
	vec3_t mins, maxs;

	e = &entities[entity_num];

	start = e->firstbrush;
	end = start + e->numbrushes;

	mins[0] = mins[1] = mins[2] = -4096;
	maxs[0] = maxs[1] = maxs[2] = 4096;
	list = MakeBspBrushList(start, end, mins, maxs);
	if (!nocsg) list = ChopBrushes (list);
	tree = BrushBSP (list, mins, maxs);
	MakeTreePortals (tree);
	MarkVisibleSides (tree, start, end);
	MakeFaces (tree->headnode);
	FixTjuncs (tree->headnode);
	WriteBSP (tree->headnode);
	Tree_Free(tree);
} //end of the function ProcessSubModel
//===========================================================================
//
// Parameter:			-
// Returns:				-
// Changes Globals:		-
//===========================================================================
void ProcessModels (void)
{
	BeginBSPFile();

	for (entity_num = 0; entity_num < num_entities; entity_num++)
	{
		if (!entities[entity_num].numbrushes)
			continue;

		Log_Print("############### model %i ###############\n", nummodels);
		BeginModel();
		if (entity_num == 0) ProcessWorldModel();
		else ProcessSubModel();
		EndModel();

		if (!verboseentities)
			verbose = false;	// don't bother printing submodels
	} //end for
	EndBSPFile();
} //end of the function ProcessModels
//===========================================================================
//
// Parameter:			-
// Returns:				-
// Changes Globals:		-
//===========================================================================
void Win_Map2Bsp(char *bspfilename)
{
	double start, end;
	char path[1024];

	start = I_FloatTime();

	ThreadSetDefault();
	//yeah sure Carmack
	//numthreads = 1;		// multiple threads aren't helping...

	strcpy(source, ExpandArg(bspfilename));
	StripExtension(source);

	//delete portal and line files
	sprintf(path, "%s.prt", source);
	remove(path);
	sprintf(path, "%s.lin", source);
	remove(path);

	strcpy(name, ExpandArg(bspfilename));	
	DefaultExtension(name, ".map");	// might be .reg

	Q2_AllocMaxBSP();
	//
	SetModelNumbers();
	SetLightStyles();
	ProcessModels();
	//write the BSP
	Q2_WriteBSPFile(bspfilename);

	Q2_FreeMaxBSP();

	end = I_FloatTime();
	Log_Print("%5.0f seconds elapsed\n", end-start);
} //end of the function Win_Map2Bsp
//===========================================================================
//
// Parameter:			-
// Returns:				-
// Changes Globals:		-
//===========================================================================
void Map2Bsp(char *mapfilename, char *outputfilename)
{
	double start, end;
	char path[1024];

	start = I_FloatTime ();

	ThreadSetDefault ();
	//yeah sure Carmack
	//numthreads = 1;		//multiple threads aren't helping...
	//SetQdirFromPath(bspfilename);

	strcpy(source, ExpandArg(mapfilename));
	StripExtension(source);

	// delete portal and line files
	sprintf(path, "%s.prt", source);
	remove(path);
	sprintf(path, "%s.lin", source);
	remove(path);

	strcpy(name, ExpandArg(mapfilename));
	DefaultExtension(name, ".map");	// might be .reg

	//
	// if onlyents, just grab the entites and resave
	//
	if (onlyents)
	{
		char out[1024];

		Q2_AllocMaxBSP();
		sprintf (out, "%s.bsp", source);
		Q2_LoadBSPFile(out, 0, 0);
		num_entities = 0;

		Q2_LoadMapFile(name);
		SetModelNumbers();
		SetLightStyles();

		Q2_UnparseEntities();

		Q2_WriteBSPFile(out);
		//
		Q2_FreeMaxBSP();
	} //end if
	else
	{
		//
		// start from scratch
		//
		Q2_AllocMaxBSP();
		//load the map
		Q2_LoadMapFile(name);
		//create the .bsp file
		SetModelNumbers();
		SetLightStyles();
		ProcessModels();
		//write the BSP
		Q2_WriteBSPFile(outputfilename);
		//
		Q2_FreeMaxBSP();
	} //end else

	end = I_FloatTime();
	Log_Print("%5.0f seconds elapsed\n", end-start);
} //end of the function Map2Bsp
*/
//===========================================================================
//
// Parameter:           -
// Returns:             -
// Changes Globals:     -
//===========================================================================
void AASOuputFile(quakefile_t * qf, char *outputpath, char *filename)
{
	char            ext[MAX_PATH];

	//
	if(strlen(outputpath))
	{
		strcpy(filename, outputpath);
		//append the bsp file base
		AppendPathSeperator(filename, MAX_PATH);
		ExtractFileBase(qf->origname, &filename[strlen(filename)]);
		//append .aas
		strcat(filename, ".aas");
		return;
	}							//end if
	//
	ExtractFileExtension(qf->filename, ext);
	if(!_stricmp(ext, "pk3") || !_stricmp(ext, "pak") || !_stricmp(ext, "sin"))
	{
		strcpy(filename, qf->filename);
		while(strlen(filename) && filename[strlen(filename) - 1] != '\\' && filename[strlen(filename) - 1] != '/')
		{
			filename[strlen(filename) - 1] = '\0';
		}						//end while
		strcat(filename, "maps");
		if(_access(filename, 0x04))
			CreatePath(filename);
		//append the bsp file base
		AppendPathSeperator(filename, MAX_PATH);
		ExtractFileBase(qf->origname, &filename[strlen(filename)]);
		//append .aas
		strcat(filename, ".aas");
	}							//end if
	else
	{
		strcpy(filename, qf->filename);
		while(strlen(filename) && filename[strlen(filename) - 1] != '.')
		{
			filename[strlen(filename) - 1] = '\0';
		}						//end while
		strcat(filename, "aas");
	}							//end else
}								//end of the function AASOutputFile

//===========================================================================
//
// Parameter:           -
// Returns:             -
// Changes Globals:     -
//===========================================================================
void CreateAASFilesForAllBSPFiles(char *quakepath)
{
#if defined(WIN32)|defined(_WIN32)
	WIN32_FIND_DATA filedata;
	HWND            handle;
	struct _stat    statbuf;
#else
	glob_t          globbuf;
	struct stat     statbuf;
	int             j;
#endif
	int             done;
	char            filter[_MAX_PATH], bspfilter[_MAX_PATH], aasfilter[_MAX_PATH];
	char            aasfile[_MAX_PATH], buf[_MAX_PATH], foldername[_MAX_PATH];
	quakefile_t    *qf, *qf2, *files, *bspfiles, *aasfiles;

	strcpy(filter, quakepath);
	AppendPathSeperator(filter, sizeof(filter));
	strcat(filter, "*");

#if defined(WIN32)|defined(_WIN32)
	handle = FindFirstFile(filter, &filedata);
	done = (handle == INVALID_HANDLE_VALUE);
	while(!done)
	{
		_splitpath(filter, foldername, NULL, NULL, NULL);
		_splitpath(filter, NULL, &foldername[strlen(foldername)], NULL, NULL);
		AppendPathSeperator(foldername, _MAX_PATH);
		strcat(foldername, filedata.cFileName);
		_stat(foldername, &statbuf);
#else
	glob(filter, 0, NULL, &globbuf);
	for(j = 0; j < globbuf.gl_pathc; j++)
	{
		strcpy(foldername, globbuf.gl_pathv[j]);
		stat(foldername, &statbuf);
#endif
		//if it is a folder
		if(statbuf.st_mode & S_IFDIR)
		{
			//
			AppendPathSeperator(foldername, sizeof(foldername));
			//get all the bsp files
			strcpy(bspfilter, foldername);
			strcat(bspfilter, "maps/*.bsp");
			files = FindQuakeFiles(bspfilter);
			strcpy(bspfilter, foldername);
			strcat(bspfilter, "*.pk3/maps/*.bsp");
			bspfiles = FindQuakeFiles(bspfilter);
			for(qf = bspfiles; qf; qf = qf->next)
				if(!qf->next)
					break;
			if(qf)
				qf->next = files;
			else
				bspfiles = files;
			//get all the aas files
			strcpy(aasfilter, foldername);
			strcat(aasfilter, "maps/*.aas");
			files = FindQuakeFiles(aasfilter);
			strcpy(aasfilter, foldername);
			strcat(aasfilter, "*.pk3/maps/*.aas");
			aasfiles = FindQuakeFiles(aasfilter);
			for(qf = aasfiles; qf; qf = qf->next)
				if(!qf->next)
					break;
			if(qf)
				qf->next = files;
			else
				aasfiles = files;
			//
			for(qf = bspfiles; qf; qf = qf->next)
			{
				sprintf(aasfile, "%s/%s", qf->pakfile, qf->origname);
				Log_Print("found %s\n", aasfile);
				strcpy(&aasfile[strlen(aasfile) - strlen(".bsp")], ".aas");
				for(qf2 = aasfiles; qf2; qf2 = qf2->next)
				{
					sprintf(buf, "%s/%s", qf2->pakfile, qf2->origname);
					if(!_stricmp(aasfile, buf))
					{
						Log_Print("found %s\n", buf);
						break;
					}			//end if
				}				//end for
			}					//end for
		}						//end if
#if defined(WIN32)|defined(_WIN32)
		//find the next file
		done = !FindNextFile(handle, &filedata);
	}							//end while
#else
	}							//end for
	globfree(&globbuf);
#endif
}								//end of the function CreateAASFilesForAllBSPFiles

//===========================================================================
//
// Parameter:           -
// Returns:             -
// Changes Globals:     -
//===========================================================================
quakefile_t    *GetArgumentFiles(int argc, char *argv[], int *i, char *ext)
{
	quakefile_t    *qfiles, *lastqf, *qf;
	int             j;
	char            buf[1024];

	qfiles = NULL;
	lastqf = NULL;
	for(; (*i) + 1 < argc && argv[(*i) + 1][0] != '-'; (*i)++)
	{
		strcpy(buf, argv[(*i) + 1]);
		for(j = strlen(buf) - 1; j >= strlen(buf) - 4; j--)
			if(buf[j] == '.')
				break;
		if(j >= strlen(buf) - 4)
			strcpy(&buf[j + 1], ext);
		qf = FindQuakeFiles(buf);
		if(!qf)
			continue;
		if(lastqf)
			lastqf->next = qf;
		else
			qfiles = qf;
		lastqf = qf;
		while(lastqf->next)
			lastqf = lastqf->next;
	}							//end for
	return qfiles;
}								//end of the function GetArgumentFiles

//===========================================================================
//
// Parameter:           -
// Returns:             -
// Changes Globals:     -
//===========================================================================

#define COMP_BSP2MAP		1
#define COMP_BSP2AAS		2
#define COMP_REACH			3
#define COMP_CLUSTER		4
#define COMP_AASOPTIMIZE	5
#define COMP_AASINFO		6

int main(int argc, char **argv)
{
	int             i, comp = 0;
	char            outputpath[MAX_PATH] = "";
	char            filename[MAX_PATH] = "unknown";
	quakefile_t    *qfiles = NULL, *qf;
	double          start_time;

	myargc = argc;
	myargv = argv;

	start_time = I_FloatTime();

	Log_Open("bspc.log");		//open a log file
	Log_Print("BSPC version " BSPC_VERSION ", %s %s\n", __DATE__, __TIME__);

	DefaultCfg();
	for(i = 1; i < argc; i++)
	{
		if(!_stricmp(argv[i], "-threads"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			numthreads = atoi(argv[++i]);
			Log_Print("threads = %d\n", numthreads);
		}						//end if
		else if(!_stricmp(argv[i], "-noverbose"))
		{
			Log_Print("verbose = false\n");
			verbose = false;
		}						//end else if
		else if(!_stricmp(argv[i], "-nocsg"))
		{
			Log_Print("nocsg = true\n");
			nocsg = true;
		}						//end else if
		else if(!_stricmp(argv[i], "-optimize"))
		{
			Log_Print("optimize = true\n");
			optimize = true;
		}						//end else if
		/*
		   else if (!stricmp(argv[i],"-glview"))
		   {
		   glview = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-draw"))
		   {
		   Log_Print("drawflag = true\n");
		   drawflag = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-noweld"))
		   {
		   Log_Print("noweld = true\n");
		   noweld = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-noshare"))
		   {
		   Log_Print("noshare = true\n");
		   noshare = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-notjunc"))
		   {
		   Log_Print("notjunc = true\n");
		   notjunc = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-nowater"))
		   {
		   Log_Print("nowater = true\n");
		   nowater = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-noprune"))
		   {
		   Log_Print("noprune = true\n");
		   noprune = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-nomerge"))
		   {
		   Log_Print("nomerge = true\n");
		   nomerge = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-nosubdiv"))
		   {
		   Log_Print("nosubdiv = true\n");
		   nosubdiv = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-nodetail"))
		   {
		   Log_Print("nodetail = true\n");
		   nodetail = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-fulldetail"))
		   {
		   Log_Print("fulldetail = true\n");
		   fulldetail = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-onlyents"))
		   {
		   Log_Print("onlyents = true\n");
		   onlyents = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-micro"))
		   {
		   if (i + 1 >= argc) {i = 0; break;}
		   microvolume = atof(argv[++i]);
		   Log_Print("microvolume = %f\n", microvolume);
		   } //end else if
		   else if (!stricmp(argv[i], "-leaktest"))
		   {
		   Log_Print("leaktest = true\n");
		   leaktest = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-verboseentities"))
		   {
		   Log_Print("verboseentities = true\n");
		   verboseentities = true;
		   } //end else if
		   else if (!stricmp(argv[i], "-chop"))
		   {
		   if (i + 1 >= argc) {i = 0; break;}
		   subdivide_size = atof(argv[++i]);
		   Log_Print("subdivide_size = %f\n", subdivide_size);
		   } //end else if
		   else if (!stricmp (argv[i], "-tmpout"))
		   {
		   strcpy (outbase, "/tmp");
		   Log_Print("temp output\n");
		   } //end else if
		 */
#ifdef ME
		else if(!_stricmp(argv[i], "-freetree"))
		{
			freetree = true;
			Log_Print("freetree = true\n");
		}						//end else if
		else if(!_stricmp(argv[i], "-grapplereach"))
		{
			calcgrapplereach = true;
			Log_Print("grapplereach = true\n");
		}						//end else if
		else if(!_stricmp(argv[i], "-nobrushmerge"))
		{
			nobrushmerge = true;
			Log_Print("nobrushmerge = true\n");
		}						//end else if
		else if(!_stricmp(argv[i], "-noliquids"))
		{
			noliquids = true;
			Log_Print("noliquids = true\n");
		}						//end else if
		else if(!_stricmp(argv[i], "-forcesidesvisible"))
		{
			forcesidesvisible = true;
			Log_Print("forcesidesvisible = true\n");
		}						//end else if
		else if(!_stricmp(argv[i], "-output"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			if(_access(argv[i + 1], 0x04))
				Warning("the folder %s does not exist", argv[i + 1]);
			strcpy(outputpath, argv[++i]);
		}						//end else if
		else if(!_stricmp(argv[i], "-breadthfirst"))
		{
			use_nodequeue = true;
			Log_Print("breadthfirst = true\n");
		}						//end else if
		else if(!_stricmp(argv[i], "-capsule"))
		{
			capsule_collision = true;
			Log_Print("capsule_collision = true\n");
		}						//end else if
		else if(!_stricmp(argv[i], "-cfg"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			if(!LoadCfgFile(argv[++i]))
				exit(0);
		}						//end else if
		else if(!_stricmp(argv[i], "-bsp2map"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			comp = COMP_BSP2MAP;
			qfiles = GetArgumentFiles(argc, argv, &i, "bsp");
		}						//end else if
		else if(!_stricmp(argv[i], "-bsp2aas"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			comp = COMP_BSP2AAS;
			qfiles = GetArgumentFiles(argc, argv, &i, "bsp");
		}						//end else if
		else if(!_stricmp(argv[i], "-aasall"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			CreateAASFilesForAllBSPFiles(argv[++i]);
		}						//end else if
		else if(!_stricmp(argv[i], "-reach"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			comp = COMP_REACH;
			qfiles = GetArgumentFiles(argc, argv, &i, "bsp");
		}						//end else if
		else if(!_stricmp(argv[i], "-cluster"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			comp = COMP_CLUSTER;
			qfiles = GetArgumentFiles(argc, argv, &i, "bsp");
		}						//end else if
		else if(!_stricmp(argv[i], "-aasinfo"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			comp = COMP_AASINFO;
			qfiles = GetArgumentFiles(argc, argv, &i, "aas");
		}						//end else if
		else if(!_stricmp(argv[i], "-aasopt"))
		{
			if(i + 1 >= argc)
			{
				i = 0;
				break;
			}
			comp = COMP_AASOPTIMIZE;
			qfiles = GetArgumentFiles(argc, argv, &i, "aas");
		}						//end else if
#endif							//ME
		else
		{
			Log_Print("unknown parameter %s\n", argv[i]);
			break;
		}						//end else
	}							//end for

	//if there are parameters and there's no mismatch in one of the parameters
	if(argc > 1 && i == argc)
	{
		switch (comp)
		{
			case COMP_BSP2MAP:
			{
				if(!qfiles)
					Log_Print("no files found\n");
				for(qf = qfiles; qf; qf = qf->next)
				{
					//copy the output path
					strcpy(filename, outputpath);
					//append the bsp file base
					AppendPathSeperator(filename, MAX_PATH);
					ExtractFileBase(qf->origname, &filename[strlen(filename)]);
					//append .map
					strcat(filename, ".map");
					//
					Log_Print("bsp2map: %s to %s\n", qf->origname, filename);
					if(qf->type != QFILETYPE_BSP)
						Warning("%s is probably not a BSP file\n", qf->origname);
					//
					LoadMapFromBSP(qf);
					//write the map file
					WriteMapFile(filename);
				}				//end for
				break;
			}					//end case
			case COMP_BSP2AAS:
			{
				if(!qfiles)
					Log_Print("no files found\n");
				for(qf = qfiles; qf; qf = qf->next)
				{
					AASOuputFile(qf, outputpath, filename);
					//
					Log_Print("bsp2aas: %s to %s\n", qf->origname, filename);
					if(qf->type != QFILETYPE_BSP)
						Warning("%s is probably not a BSP file\n", qf->origname);
					//set before map loading
					create_aas = 1;
					LoadMapFromBSP(qf);
					//create the AAS file
					AAS_Create(filename);
					//if it's a Quake3 map calculate the reachabilities and clusters
					if(loadedmaptype == MAPTYPE_QUAKE3)
						AAS_CalcReachAndClusters(qf);
					//
					if(optimize)
						AAS_Optimize();
					//
					//write out the stored AAS file
					if(!AAS_WriteAASFile(filename))
					{
						Error("error writing %s\n", filename);
					}			//end if
					//deallocate memory
					AAS_FreeMaxAAS();
				}				//end for
				break;
			}					//end case
			case COMP_REACH:
			{
				if(!qfiles)
					Log_Print("no files found\n");
				for(qf = qfiles; qf; qf = qf->next)
				{
					AASOuputFile(qf, outputpath, filename);
					//
					Log_Print("reach: %s to %s\n", qf->origname, filename);
					if(qf->type != QFILETYPE_BSP)
						Warning("%s is probably not a BSP file\n", qf->origname);
					//if the AAS file exists in the output directory
					if(!_access(filename, 0x04))
					{
						if(!AAS_LoadAASFile(filename, 0, 0))
						{
							Error("error loading aas file %s\n", filename);
						}		//end if
						//assume it's a Quake3 BSP file
						loadedmaptype = MAPTYPE_QUAKE3;
					}			//end if
					else
					{
						Warning("AAS file %s not found in output folder\n", filename);
						Log_Print("creating %s...\n", filename);
						//set before map loading
						create_aas = 1;
						LoadMapFromBSP(qf);
						//create the AAS file
						AAS_Create(filename);
					}			//end else
					//if it's a Quake3 map calculate the reachabilities and clusters
					if(loadedmaptype == MAPTYPE_QUAKE3)
					{
						AAS_CalcReachAndClusters(qf);
					}			//end if
					//
					if(optimize)
						AAS_Optimize();
					//write out the stored AAS file
					if(!AAS_WriteAASFile(filename))
					{
						Error("error writing %s\n", filename);
					}			//end if
					//deallocate memory
					AAS_FreeMaxAAS();
				}				//end for
				break;
			}					//end case
			case COMP_CLUSTER:
			{
				if(!qfiles)
					Log_Print("no files found\n");
				for(qf = qfiles; qf; qf = qf->next)
				{
					AASOuputFile(qf, outputpath, filename);
					//
					Log_Print("cluster: %s to %s\n", qf->origname, filename);
					if(qf->type != QFILETYPE_BSP)
						Warning("%s is probably not a BSP file\n", qf->origname);
					//if the AAS file exists in the output directory
					if(!_access(filename, 0x04))
					{
						if(!AAS_LoadAASFile(filename, 0, 0))
						{
							Error("error loading aas file %s\n", filename);
						}		//end if
						//assume it's a Quake3 BSP file
						loadedmaptype = MAPTYPE_QUAKE3;
						//if it's a Quake3 map calculate the clusters
						if(loadedmaptype == MAPTYPE_QUAKE3)
						{
							aasworld.numclusters = 0;
							AAS_InitBotImport();
							AAS_InitClustering();
						}		//end if
					}			//end if
					else
					{
						Warning("AAS file %s not found in output folder\n", filename);
						Log_Print("creating %s...\n", filename);
						//set before map loading
						create_aas = 1;
						LoadMapFromBSP(qf);
						//create the AAS file
						AAS_Create(filename);
						//if it's a Quake3 map calculate the reachabilities and clusters
						if(loadedmaptype == MAPTYPE_QUAKE3)
							AAS_CalcReachAndClusters(qf);
					}			//end else
					//
					if(optimize)
						AAS_Optimize();
					//write out the stored AAS file
					if(!AAS_WriteAASFile(filename))
					{
						Error("error writing %s\n", filename);
					}			//end if
					//deallocate memory
					AAS_FreeMaxAAS();
				}				//end for
				break;
			}					//end case
			case COMP_AASOPTIMIZE:
			{
				if(!qfiles)
					Log_Print("no files found\n");
				for(qf = qfiles; qf; qf = qf->next)
				{
					AASOuputFile(qf, outputpath, filename);
					//
					Log_Print("optimizing: %s to %s\n", qf->origname, filename);
					if(qf->type != QFILETYPE_AAS)
						Warning("%s is probably not a AAS file\n", qf->origname);
					//
					AAS_InitBotImport();
					//
					if(!AAS_LoadAASFile(qf->filename, qf->offset, qf->length))
					{
						Error("error loading aas file %s\n", qf->filename);
					}			//end if
					AAS_Optimize();
					//write out the stored AAS file
					if(!AAS_WriteAASFile(filename))
					{
						Error("error writing %s\n", filename);
					}			//end if
					//deallocate memory
					AAS_FreeMaxAAS();
				}				//end for
				break;
			}					//end case
			case COMP_AASINFO:
			{
				if(!qfiles)
					Log_Print("no files found\n");
				for(qf = qfiles; qf; qf = qf->next)
				{
					AASOuputFile(qf, outputpath, filename);
					//
					Log_Print("aas info for: %s\n", filename);
					if(qf->type != QFILETYPE_AAS)
						Warning("%s is probably not a AAS file\n", qf->origname);
					//
					AAS_InitBotImport();
					//
					if(!AAS_LoadAASFile(qf->filename, qf->offset, qf->length))
					{
						Error("error loading aas file %s\n", qf->filename);
					}			//end if
					AAS_ShowTotals();
				}				//end for
			}					//end case
			default:
			{
				Log_Print("don't know what to do\n");
				break;
			}					//end default
		}						//end switch
	}							//end if
	else
	{
		Log_Print("Usage:   bspc [-<switch> [-<switch> ...]]\n"
#if defined(WIN32) || defined(_WIN32)
				  "Example 1: bspc -bsp2aas d:\\quake3\\baseq3\\maps\\mymap?.bsp\n"
				  "Example 2: bspc -bsp2aas d:\\quake3\\baseq3\\pak0.pk3\\maps/q3dm*.bsp\n"
#else
				  "Example 1: bspc -bsp2aas /quake3/baseq3/maps/mymap?.bsp\n"
				  "Example 2: bspc -bsp2aas /quake3/baseq3/pak0.pk3/maps/q3dm*.bsp\n"
#endif
				  "\n" "Switches:\n"
				  //"   bsp2map  <[pakfilter/]filter.bsp>    = convert BSP to MAP\n"
				  //"   aasall   <quake3folder>              = create AAS files for all BSPs\n"
				  "   bsp2aas  <[pakfilter/]filter.bsp>    = convert BSP to AAS\n"
				  "   reach    <filter.bsp>                = compute reachability & clusters\n"
				  "   cluster  <filter.aas>                = compute clusters\n"
				  "   aasopt   <filter.aas>                = optimize aas file\n"
				  "   aasinfo  <filter.aas>                = show AAS file info\n"
				  "   output   <output path>               = set output path\n"
				  "   threads  <X>                         = set number of threads to X\n"
				  "   cfg      <filename>                  = use this cfg file\n"
				  "   optimize                             = enable optimization\n"
				  "   noverbose                            = disable verbose output\n"
				  "   breadthfirst                         = breadth first bsp building\n"
				  "   nobrushmerge                         = don't merge brushes\n"
				  "   noliquids                            = don't write liquids to map\n"
				  "   freetree                             = free the bsp tree\n"
				  "   nocsg                                = disables brush chopping\n"
				  "   forcesidesvisible                    = force all sides to be visible\n"
				  "   grapplereach                         = calculate grapple reachabilities\n"
/*			"   glview     = output a GL view\n"
			"   draw       = enables drawing\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"
			"   nosubdiv   = disables subdeviding\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"
			"   verboseentities\n"
			"              = enable entity verbose mode\n"
			"   chop <subdivide_size>\n"
			"              = sets the subdivide size to the given float\n"*/
				  "\n");
	}							//end else
	Log_Print("BSPC run time is %5.0f seconds\n", I_FloatTime() - start_time);
	Log_Close();				//close the log file
	return 0;
}								//end of the function main




See more files for this project here

Nxabega

Nxabega is a First Person Shooter (FPS) based upon the open sourced Quake 3 engine and game code. The final intention is to provide a rich single player game.

Project homepage: http://sourceforge.net/projects/nxabega
Programming language(s): C,C++
License: other

  Conscript
  Makefile
  _files.c
  aas_areamerging.c
  aas_areamerging.h
  aas_cfg.c
  aas_cfg.h
  aas_create.c
  aas_create.h
  aas_edgemelting.c
  aas_edgemelting.h
  aas_facemerging.c
  aas_facemerging.h
  aas_file.c
  aas_file.h
  aas_gsubdiv.c
  aas_gsubdiv.h
  aas_map.c
  aas_map.h
  aas_prunenodes.c
  aas_prunenodes.h
  aas_store.c
  aas_store.h
  aasfile.h
  be_aas_bspc.c
  be_aas_bspc.h
  brushbsp.c
  bspc.c
  bspc.sln
  bspc.vcproj
  cfgq3.c
  csg.c
  faces.c
  gldraw.c
  glfile.c
  l_bsp_ent.c
  l_bsp_ent.h
  l_bsp_hl.c
  l_bsp_hl.h
  l_bsp_q1.c
  l_bsp_q1.h
  l_bsp_q2.c
  l_bsp_q2.h
  l_bsp_q3.c
  l_bsp_q3.h
  l_bsp_sin.c
  l_bsp_sin.h
  l_cmd.c
  l_cmd.h
  l_log.c
  l_log.h
  l_math.c
  l_math.h
  l_mem.c
  l_mem.h
  l_poly.c
  l_poly.h
  l_qfiles.c
  l_qfiles.h
  l_threads.c
  l_threads.h
  l_utils.c
  l_utils.h
  lcc.mak
  leakfile.c
  linux-i386.mak
  map.c
  map_hl.c
  map_q1.c
  map_q2.c
  map_q3.c
  map_sin.c
  nodraw.c
  portals.c
  prtfile.c
  q2files.h
  q3files.h
  qbsp.h
  qfiles.h
  sinfiles.h
  tetrahedron.c
  tetrahedron.h
  textures.c
  tree.c
  writebsp.c