From 2c175ab8701b4c4cb952b8d6edb5fde2e91d4921 Mon Sep 17 00:00:00 2001 From: TimeServ Date: Wed, 18 May 2005 23:15:58 +0000 Subject: [PATCH] t_ beam effects to te_ type field added (normal, beam, decal) git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@1028 fc73d0e0-1445-4013-8a0c-d673dee63da5 --- engine/client/cl_tent.c | 56 ++++++++++++++++++++--------- engine/client/r_part.c | 74 +++++++++++++++++++++++---------------- engine/client/r_partset.c | 6 ++-- engine/common/particles.h | 7 +++- 4 files changed, 91 insertions(+), 52 deletions(-) diff --git a/engine/client/cl_tent.c b/engine/client/cl_tent.c index 121c41e5f..9d9decdfb 100644 --- a/engine/client/cl_tent.c +++ b/engine/client/cl_tent.c @@ -122,6 +122,7 @@ typedef struct float endtime; float alpha; vec3_t start, end; + int particleeffect; } beam_t; beam_t cl_beams[MAX_BEAMS]; @@ -309,6 +310,7 @@ void CL_ParseBeam (int tent) beam_t *b; model_t *m; + int btype, etype; ent = MSG_ReadShort (); @@ -320,7 +322,6 @@ void CL_ParseBeam (int tent) end[1] = MSG_ReadCoord (); end[2] = MSG_ReadCoord (); - switch(tent) { case 0: @@ -331,27 +332,42 @@ void CL_ParseBeam (int tent) } default: m = Mod_ForName("progs/bolt.mdl", false); + btype = rt_lightning1; + etype = pt_lightning1_end; break; case 1: if (ent < 0 && ent >= -MAX_CLIENTS) //based on the railgun concept - this adds a rogue style TE_BEAM effect. + { m = Mod_ForName("progs/beam.mdl", false); //remember to precache! + btype = P_FindParticleType("te_beam"); + } else + { m = Mod_ForName("progs/bolt2.mdl", false); + btype = rt_lightning2; + etype = pt_lightning2_end; + } break; case 2: m = Mod_ForName("progs/bolt3.mdl", false); + btype = rt_lightning3; + etype = pt_lightning3_end; break; #ifdef Q2CLIENT case 3: m = Mod_ForName(q2tentmodels[q2cl_mod_parasite_segment].modelname, false); + btype = P_FindParticleType("te_parasite_attack"); + etype = P_FindParticleType("te_parasite_attack_end"); break; case 4: m = Mod_ForName(q2tentmodels[q2cl_mod_grapple_cable].modelname, false); + btype = P_FindParticleType("te_grapple_cable"); + etype = P_FindParticleType("te_grapple_cable_end"); break; #endif } - if (tent <= 2 && cls.state == ca_active) + if (tent <= 2 && cls.state == ca_active && etype >= 0) { vec3_t impact, normal; vec3_t extra; @@ -360,7 +376,7 @@ void CL_ParseBeam (int tent) VectorMA(end, 4, normal, extra); //extend the end-point by four if (TraceLineN(start, extra, impact, normal)) { - P_RunParticleEffectTypeString(impact, normal, 1, "te_lightningend"); + P_RunParticleEffectType(impact, normal, 1, etype); R_AddDecals(end); R_AddStain(end, -10, -10, -10, 20); } @@ -379,6 +395,7 @@ void CL_ParseBeam (int tent) b->flags |= /*STREAM_ATTACHED|*/1; b->endtime = cl.time + 0.2; b->alpha = 1; + b->particleeffect = btype; VectorCopy (start, b->start); VectorCopy (end, b->end); } @@ -430,20 +447,26 @@ void CL_ParseStream (int type) case TE_STREAM_ICECHUNKS: b->model = Mod_ForName("models/stice.mdl", true); b->flags |= 2; + b->particleeffect = P_AllocateParticleType("te_stream_icechunks"); R_AddStain(end, -10, -10, 0, 20); break; case TE_STREAM_SUNSTAFF1: b->model = Mod_ForName("models/stsunsf1.mdl", true); - b2 = CL_NewBeam(ent, tag+128); - if (b2) + b->particleeffect = P_AllocateParticleType("te_stream_sunstaff1"); + if (b->particleeffect < 0) { - memcpy(b2, b, sizeof(*b2)); - b2->model = Mod_ForName("models/stsunsf2.mdl", true); - b2->alpha = 0.5; + b2 = CL_NewBeam(ent, tag+128); + if (b2) + { + memcpy(b2, b, sizeof(*b2)); + b2->model = Mod_ForName("models/stsunsf2.mdl", true); + b2->alpha = 0.5; + } } break; case TE_STREAM_SUNSTAFF2: b->model = Mod_ForName("models/stsunsf1.mdl", true); + b->particleeffect = P_AllocateParticleType("te_stream_sunstaff2"); R_AddStain(end, -10, -10, -10, 20); break; } @@ -818,10 +841,8 @@ void CL_ParseTEnt (void) pos2[2] = MSG_ReadChar (); cnt = MSG_ReadByte (); - { - extern int pt_spark; - P_RunParticleEffectType(pos, pos2, cnt, pt_blood); - } + + P_RunParticleEffectType(pos, pos2, cnt, pt_blood); break; case DPTE_SPARK: @@ -1759,7 +1780,7 @@ void CLQ2_ParseTEnt (void) case Q2TE_DEBUGTRAIL: MSG_ReadPos (pos); MSG_ReadPos (pos2); - P_ParticleTrail(pos, pos2, P_AllocateParticleType("t_debugtrail"), NULL); + P_ParticleTrail(pos, pos2, P_AllocateParticleType("te_debugtrail"), NULL); break; case Q2TE_PLAIN_EXPLOSION: @@ -1876,10 +1897,10 @@ void CLQ2_ParseTEnt (void) case Q2TE_DBALL_GOAL: MSG_ReadPos (pos); if (P_RunParticleEffectType(pos, NULL, 1, pt_teleportsplash)) - P_RunParticleEffect(pos, NULL, 7, 768); + P_RunParticleEffect(pos, NULL, 8, 768); // This effect won't match --- // Color should be 7+(rand()%8) - // not 7&~7+(rand()%8) + // not 8&~7+(rand()%8) break; /* case Q2TE_WIDOWBEAMOUT: @@ -1939,7 +1960,6 @@ CL_UpdateBeams */ void CL_UpdateBeams (void) { - extern int rt_lightning1; int i; beam_t *b; vec3_t dist, org; @@ -2033,7 +2053,9 @@ void CL_UpdateBeams (void) } */ // if (part_type[rt_lightning1].loaded) - if (!P_ParticleTrail(b->start, b->end, rt_lightning1, NULL)) +// if (!P_ParticleTrail(b->start, b->end, rt_lightning1, NULL)) +// continue; + if (b->particleeffect >= 0 && !P_ParticleTrail(b->start, b->end, b->particleeffect, NULL)) continue; // add new entities for the lightning diff --git a/engine/client/r_part.c b/engine/client/r_part.c index dff30049c..fe74c70af 100644 --- a/engine/client/r_part.c +++ b/engine/client/r_part.c @@ -70,7 +70,10 @@ int rt_blastertrail, rt_gib, rt_lightning1, rt_lightning2, - rt_lightning3; + rt_lightning3, + pt_lightning1_end, + pt_lightning2_end, + pt_lightning3_end; //triangle fan sparks use these. static double sint[7] = {0.000000, 0.781832, 0.974928, 0.433884, -0.433884, -0.974928, -0.781832}; @@ -87,7 +90,7 @@ void P_ReadPointFile_f (void); #define MAX_BEAMS 2048 // default max # of beam segments #define MAX_PARTICLES 32768 // default max # of particles at one // time -#define MAX_DECALS 32768 // this is going to be expensive +#define MAX_DECALS 4096 // this is going to be expensive //int ramp1[8] = {0x6f, 0x6d, 0x6b, 0x69, 0x67, 0x65, 0x63, 0x61}; //int ramp2[8] = {0x6f, 0x6e, 0x6d, 0x6c, 0x6b, 0x6a, 0x68, 0x66}; @@ -133,12 +136,6 @@ typedef struct skytris_s { msurface_t *face; } skytris_t; - - - - - - //these could be deltas or absolutes depending on ramping mode. typedef struct { vec3_t rgb; @@ -166,7 +163,7 @@ typedef struct part_type_s { float offsetspreadvert; float randomvelvert; float randscale; - qboolean isbeam; + enum {PT_NORMAL, PT_BEAM, PT_DECAL} type; enum {BM_MERGE, BM_ADD, BM_SUBTRACT} blendmode; float rotationstartmin, rotationstartrand; @@ -194,7 +191,7 @@ typedef struct part_type_s { float offsetup; // make this into a vec3_t later with dir, possibly for mdls - enum {SM_BOX, SM_CIRCLE, SM_BALL, SM_SPIRAL, SM_TRACER, SM_TELEBOX, SM_LAVASPLASH, SM_UNICIRCLE, SM_FIELD, SM_DECAL} spawnmode; + enum {SM_BOX, SM_CIRCLE, SM_BALL, SM_SPIRAL, SM_TRACER, SM_TELEBOX, SM_LAVASPLASH, SM_UNICIRCLE, SM_FIELD} spawnmode; //box = even spread within the area //circle = around edge of a circle //ball = filled sphere @@ -272,7 +269,7 @@ int P_ParticleTypeForName(char *name) return to; } -static int P_FindParticleType(char *name) //checks if particle description 'name' exists, returns -1 if not. +int P_FindParticleType(char *name) //checks if particle description 'name' exists, returns -1 if not. { int i; for (i = 0; i < numparticletypes; i++) @@ -645,15 +642,25 @@ void P_ParticleEffect_f(void) ptype->spawnmode = SM_UNICIRCLE; else if (!strcmp(value, "syncfield")) ptype->spawnmode = SM_FIELD; - else if (!strcmp(value, "decal")) - ptype->spawnmode = SM_DECAL; else ptype->spawnmode = SM_BOX; } - else if (!strcmp(var, "isbeam")) - ptype->isbeam = true; + else if (!strcmp(var, "type")) + { + if (!strcmp(value, "beam")) + ptype->type = PT_BEAM; + else if (!strcmp(value, "decal")) + ptype->type = PT_DECAL; + else + ptype->type = PT_NORMAL; + } + else if (!strcmp(var, "isbeam")) + { + Con_DPrintf("isbeam is deprechiated, use type beam\n"); + ptype->type = PT_BEAM; + } else if (!strcmp(var, "cliptype")) { assoc = P_ParticleTypeForName(value);//careful - this can realloc all the particle types @@ -1134,16 +1141,20 @@ void P_InitParticles (void) pt_spike = P_AllocateParticleType("te_spike"); pt_superspike = P_AllocateParticleType("te_superspike"); - rt_railtrail = P_AllocateParticleType("t_railtrail"); + rt_railtrail = P_AllocateParticleType("te_railtrail"); + rt_bubbletrail = P_AllocateParticleType("te_bubbletrail"); rt_blastertrail = P_AllocateParticleType("t_blastertrail"); - rt_bubbletrail = P_AllocateParticleType("t_bubbletrail"); rt_rocket = P_AllocateParticleType("t_rocket"); rt_grenade = P_AllocateParticleType("t_grenade"); rt_gib = P_AllocateParticleType("t_gib"); - rt_lightning1 = P_AllocateParticleType("t_lightning1"); - rt_lightning2 = P_AllocateParticleType("t_lightning2"); - rt_lightning3 = P_AllocateParticleType("t_lightning3"); + rt_lightning1 = P_AllocateParticleType("te_lightning1"); + rt_lightning2 = P_AllocateParticleType("te_lightning2"); + rt_lightning3 = P_AllocateParticleType("te_lightning3"); + + pt_lightning1_end = P_AllocateParticleType("te_lightning1_end"); + pt_lightning2_end = P_AllocateParticleType("te_lightning2_end"); + pt_lightning3_end = P_AllocateParticleType("te_lightning3_end"); pt_spark = P_AllocateParticleType("te_spark"); pt_plasma = P_AllocateParticleType("te_plasma"); @@ -1715,7 +1726,7 @@ int P_RunParticleEffectType (vec3_t org, vec3_t dir, float count, int typenum) if (!ptype->loaded) return 1; - if (ptype->spawnmode == SM_DECAL) + if (ptype->type == PT_DECAL) { clippeddecal_t *d; int decalcount; @@ -1780,6 +1791,7 @@ int P_RunParticleEffectType (vec3_t org, vec3_t dir, float count, int typenum) } else VectorCopy(ptype->rgb, d->rgb); + vec[2] = frandom(); vec[0] = vec[2]*ptype->rgbrandsync[0] + frandom()*(1-ptype->rgbrandsync[0]); vec[1] = vec[2]*ptype->rgbrandsync[1] + frandom()*(1-ptype->rgbrandsync[1]); @@ -1811,7 +1823,7 @@ int P_RunParticleEffectType (vec3_t org, vec3_t dir, float count, int typenum) { case SM_UNICIRCLE: m = (count*ptype->count); - if (ptype->isbeam) + if (ptype->type == PT_BEAM) m--; if (m < 1) @@ -1855,7 +1867,7 @@ int P_RunParticleEffectType (vec3_t org, vec3_t dir, float count, int typenum) if (!free_particles) break; p = free_particles; - if (ptype->isbeam) + if (ptype->type == PT_BEAM) { if (!free_beams) break; @@ -2049,7 +2061,7 @@ int P_RunParticleEffectType (vec3_t org, vec3_t dir, float count, int typenum) } // update beam list - if (ptype->isbeam) + if (ptype->type == PT_BEAM) { if (b) { @@ -2373,7 +2385,7 @@ int P_ParticleTrail (vec3_t startpos, vec3_t end, int type, trailstate_t *ts) } p = free_particles; - if (ptype->isbeam) + if (ptype->type == PT_BEAM) { if (!free_beams) { @@ -2518,7 +2530,7 @@ int P_ParticleTrail (vec3_t startpos, vec3_t end, int type, trailstate_t *ts) ts->lastdist = len; // update beamseg list - if (ptype->isbeam) + if (ptype->type == PT_BEAM) { if (b) { @@ -2554,7 +2566,7 @@ int P_ParticleTrail (vec3_t startpos, vec3_t end, int type, trailstate_t *ts) } } } - else if (ptype->isbeam) + else if (ptype->type == PT_BEAM) { if (b) { @@ -3356,7 +3368,7 @@ void DrawParticleTypes (void texturedparticles(particle_t *,part_type_t*), void if (!type->particles) continue; - if (type->isbeam) + if (type->type == PT_BEAM) { if (*type->texname) pdraw = beamparticlest; @@ -3377,7 +3389,7 @@ void DrawParticleTypes (void texturedparticles(particle_t *,part_type_t*), void { while ((p=type->particles)) { - if (!type->isbeam) + if (type->type == PT_NORMAL) RQ_AddDistReorder(pdraw, p, type, p->org); type->particles = p->next; @@ -3551,7 +3563,7 @@ void DrawParticleTypes (void texturedparticles(particle_t *,part_type_t*), void p->vel[1] *= type->clipbounce; p->vel[2] *= type->clipbounce; - if (!*type->texname && Length(p->vel)<1000*pframetime && !type->isbeam) + if (!*type->texname && Length(p->vel)<1000*pframetime && type->type == PT_NORMAL) p->die = -1; } else @@ -3577,7 +3589,7 @@ void DrawParticleTypes (void texturedparticles(particle_t *,part_type_t*), void } } - if (!type->isbeam) + if (type->type == PT_NORMAL) RQ_AddDistReorder((void*)pdraw, p, type, p->org); } diff --git a/engine/client/r_partset.c b/engine/client/r_partset.c index e300e0928..1603a6543 100644 --- a/engine/client/r_partset.c +++ b/engine/client/r_partset.c @@ -131,7 +131,7 @@ char *particle_set_spikeset = #endif //TeamFortress railgun (by model - this is also the effect used with the TE_LIGHTNING1 extension) -"r_part t_railtrail\n" +"r_part te_railtrail\n" "{\n" " texture \"particles/b_rocket3\"\n" " step 15\n" @@ -145,10 +145,10 @@ char *particle_set_spikeset = " isbeam\n" " spawnmode spiral\n" " offsetspread 100\n" -" cliptype t_railtrail\n" +" cliptype te_railtrail\n" " friction 0.7\n" "}\n" -"r_trail progs/e_spike1.mdl t_railtrail\n" +"r_trail progs/e_spike1.mdl te_railtrail\n" "r_part t_grenade\n" diff --git a/engine/common/particles.h b/engine/common/particles.h index 1fb7ffc88..deaeeae12 100644 --- a/engine/common/particles.h +++ b/engine/common/particles.h @@ -30,7 +30,10 @@ extern int rt_blastertrail, rt_gib, rt_lightning1, rt_lightning2, - rt_lightning3; + rt_lightning3, + pt_lightning1_end, + pt_lightning2_end, + pt_lightning3_end; /* extern int rt_rocket_trail, @@ -120,6 +123,8 @@ void P_NewServer(void); //allocate a new effect int P_ParticleTypeForName(char *name); int P_AllocateParticleType(char *name); //find one if it exists, or create if it doesn't. +int P_FindParticleType(char *name); //checks if particle description 'name' exists, returns -1 if not. + qboolean P_DescriptionIsLoaded(char *name); //returns true if it's usable. void P_SkyTri(float *v1, float *v2, float *v3, struct msurface_s *surf);