示例#1
0
/*QUAKED script_mover (0.5 0.25 1.0) ? TRIGGERSPAWN SOLID EXPLOSIVEDAMAGEONLY RESURECTABLE COMPASS ALLIED AXIS MOUNTED_GUN
Scripted brush entity. A simplified means of moving brushes around based on events.

"modelscale" - Scale multiplier (defaults to 1, and scales uniformly)
"modelscale_vec" - Set scale per-axis.  Overrides "modelscale", so if you have both the "modelscale" is ignored
"model2" optional md3 to draw over the solid clip brush
"scriptname" name used for scripting purposes (like aiName in AI scripting)
"health" optionally make this entity damagable
"description" used with health, if the entity is damagable, it draws a healthbar with this description above it.
*/
void SP_script_mover(gentity_t *ent) {

	float	scale[3] = {1,1,1};
	vec3_t	scalevec;
	char	tagname[MAX_QPATH];
	char*	modelname;
	char*	tagent;
	char	cs[MAX_INFO_STRING];
	char*	s;
	
	if (!ent->model)
		G_Error("script_mover must have a \"model\"\n" );
	if (!ent->scriptName)
		G_Error("script_mover must have a \"scriptname\"\n" );

	ent->blocked = script_mover_blocked;

	// first position at start
	VectorCopy( ent->s.origin, ent->pos1 );

//	VectorCopy( ent->r.currentOrigin, ent->pos1 );
	VectorCopy( ent->pos1, ent->pos2 );	// don't go anywhere just yet

	trap_SetBrushModel( ent, ent->model );

	InitMover( ent );
	ent->reached = NULL;
	ent->s.animMovetype = 0;

	ent->s.density = 0;

	if (ent->spawnflags & 256) {
		ent->s.density |= 2;
	}

	if (ent->spawnflags & 8) {
		ent->use = script_mover_use;
	}

	if (ent->spawnflags & 16) {
		ent->s.time2 = 1;
	} else {
		ent->s.time2 = 0;
	}

	if (ent->spawnflags & 32) {
		ent->s.teamNum = TEAM_ALLIES;
	} else if (ent->spawnflags & 64) {
		ent->s.teamNum = TEAM_AXIS;
	} else {
		ent->s.teamNum = TEAM_FREE;
	}

	if (ent->spawnflags & 1) {
		ent->use = script_mover_use;
		trap_UnlinkEntity(ent);	// make sure it's not visible
		return;
	}

 	G_SetAngle (ent, ent->s.angles);

	G_SpawnInt( "health", "0", &ent->health );
	if(ent->health) {
		ent->takedamage = qtrue;
		ent->count = ent->health;

		// client needs to know about it as well
		ent->s.effect1Time = ent->count;
		ent->s.dl_intensity = 255;

		if( G_SpawnString( "description", "", &s ) ) {
			trap_GetConfigstring( CS_SCRIPT_MOVER_NAMES, cs, sizeof(cs) );
			Info_SetValueForKey( cs, va("%i",ent-g_entities), s );
			trap_SetConfigstring( CS_SCRIPT_MOVER_NAMES, cs );
		}
	} else {
		ent->count = 0;
	}

	ent->die = script_mover_die;

	// look for general scaling
	if(G_SpawnFloat( "modelscale", "1", &scale[0])) {
		scale[2] = scale[1] = scale[0];
	}

	if(G_SpawnString( "model2", "", &modelname ) ) {
		COM_StripExtension( modelname, tagname );
		Q_strcat( tagname, MAX_QPATH, ".tag" );

		ent->tagNumber = trap_LoadTag( tagname );

/*		if( !(ent->tagNumber = trap_LoadTag( tagname )) ) {
			Com_Error( ERR_DROP, "Failed to load Tag File (%s)\n", tagname );
		}*/
	}

	// look for axis specific scaling
	if(G_SpawnVector("modelscale_vec", "1 1 1", &scalevec[0])) {
		VectorCopy(scalevec, scale);
	}

	if(scale[0] != 1 || scale[1] != 1 || scale[2] != 1) {
		ent->s.density |= 1;
		// scale is stored in 'angles2'
		VectorCopy(scale, ent->s.angles2);
	}

	if (ent->spawnflags & 128) {
		ent->s.density |= 4;
		ent->waterlevel = 0;
		
		if( G_SpawnString( "gun", "", &modelname ) ) {
			if( !Q_stricmp( modelname, "browning" ) ) {
				ent->s.density |= 8;
			}
		}

		G_SpawnString("tagent", "", &tagent);
		Q_strncpyz( ent->tagBuffer, tagent, 16 );
		ent->s.powerups = -1;
	}

	ent->think = script_mover_spawn;
	ent->nextthink = level.time + FRAMETIME;
}
示例#2
0
文件: g_main.c 项目: wombat23/omoh2
/*
================
G_RunFrame

Advances the non-player objects in the world
================
*/
void G_RunFrame( int levelTime ) {
	int			i;
	gentity_t	*ent;

	// if we are waiting for the level to restart, do nothing
	if ( level.restarted ) {
		return;
	}

	level.framenum++;
	level.previousTime = level.time;
	level.time = levelTime;

	// get any cvar changes
	G_UpdateCvars();

	//
	// go through all allocated objects
	//
	ent = &g_entities[0];
	for (i=0 ; i<level.num_entities ; i++, ent++) {
		if ( !ent->inuse ) {
			continue;
		}

		// clear events that are too old
		if ( level.time - ent->eventTime > EVENT_VALID_MSEC ) {
			if ( ent->s.event ) {
				ent->s.event = 0;	// &= EV_EVENT_BITS;
				if ( ent->client ) {
					ent->client->ps.externalEvent = 0;
					// predicted events should never be set to zero
					//ent->client->ps.events[0] = 0;
					//ent->client->ps.events[1] = 0;
				}
			}
			if ( ent->freeAfterEvent ) {
				// tempEntities or dropped items completely go away after their event
				G_FreeEntity( ent );
				continue;
			} else if ( ent->unlinkAfterEvent ) {
				// items that will respawn will hide themselves after their pickup event
				ent->unlinkAfterEvent = qfalse;
				trap_UnlinkEntity( ent );
			}
		}

		// temporary entities don't think
		if ( ent->freeAfterEvent ) {
			continue;
		}

		if ( !ent->r.linked && ent->neverFree ) {
			continue;
		}

		if ( ent->s.eType == ET_MISSILE ) {
			G_RunMissile( ent );
			continue;
		}

		if ( ent->s.eType == ET_ITEM || ent->physicsObject ) {
			G_RunItem( ent );
			continue;
		}

		if ( ent->s.eType == ET_MOVER ) {
			G_RunMover( ent );
			continue;
		}

		if ( i < MAX_CLIENTS ) {
			G_RunClient( ent );
			continue;
		}

		G_RunThink( ent );
	}

	// perform final fixups on the players
	ent = &g_entities[0];
	for (i=0 ; i < level.maxclients ; i++, ent++ ) {
		if ( ent->inuse ) {
			ClientEndFrame( ent );
		}
	}

	// see if it is time to do a tournement restart
	CheckTournament();

	// see if it is time to end the level
	CheckExitRules();

	// update to team status?
	CheckTeamStatus();

	// cancel vote if timed out
	CheckVote();

	// check team votes
	CheckTeamVote( TEAM_RED );
	CheckTeamVote( TEAM_BLUE );

	// for tracking changes
	CheckCvars();

	if (g_listEntity.integer) {
		for (i = 0; i < MAX_GENTITIES; i++) {
			G_Printf("%4i: %s\n", i, g_entities[i].classname);
		}
		trap_Cvar_Set("g_listEntity", "0");
	}
}