示例#1
0
文件: gl_model.c 项目: Cabriter/Quake
/*
==================
Mod_LoadModel

Loads a model into the cache
==================
*/
model_t *Mod_LoadModel (model_t *mod, qboolean crash)
{
    void	*d;
    unsigned *buf;
    byte	stackbuf[1024];		// avoid dirtying the cache heap

    if (!mod->needload)
    {
        if (mod->type == mod_alias)
        {
            d = Cache_Check (&mod->cache);
            if (d)
                return mod;
        }
        else
            return mod;		// not cached at all
    }

//
// because the world is so huge, load it one piece at a time
//
    if (!crash)
    {

    }

//
// load the file
//
    buf = (unsigned *)COM_LoadStackFile (mod->name, stackbuf, sizeof(stackbuf));
    if (!buf)
    {
        if (crash)
            Sys_Error ("Mod_NumForName: %s not found", mod->name);
        return NULL;
    }

//
// allocate a new model
//
    COM_FileBase (mod->name, loadname);

    loadmodel = mod;

//
// fill it in
//

// call the apropriate loader
    mod->needload = false;

    switch (LittleLong(*(unsigned *)buf))
    {
    case IDPOLYHEADER:
        Mod_LoadAliasModel (mod, buf);
        break;

    case IDSPRITEHEADER:
        Mod_LoadSpriteModel (mod, buf);
        break;

    default:
        Mod_LoadBrushModel (mod, buf);
        break;
    }

    return mod;
}
示例#2
0
/*
==================
Mod_ForName

Loads in a model for the given name
==================
*/
model_t *Mod_ForName (char *name, qboolean crash)
{
	model_t	*mod;
	unsigned *buf;
	int		i;
	
	if (!name[0])
		ri.Sys_Error (ERR_DROP, "Mod_ForName: NULL name");
		
	//
	// inline models are grabbed only from worldmodel
	//
	if (name[0] == '*')
	{
		i = atoi(name+1);
		if (i < 1 || !r_worldmodel || i >= r_worldmodel->numsubmodels)
			ri.Sys_Error (ERR_DROP, "bad inline model number");
		return &mod_inline[i];
	}

	//
	// search the currently loaded models
	//
	for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
	{
		if (!mod->name[0])
			continue;
		if (!strcmp (mod->name, name) )
			return mod;
	}
	
	//
	// find a free model slot spot
	//
	for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
	{
		if (!mod->name[0])
			break;	// free spot
	}
	if (i == mod_numknown)
	{
		if (mod_numknown == MAX_MOD_KNOWN)
			ri.Sys_Error (ERR_DROP, "mod_numknown == MAX_MOD_KNOWN");
		mod_numknown++;
	}
	strcpy (mod->name, name);
	
	//
	// load the file
	//
	modfilelen = ri.FS_LoadFile (mod->name, &buf);
	if (!buf)
	{
		if (crash)
			ri.Sys_Error (ERR_DROP, "Mod_NumForName: %s not found", mod->name);
		memset (mod->name, 0, sizeof(mod->name));
		return NULL;
	}
	
	loadmodel = mod;

	//
	// fill it in
	//


	// call the apropriate loader
	
	switch (LittleLong(*(unsigned *)buf))
	{
	case IDALIASHEADER:
		loadmodel->extradata = Hunk_Begin (0x200000);
		Mod_LoadAliasModel (mod, buf);
		break;
		
	case IDSPRITEHEADER:
		loadmodel->extradata = Hunk_Begin (0x10000);
		Mod_LoadSpriteModel (mod, buf);
		break;
	
	case IDBSPHEADER:
		loadmodel->extradata = Hunk_Begin (0x1000000);
		Mod_LoadBrushModel (mod, buf);
		break;

	default:
		ri.Sys_Error (ERR_DROP,"Mod_NumForName: unknown fileid for %s", mod->name);
		break;
	}

	loadmodel->extradatasize = Hunk_End ();

	ri.FS_FreeFile (buf);

	return mod;
}
示例#3
0
/*
==================
Mod_ForName

Loads in a model for the given name
==================
*/
model_t *Mod_ForName (char *name, qboolean crash)
{
	model_t	*mod;
	int		i;
	FILE *file;
	long base;
	int type;
	char *extradata;
	
	if (!name[0])
		ri.Sys_Error (ERR_DROP, "Mod_ForName: NULL name");
		
	//
	// inline models are grabbed only from worldmodel
	//
	if (name[0] == '*')
	{
		i = atoi(name+1);
		if (i < 1 || !r_worldmodel || i >= r_worldmodel->numsubmodels)
			ri.Sys_Error (ERR_DROP, "bad inline model number");
		return &mod_inline[i];
	}

	//
	// search the currently loaded models
	//
	for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
	{
		if (!mod->name[0])
			continue;
		if (!strcmp (mod->name, name) )
			return mod;
	}
	
	//
	// find a free model slot spot
	//
	for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
	{
		if (!mod->name[0])
			break;	// free spot
	}
	if (i == mod_numknown)
	{
		if (mod_numknown == MAX_MOD_KNOWN)
			ri.Sys_Error (ERR_DROP, "mod_numknown == MAX_MOD_KNOWN");
		mod_numknown++;
	}
	strcpy (mod->name, name);
	
	//
	// load the file
	//
	modfilelen = ri.FS_FOpenFile (mod->name, &file);
	if (modfilelen < 0)
	{
		if (crash)
			ri.Sys_Error (ERR_DROP, "Mod_NumForName: %s not found", mod->name);
		memset (mod->name, 0, sizeof(mod->name));
		return NULL;
	}
	
	loadmodel = mod;
	extradata = Hunk_Alloc(&hunk_ref, 0);

	//
	// fill it in
	//

	base = ftell(file);

	// call the apropriate loader
	ri.FS_Read(&type, sizeof(type), file);
	
	fseek(file, base, SEEK_SET);

	switch (LittleLong(type))
	{
	case IDALIASHEADER:
		Mod_LoadAliasModel (mod, file, base);
		break;
		
	case IDSPRITEHEADER:
		Mod_LoadSpriteModel (mod, file, base);
		break;
	
	case IDBSPHEADER:
		Mod_LoadBrushModel (mod, file, base);
		break;

	default:
		ri.Sys_Error (ERR_DROP,"Mod_NumForName: unknown fileid for %s", mod->name);
		break;
	}

	loadmodel->extradatasize = (char *)Hunk_Alloc (&hunk_ref, 0) - extradata;

	ri.FS_FCloseFile(file);

	return mod;
}
示例#4
0
文件: model.c 项目: Izhido/qrevpak
/*
==================
Mod_LoadModel

Loads a model into the cache
==================
*/
model_t *Mod_LoadModel (model_t *mod, qboolean crash)
{
	unsigned *buf;
// >>> FIX: For Nintendo Wii using devkitPPC / libogc
// Deferring allocation. Stack in this device is pretty small:
	//byte	stackbuf[1024];		// avoid dirtying the cache heap
	byte*	stackbuf;		// avoid dirtying the cache heap
// <<< FIX

	if (mod->type == mod_alias)
	{
		if (Cache_Check (&mod->cache))
		{
			mod->needload = NL_PRESENT;
			return mod;
		}
	}
	else
	{
		if (mod->needload == NL_PRESENT)
			return mod;
	}

//
// because the world is so huge, load it one piece at a time
//
	
//
// load the file
//
// >>> FIX: For Nintendo Wii using devkitPPC / libogc
// Allocating for previous fixes (and, this time, expanding the allocated size), in big stack:
	stackbuf = Sys_BigStackAlloc(4096 * sizeof(byte), "Mod_LoadModel");
// <<< FIX
// >>> FIX: For Nintendo Wii using devkitPPC / libogc
// Adjusting for previous fix:
	//buf = (unsigned *)COM_LoadStackFile (mod->name, stackbuf, sizeof(stackbuf));
	buf = (unsigned *)COM_LoadStackFile (mod->name, stackbuf, 4096);
// <<< FIX
	if (!buf)
	{
		if (crash)
			Sys_Error ("Mod_NumForName: %s not found", mod->name);
// >>> FIX: For Nintendo Wii using devkitPPC / libogc
// Deallocating from previous fixes:
		Sys_BigStackFree(4096 * sizeof(byte), "Mod_LoadModel");
// <<< FIX
		return NULL;
	}
	
//
// allocate a new model
//
	COM_FileBase (mod->name, loadname);
	
	loadmodel = mod;

//
// fill it in
//

// call the apropriate loader
	mod->needload = NL_PRESENT;

	switch (LittleLong(*(unsigned *)buf))
	{
	case IDPOLYHEADER:
		Mod_LoadAliasModel (mod, buf);
		break;
		
	case IDSPRITEHEADER:
		Mod_LoadSpriteModel (mod, buf);
		break;
	
	default:
		Mod_LoadBrushModel (mod, buf);
		break;
	}

// >>> FIX: For Nintendo Wii using devkitPPC / libogc
// Deallocating from previous fixes:
	Sys_BigStackFree(4096 * sizeof(byte), "Mod_LoadModel");
// <<< FIX

	return mod;
}
示例#5
0
/*
==================
Mod_ForName

Loads in a model for the given name
==================
*/
model_t *Mod_ForName (const char *name_, qboolean crash)
{
	model_t		*mod;
	model_t		*modelhash;
	mscache_t	*model_size;
	byte		*buf;
	int			i;
	unsigned	hash;

	size_t len = strlen(name_);
	char *name = (char *) alloca(len + 1);
	strcpy(name, name_);

	if (!name || !name[0])
		VID_Error (ERR_DROP, "Mod_ForName: NULL name");
		
	//
	// inline models are grabbed only from worldmodel
	//
	if (name[0] == '*')
	{
		i = atoi(name+1);
		if (i < 1 || !r_worldmodel || i >= r_worldmodel->numsubmodels)
			VID_Error (ERR_DROP, "bad inline model number %d", i);
		return &mod_inline[i];
	}

	fast_strlwr (name);

	hash = hashify (name) % MODEL_HASH_SIZE;

	for (modelhash = models_hash[hash]; modelhash; modelhash = modelhash->hash_next)
	{
		if (!strcmp (modelhash->name, name))
		{
			return modelhash;
		}
	}

	for (model_size = model_size_cache[hash]; model_size; model_size = model_size->hash_next)
	{
		if (!strcmp (model_size->name, name))
			break;
	}

	//
	// search the currently loaded models
	//
	/*for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
	{
		if (!mod->name[0] || mod->hash != hash)
			continue;
		if (!strcmp (mod->name, name) )
			return mod;
	}*/
	
	//
	// find a free model slot spot
	//
	for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
	{
		if (!mod->name[0])
			break;	// free spot
	}

	if (i == mod_numknown)
	{
		if (mod_numknown == MAX_MOD_KNOWN)
			VID_Error (ERR_DROP, "mod_numknown == MAX_MOD_KNOWN");
		mod_numknown++;
	}

	strncpy (mod->name, name, sizeof(mod->name)-1);

	//
	// load the file
	//
	modfilelen = FS_LoadFile (name, (void **)&buf);
	if (!buf)
	{
		if (crash)
			VID_Error (ERR_DROP, "Mod_NumForName: %s not found", mod->name);
		mod->name[0] = 0;
		return NULL;
	}
	
	loadmodel = mod;

	//
	// fill it in
	//


	// call the apropriate loader
	
	switch (LittleLong(*(unsigned *)buf))
	{
		case IDALIASHEADER:
			if (model_size)
				loadmodel->extradata = Hunk_Begin (model_size->size, model_size->size);
			else
				loadmodel->extradata = Hunk_Begin (0x200000, 0);
			Mod_LoadAliasModel (mod, buf);
			break;
			
		case IDSPRITEHEADER:
			if (model_size)
				loadmodel->extradata = Hunk_Begin (model_size->size, model_size->size);
			else
				loadmodel->extradata = Hunk_Begin (0x4000, 0);
			Mod_LoadSpriteModel (mod, buf);
			break;
		
		case IDBSPHEADER:
			if (model_size)
				loadmodel->extradata = Hunk_Begin (model_size->size, model_size->size);
			else
				loadmodel->extradata = Hunk_Begin (0x1000000, 0);
			Mod_LoadBrushModel (mod, buf);
			break;

		default:
			VID_Error (ERR_DROP,"Mod_NumForName: unknown 0x%.8x fileid for %s", LittleLong(*(unsigned *)buf), mod->name);
			break;
	}

	if (model_size)
	{
		loadmodel->extradatasize = model_size->size;
	}
	else
	{
		loadmodel->extradatasize = Hunk_End ();

		model_size = (mscache_t	*) malloc (sizeof(*model_size));
		if (!model_size)
			VID_Error (ERR_FATAL, "Mod_ForName: out of memory");
		strcpy (model_size->name, mod->name);
		model_size->size = loadmodel->extradatasize;
		model_size->hash_next = model_size_cache[hash];

		model_size_cache[hash] = model_size;
	}

	mod->hash_next = models_hash[hash];
	models_hash[hash] = mod;

	FS_FreeFile (buf);

	return mod;
}