Annotation of quake2/client/cl_tent.c, revision 1.1

1.1     ! root        1: // cl_tent.c -- client side temporary entities
        !             2: 
        !             3: #include "client.h"
        !             4: 
        !             5: typedef enum
        !             6: {
        !             7:        ex_free, ex_explosion, ex_misc, ex_flash, ex_mflash, ex_poly
        !             8: } exptype_t;
        !             9: 
        !            10: typedef struct
        !            11: {
        !            12:        exptype_t       type;
        !            13:        entity_t        ent;
        !            14: 
        !            15:        int                     frames;
        !            16:        float           light;
        !            17:        vec3_t          lightcolor;
        !            18:        float           start;
        !            19:        int                     baseframe;
        !            20: } explosion_t;
        !            21: 
        !            22: 
        !            23: 
        !            24: #define        MAX_EXPLOSIONS  32
        !            25: explosion_t    cl_explosions[MAX_EXPLOSIONS];
        !            26: 
        !            27: 
        !            28: #define        MAX_BEAMS       32
        !            29: typedef struct
        !            30: {
        !            31:        int             entity;
        !            32:        struct model_s  *model;
        !            33:        int             endtime;
        !            34:        vec3_t  offset;
        !            35:        vec3_t  start, end;
        !            36: } beam_t;
        !            37: beam_t         cl_beams[MAX_BEAMS];
        !            38: 
        !            39: 
        !            40: #define        MAX_LASERS      32
        !            41: typedef struct
        !            42: {
        !            43:        entity_t        ent;
        !            44:        int                     endtime;
        !            45: } laser_t;
        !            46: laser_t                cl_lasers[MAX_LASERS];
        !            47: 
        !            48: 
        !            49: void CL_BlasterParticles (vec3_t org, vec3_t dir);
        !            50: void CL_ExplosionParticles (vec3_t org);
        !            51: void CL_BFGExplosionParticles (vec3_t org);
        !            52: 
        !            53: struct sfx_s   *cl_sfx_ric1;
        !            54: struct sfx_s   *cl_sfx_ric2;
        !            55: struct sfx_s   *cl_sfx_ric3;
        !            56: struct sfx_s   *cl_sfx_lashit;
        !            57: struct sfx_s   *cl_sfx_spark5;
        !            58: struct sfx_s   *cl_sfx_spark6;
        !            59: struct sfx_s   *cl_sfx_spark7;
        !            60: struct sfx_s   *cl_sfx_railg;
        !            61: struct sfx_s   *cl_sfx_rockexp;
        !            62: struct sfx_s   *cl_sfx_grenexp;
        !            63: struct sfx_s   *cl_sfx_watrexp;
        !            64: 
        !            65: struct sfx_s   *cl_sfx_footsteps[4];
        !            66: 
        !            67: struct model_s *cl_mod_explode;
        !            68: struct model_s *cl_mod_smoke;
        !            69: struct model_s *cl_mod_flash;
        !            70: struct model_s *cl_mod_parasite_segment;
        !            71: struct model_s *cl_mod_grapple_cable;
        !            72: struct model_s *cl_mod_parasite_tip;
        !            73: struct model_s *cl_mod_explo4;
        !            74: struct model_s *cl_mod_bfg_explo;
        !            75: struct model_s *cl_mod_powerscreen;
        !            76: 
        !            77: /*
        !            78: =================
        !            79: CL_RegisterTEntSounds
        !            80: =================
        !            81: */
        !            82: void CL_RegisterTEntSounds (void)
        !            83: {
        !            84:        int             i;
        !            85:        char    name[MAX_QPATH];
        !            86: 
        !            87:        cl_sfx_ric1 = S_RegisterSound ("world/ric1.wav");
        !            88:        cl_sfx_ric2 = S_RegisterSound ("world/ric2.wav");
        !            89:        cl_sfx_ric3 = S_RegisterSound ("world/ric3.wav");
        !            90:        cl_sfx_lashit = S_RegisterSound("weapons/lashit.wav");
        !            91:        cl_sfx_spark5 = S_RegisterSound ("world/spark5.wav");
        !            92:        cl_sfx_spark6 = S_RegisterSound ("world/spark6.wav");
        !            93:        cl_sfx_spark7 = S_RegisterSound ("world/spark7.wav");
        !            94:        cl_sfx_railg = S_RegisterSound ("weapons/railgf1a.wav");
        !            95:        cl_sfx_rockexp = S_RegisterSound ("weapons/rocklx1a.wav");
        !            96:        cl_sfx_grenexp = S_RegisterSound ("weapons/grenlx1a.wav");
        !            97:        cl_sfx_watrexp = S_RegisterSound ("weapons/xpld_wat.wav");
        !            98: 
        !            99:        S_RegisterSound ("player/land1.wav");
        !           100: 
        !           101:        S_RegisterSound ("player/fall2.wav");
        !           102:        S_RegisterSound ("player/fall1.wav");
        !           103: 
        !           104:        for (i=0 ; i<4 ; i++)
        !           105:        {
        !           106:                Com_sprintf (name, sizeof(name), "player/step%i.wav", i+1);
        !           107:                cl_sfx_footsteps[i] = S_RegisterSound (name);
        !           108:        }
        !           109: }      
        !           110: 
        !           111: /*
        !           112: =================
        !           113: CL_RegisterTEntModels
        !           114: =================
        !           115: */
        !           116: void CL_RegisterTEntModels (void)
        !           117: {
        !           118:        cl_mod_explode = re.RegisterModel ("models/objects/explode/tris.md2");
        !           119:        cl_mod_smoke = re.RegisterModel ("models/objects/smoke/tris.md2");
        !           120:        cl_mod_flash = re.RegisterModel ("models/objects/flash/tris.md2");
        !           121:        cl_mod_parasite_segment = re.RegisterModel ("models/monsters/parasite/segment/tris.md2");
        !           122:        cl_mod_grapple_cable = re.RegisterModel ("models/ctf/segment/tris.md2");
        !           123:        cl_mod_parasite_tip = re.RegisterModel ("models/monsters/parasite/tip/tris.md2");
        !           124:        cl_mod_explo4 = re.RegisterModel ("models/objects/r_explode/tris.md2");
        !           125:        cl_mod_bfg_explo = re.RegisterModel ("sprites/s_bfg2.sp2");
        !           126:        cl_mod_powerscreen = re.RegisterModel ("models/items/armor/effect/tris.md2");
        !           127: 
        !           128: re.RegisterModel ("models/objects/laser/tris.md2");
        !           129: re.RegisterModel ("models/objects/grenade2/tris.md2");
        !           130: re.RegisterModel ("models/weapons/v_machn/tris.md2");
        !           131: re.RegisterModel ("models/weapons/v_handgr/tris.md2");
        !           132: re.RegisterModel ("models/weapons/v_shotg2/tris.md2");
        !           133: re.RegisterModel ("models/objects/gibs/bone/tris.md2");
        !           134: re.RegisterModel ("models/objects/gibs/sm_meat/tris.md2");
        !           135: re.RegisterModel ("models/objects/gibs/bone2/tris.md2");
        !           136: 
        !           137: re.RegisterPic ("w_machinegun");
        !           138: re.RegisterPic ("a_bullets");
        !           139: re.RegisterPic ("i_health");
        !           140: re.RegisterPic ("a_grenades");
        !           141: }      
        !           142: 
        !           143: /*
        !           144: =================
        !           145: CL_ClearTEnts
        !           146: =================
        !           147: */
        !           148: void CL_ClearTEnts (void)
        !           149: {
        !           150:        memset (cl_beams, 0, sizeof(cl_beams));
        !           151:        memset (cl_explosions, 0, sizeof(cl_explosions));
        !           152:        memset (cl_lasers, 0, sizeof(cl_lasers));
        !           153: }
        !           154: 
        !           155: /*
        !           156: =================
        !           157: CL_AllocExplosion
        !           158: =================
        !           159: */
        !           160: explosion_t *CL_AllocExplosion (void)
        !           161: {
        !           162:        int             i;
        !           163:        int             time;
        !           164:        int             index;
        !           165:        
        !           166:        for (i=0 ; i<MAX_EXPLOSIONS ; i++)
        !           167:        {
        !           168:                if (cl_explosions[i].type == ex_free)
        !           169:                {
        !           170:                        memset (&cl_explosions[i], 0, sizeof (cl_explosions[i]));
        !           171:                        return &cl_explosions[i];
        !           172:                }
        !           173:        }
        !           174: // find the oldest explosion
        !           175:        time = cl.time;
        !           176:        index = 0;
        !           177: 
        !           178:        for (i=0 ; i<MAX_EXPLOSIONS ; i++)
        !           179:                if (cl_explosions[i].start < time)
        !           180:                {
        !           181:                        time = cl_explosions[i].start;
        !           182:                        index = i;
        !           183:                }
        !           184:        memset (&cl_explosions[index], 0, sizeof (cl_explosions[index]));
        !           185:        return &cl_explosions[index];
        !           186: }
        !           187: 
        !           188: /*
        !           189: =================
        !           190: CL_SmokeAndFlash
        !           191: =================
        !           192: */
        !           193: void CL_SmokeAndFlash(vec3_t origin)
        !           194: {
        !           195:        explosion_t     *ex;
        !           196: 
        !           197:        ex = CL_AllocExplosion ();
        !           198:        VectorCopy (origin, ex->ent.origin);
        !           199:        ex->type = ex_misc;
        !           200:        ex->frames = 4;
        !           201:        ex->ent.flags = RF_TRANSLUCENT;
        !           202:        ex->start = cl.frame.servertime - 100;
        !           203:        ex->ent.model = cl_mod_smoke;
        !           204: 
        !           205:        ex = CL_AllocExplosion ();
        !           206:        VectorCopy (origin, ex->ent.origin);
        !           207:        ex->type = ex_flash;
        !           208:        ex->ent.flags = RF_FULLBRIGHT;
        !           209:        ex->frames = 2;
        !           210:        ex->start = cl.frame.servertime - 100;
        !           211:        ex->ent.model = cl_mod_flash;
        !           212: }
        !           213: 
        !           214: /*
        !           215: =================
        !           216: CL_ParseParticles
        !           217: =================
        !           218: */
        !           219: void CL_ParseParticles (void)
        !           220: {
        !           221:        int             color, count;
        !           222:        vec3_t  pos, dir;
        !           223: 
        !           224:        MSG_ReadPos (&net_message, pos);
        !           225:        MSG_ReadDir (&net_message, dir);
        !           226: 
        !           227:        color = MSG_ReadByte (&net_message);
        !           228: 
        !           229:        count = MSG_ReadByte (&net_message);
        !           230: 
        !           231:        CL_ParticleEffect (pos, dir, color, count);
        !           232: }
        !           233: 
        !           234: /*
        !           235: =================
        !           236: CL_ParseBeam
        !           237: =================
        !           238: */
        !           239: int CL_ParseBeam (struct model_s *model)
        !           240: {
        !           241:        int             ent;
        !           242:        vec3_t  start, end;
        !           243:        beam_t  *b;
        !           244:        int             i;
        !           245:        
        !           246:        ent = MSG_ReadShort (&net_message);
        !           247:        
        !           248:        MSG_ReadPos (&net_message, start);
        !           249:        MSG_ReadPos (&net_message, end);
        !           250: 
        !           251: // override any beam with the same entity
        !           252:        for (i=0, b=cl_beams ; i< MAX_BEAMS ; i++, b++)
        !           253:                if (b->entity == ent)
        !           254:                {
        !           255:                        b->entity = ent;
        !           256:                        b->model = model;
        !           257:                        b->endtime = cl.time + 200;
        !           258:                        VectorCopy (start, b->start);
        !           259:                        VectorCopy (end, b->end);
        !           260:                        VectorClear (b->offset);
        !           261:                        return ent;
        !           262:                }
        !           263: 
        !           264: // find a free beam
        !           265:        for (i=0, b=cl_beams ; i< MAX_BEAMS ; i++, b++)
        !           266:        {
        !           267:                if (!b->model || b->endtime < cl.time)
        !           268:                {
        !           269:                        b->entity = ent;
        !           270:                        b->model = model;
        !           271:                        b->endtime = cl.time + 200;
        !           272:                        VectorCopy (start, b->start);
        !           273:                        VectorCopy (end, b->end);
        !           274:                        VectorClear (b->offset);
        !           275:                        return ent;
        !           276:                }
        !           277:        }
        !           278:        Com_Printf ("beam list overflow!\n");   
        !           279:        return ent;
        !           280: }
        !           281: 
        !           282: /*
        !           283: =================
        !           284: CL_ParseBeam2
        !           285: =================
        !           286: */
        !           287: int CL_ParseBeam2 (struct model_s *model)
        !           288: {
        !           289:        int             ent;
        !           290:        vec3_t  start, end, offset;
        !           291:        beam_t  *b;
        !           292:        int             i;
        !           293:        
        !           294:        ent = MSG_ReadShort (&net_message);
        !           295:        
        !           296:        MSG_ReadPos (&net_message, start);
        !           297:        MSG_ReadPos (&net_message, end);
        !           298:        MSG_ReadPos (&net_message, offset);
        !           299: 
        !           300: // override any beam with the same entity
        !           301:        for (i=0, b=cl_beams ; i< MAX_BEAMS ; i++, b++)
        !           302:                if (b->entity == ent)
        !           303:                {
        !           304:                        b->entity = ent;
        !           305:                        b->model = model;
        !           306:                        b->endtime = cl.time + 200;
        !           307:                        VectorCopy (start, b->start);
        !           308:                        VectorCopy (end, b->end);
        !           309:                        VectorCopy (offset, b->offset);
        !           310:                        return ent;
        !           311:                }
        !           312: 
        !           313: // find a free beam
        !           314:        for (i=0, b=cl_beams ; i< MAX_BEAMS ; i++, b++)
        !           315:        {
        !           316:                if (!b->model || b->endtime < cl.time)
        !           317:                {
        !           318:                        b->entity = ent;
        !           319:                        b->model = model;
        !           320:                        b->endtime = cl.time + 200;
        !           321:                        VectorCopy (start, b->start);
        !           322:                        VectorCopy (end, b->end);
        !           323:                        VectorCopy (offset, b->offset);
        !           324:                        return ent;
        !           325:                }
        !           326:        }
        !           327:        Com_Printf ("beam list overflow!\n");   
        !           328:        return ent;
        !           329: }
        !           330: 
        !           331: /*
        !           332: =================
        !           333: CL_ParseLaser
        !           334: =================
        !           335: */
        !           336: void CL_ParseLaser (int colors)
        !           337: {
        !           338:        vec3_t  start;
        !           339:        vec3_t  end;
        !           340:        laser_t *l;
        !           341:        int             i;
        !           342: 
        !           343:        MSG_ReadPos (&net_message, start);
        !           344:        MSG_ReadPos (&net_message, end);
        !           345: 
        !           346:        for (i=0, l=cl_lasers ; i< MAX_LASERS ; i++, l++)
        !           347:        {
        !           348:                if (l->endtime < cl.time)
        !           349:                {
        !           350:                        l->ent.flags = RF_TRANSLUCENT | RF_BEAM;
        !           351:                        VectorCopy (start, l->ent.origin);
        !           352:                        VectorCopy (end, l->ent.oldorigin);
        !           353:                        l->ent.alpha = 0.30;
        !           354:                        l->ent.skinnum = (colors >> ((rand() % 4)*8)) & 0xff;
        !           355:                        l->ent.model = NULL;
        !           356:                        l->ent.frame = 4;
        !           357:                        l->endtime = cl.time + 100;
        !           358:                        return;
        !           359:                }
        !           360:        }
        !           361: }
        !           362: 
        !           363: 
        !           364: /*
        !           365: =================
        !           366: CL_ParseTEnt
        !           367: =================
        !           368: */
        !           369: static byte splash_color[] = {0x00, 0xe0, 0xb0, 0x50, 0xd0, 0xe0, 0xe8};
        !           370: 
        !           371: void CL_ParseTEnt (void)
        !           372: {
        !           373:        int             type;
        !           374:        vec3_t  pos, pos2, dir;
        !           375:        explosion_t     *ex;
        !           376:        int             cnt;
        !           377:        int             color;
        !           378:        int             r;
        !           379:        int             ent;
        !           380: 
        !           381:        type = MSG_ReadByte (&net_message);
        !           382: 
        !           383:        switch (type)
        !           384:        {
        !           385:        case TE_BLOOD:                  // bullet hitting flesh
        !           386:                MSG_ReadPos (&net_message, pos);
        !           387:                MSG_ReadDir (&net_message, dir);
        !           388:                CL_ParticleEffect (pos, dir, 0xe8, 60);
        !           389:                break;
        !           390: 
        !           391:        case TE_GUNSHOT:                        // bullet hitting wall
        !           392:        case TE_SPARKS:
        !           393:        case TE_BULLET_SPARKS:
        !           394:                MSG_ReadPos (&net_message, pos);
        !           395:                MSG_ReadDir (&net_message, dir);
        !           396:                if (type == TE_GUNSHOT)
        !           397:                        CL_ParticleEffect (pos, dir, 0, 40);
        !           398:                else
        !           399:                        CL_ParticleEffect (pos, dir, 0xe0, 6);
        !           400: 
        !           401:                if (type != TE_SPARKS)
        !           402:                {
        !           403:                        CL_SmokeAndFlash(pos);
        !           404: 
        !           405:                        // impact sound
        !           406:                        cnt = rand()&15;
        !           407:                        if (cnt == 1)
        !           408:                                S_StartSound (pos, 0, 0, cl_sfx_ric1, 1, ATTN_NORM, 0);
        !           409:                        else if (cnt == 2)
        !           410:                                S_StartSound (pos, 0, 0, cl_sfx_ric2, 1, ATTN_NORM, 0);
        !           411:                        else if (cnt == 3)
        !           412:                                S_StartSound (pos, 0, 0, cl_sfx_ric3, 1, ATTN_NORM, 0);
        !           413:                }
        !           414: 
        !           415:                break;
        !           416:                
        !           417:        case TE_SCREEN_SPARKS:
        !           418:        case TE_SHIELD_SPARKS:
        !           419:                MSG_ReadPos (&net_message, pos);
        !           420:                MSG_ReadDir (&net_message, dir);
        !           421:                if (type == TE_SCREEN_SPARKS)
        !           422:                        CL_ParticleEffect (pos, dir, 0xd0, 40);
        !           423:                else
        !           424:                        CL_ParticleEffect (pos, dir, 0xb0, 40);
        !           425:                //FIXME : replace or remove this sound
        !           426:                S_StartSound (pos, 0, 0, cl_sfx_lashit, 1, ATTN_NORM, 0);
        !           427:                break;
        !           428:                
        !           429:        case TE_SHOTGUN:                        // bullet hitting wall
        !           430:                MSG_ReadPos (&net_message, pos);
        !           431:                MSG_ReadDir (&net_message, dir);
        !           432:                CL_ParticleEffect (pos, dir, 0, 20);
        !           433:                CL_SmokeAndFlash(pos);
        !           434:                break;
        !           435: 
        !           436:        case TE_SPLASH:                 // bullet hitting water
        !           437:                cnt = MSG_ReadByte (&net_message);
        !           438:                MSG_ReadPos (&net_message, pos);
        !           439:                MSG_ReadDir (&net_message, dir);
        !           440:                r = MSG_ReadByte (&net_message);
        !           441:                if (r > 6)
        !           442:                        color = 0x00;
        !           443:                else
        !           444:                        color = splash_color[r];
        !           445:                CL_ParticleEffect (pos, dir, color, cnt);
        !           446: 
        !           447:                if (r == SPLASH_SPARKS)
        !           448:                {
        !           449:                        r = rand() & 3;
        !           450:                        if (r == 0)
        !           451:                                S_StartSound (pos, 0, 0, cl_sfx_spark5, 1, ATTN_STATIC, 0);
        !           452:                        else if (r == 1)
        !           453:                                S_StartSound (pos, 0, 0, cl_sfx_spark6, 1, ATTN_STATIC, 0);
        !           454:                        else
        !           455:                                S_StartSound (pos, 0, 0, cl_sfx_spark7, 1, ATTN_STATIC, 0);
        !           456:                }
        !           457:                break;
        !           458: 
        !           459:        case TE_LASER_SPARKS:
        !           460:                cnt = MSG_ReadByte (&net_message);
        !           461:                MSG_ReadPos (&net_message, pos);
        !           462:                MSG_ReadDir (&net_message, dir);
        !           463:                color = MSG_ReadByte (&net_message);
        !           464:                CL_ParticleEffect2 (pos, dir, color, cnt);
        !           465:                break;
        !           466: 
        !           467:        case TE_BLASTER:                        // blaster hitting wall
        !           468:                MSG_ReadPos (&net_message, pos);
        !           469:                MSG_ReadDir (&net_message, dir);
        !           470:                CL_BlasterParticles (pos, dir);
        !           471: 
        !           472:                ex = CL_AllocExplosion ();
        !           473:                VectorCopy (pos, ex->ent.origin);
        !           474:                ex->ent.angles[0] = acos(dir[2])/M_PI*180;
        !           475:                ex->ent.angles[2] = atan2(dir[1], dir[0])/M_PI*180;
        !           476:                ex->type = ex_misc;
        !           477:                ex->ent.flags = RF_FULLBRIGHT|RF_TRANSLUCENT;
        !           478:                ex->start = cl.frame.servertime - 100;
        !           479:                ex->light = 150;
        !           480:                ex->lightcolor[0] = 1;
        !           481:                ex->lightcolor[1] = 1;
        !           482:                ex->ent.model = cl_mod_explode;
        !           483:                ex->frames = 4;
        !           484:                S_StartSound (pos,  0, 0, cl_sfx_lashit, 1, ATTN_NORM, 0);
        !           485:                break;
        !           486:                
        !           487:        case TE_RAILTRAIL:                      // railgun effect
        !           488:                MSG_ReadPos (&net_message, pos);
        !           489:                MSG_ReadPos (&net_message, pos2);
        !           490:                CL_RailTrail (pos, pos2);
        !           491:                S_StartSound (pos2, 0, 0, cl_sfx_railg, 1, ATTN_NORM, 0);
        !           492:                break;
        !           493: 
        !           494:        case TE_PLASMATRAIL:
        !           495:                MSG_ReadPos (&net_message, pos);
        !           496:                MSG_ReadPos (&net_message, pos2);
        !           497:                CL_PlasmaTrail (pos, pos2);
        !           498:                S_StartSound (pos2, 0, 0, cl_sfx_railg, 1, ATTN_NORM, 0);
        !           499:                break;
        !           500: 
        !           501:        case TE_EXPLOSION2:
        !           502:        case TE_GRENADE_EXPLOSION:
        !           503:        case TE_GRENADE_EXPLOSION_WATER:
        !           504:                MSG_ReadPos (&net_message, pos);
        !           505: 
        !           506:                ex = CL_AllocExplosion ();
        !           507:                VectorCopy (pos, ex->ent.origin);
        !           508:                ex->type = ex_poly;
        !           509:                ex->ent.flags = RF_FULLBRIGHT;
        !           510:                ex->start = cl.frame.servertime - 100;
        !           511:                ex->light = 350;
        !           512:                ex->lightcolor[0] = 1.0;
        !           513:                ex->lightcolor[1] = 0.5;
        !           514:                ex->lightcolor[2] = 0.5;
        !           515:                ex->ent.model = cl_mod_explo4;
        !           516:                ex->frames = 19;
        !           517:                ex->baseframe = 30;
        !           518:                ex->ent.angles[1] = rand() % 360;
        !           519:                CL_ExplosionParticles (pos);
        !           520:                if (type == TE_GRENADE_EXPLOSION_WATER)
        !           521:                        S_StartSound (pos, 0, 0, cl_sfx_watrexp, 1, ATTN_NORM, 0);
        !           522:                else
        !           523:                        S_StartSound (pos, 0, 0, cl_sfx_grenexp, 1, ATTN_NORM, 0);
        !           524:                break;
        !           525: 
        !           526:        case TE_EXPLOSION1:
        !           527:        case TE_ROCKET_EXPLOSION:
        !           528:        case TE_ROCKET_EXPLOSION_WATER:
        !           529:                MSG_ReadPos (&net_message, pos);
        !           530: 
        !           531:                ex = CL_AllocExplosion ();
        !           532:                VectorCopy (pos, ex->ent.origin);
        !           533:                ex->type = ex_poly;
        !           534:                ex->ent.flags = RF_FULLBRIGHT;
        !           535:                ex->start = cl.frame.servertime - 100;
        !           536:                ex->light = 350;
        !           537:                ex->lightcolor[0] = 1.0;
        !           538:                ex->lightcolor[1] = 0.5;
        !           539:                ex->lightcolor[2] = 0.5;
        !           540:                ex->ent.angles[1] = rand() % 360;
        !           541:                ex->ent.model = cl_mod_explo4;
        !           542:                if (frand() < 0.5)
        !           543:                        ex->baseframe = 15;
        !           544:                ex->frames = 15;
        !           545:                CL_ExplosionParticles (pos);
        !           546:                if (type == TE_ROCKET_EXPLOSION_WATER)
        !           547:                        S_StartSound (pos, 0, 0, cl_sfx_watrexp, 1, ATTN_NORM, 0);
        !           548:                else
        !           549:                        S_StartSound (pos, 0, 0, cl_sfx_rockexp, 1, ATTN_NORM, 0);
        !           550:                break;
        !           551: 
        !           552:        case TE_BFG_EXPLOSION:
        !           553:                MSG_ReadPos (&net_message, pos);
        !           554:                ex = CL_AllocExplosion ();
        !           555:                VectorCopy (pos, ex->ent.origin);
        !           556:                ex->type = ex_poly;
        !           557:                ex->ent.flags = RF_FULLBRIGHT;
        !           558:                ex->start = cl.frame.servertime - 100;
        !           559:                ex->light = 350;
        !           560:                ex->lightcolor[0] = 0.0;
        !           561:                ex->lightcolor[1] = 1.0;
        !           562:                ex->lightcolor[2] = 0.0;
        !           563:                ex->ent.model = cl_mod_bfg_explo;
        !           564:                ex->ent.flags |= RF_TRANSLUCENT;
        !           565:                ex->ent.alpha = 0.30;
        !           566:                ex->frames = 4;
        !           567:                break;
        !           568: 
        !           569:        case TE_BFG_BIGEXPLOSION:
        !           570:                MSG_ReadPos (&net_message, pos);
        !           571:                CL_BFGExplosionParticles (pos);
        !           572:                break;
        !           573: 
        !           574:        case TE_BFG_LASER:
        !           575:                CL_ParseLaser (0xd0d1d2d3);
        !           576:                break;
        !           577: 
        !           578:        case TE_BUBBLETRAIL:
        !           579:                MSG_ReadPos (&net_message, pos);
        !           580:                MSG_ReadPos (&net_message, pos2);
        !           581:                CL_BubbleTrail (pos, pos2);
        !           582:                break;
        !           583: 
        !           584:        case TE_PARASITE_ATTACK:
        !           585:        case TE_MEDIC_CABLE_ATTACK:
        !           586:                ent = CL_ParseBeam (cl_mod_parasite_segment);
        !           587:                break;
        !           588: 
        !           589:        case TE_BOSSTPORT:                      // boss teleporting to station
        !           590:                MSG_ReadPos (&net_message, pos);
        !           591:                CL_BigTeleportParticles (pos);
        !           592:                S_StartSound (pos, 0, 0, S_RegisterSound ("misc/bigtele.wav"), 1, ATTN_NONE, 0);
        !           593:                break;
        !           594: 
        !           595:        case TE_GRAPPLE_CABLE:
        !           596:                ent = CL_ParseBeam2 (cl_mod_grapple_cable);
        !           597:                break;
        !           598: 
        !           599:        case TE_WELDING_SPARKS:
        !           600:                cnt = MSG_ReadByte (&net_message);
        !           601:                MSG_ReadPos (&net_message, pos);
        !           602:                MSG_ReadDir (&net_message, dir);
        !           603:                color = MSG_ReadByte (&net_message);
        !           604:                CL_ParticleEffect2 (pos, dir, color, cnt);
        !           605: 
        !           606:                ex = CL_AllocExplosion ();
        !           607:                VectorCopy (pos, ex->ent.origin);
        !           608:                ex->type = ex_flash;
        !           609:                // note to self
        !           610:                // we need a better no draw flag
        !           611:                ex->ent.flags = RF_BEAM;
        !           612:                ex->start = cl.frame.servertime - 0.1;
        !           613:                ex->light = 100 + (rand()%75);
        !           614:                ex->lightcolor[0] = 1.0;
        !           615:                ex->lightcolor[1] = 1.0;
        !           616:                ex->lightcolor[2] = 0.3;
        !           617:                ex->ent.model = cl_mod_flash;
        !           618:                ex->frames = 2;
        !           619:                break;
        !           620: 
        !           621:        case TE_GREENBLOOD:
        !           622:                MSG_ReadPos (&net_message, pos);
        !           623:                MSG_ReadDir (&net_message, dir);
        !           624:                CL_ParticleEffect2 (pos, dir, 0xc0, 30);
        !           625:                break;
        !           626:        
        !           627:        default:
        !           628:                Com_Error (ERR_DROP, "CL_ParseTEnt: bad type");
        !           629:        }
        !           630: }
        !           631: 
        !           632: /*
        !           633: =================
        !           634: CL_AddBeams
        !           635: =================
        !           636: */
        !           637: void CL_AddBeams (void)
        !           638: {
        !           639:        int                     i,j;
        !           640:        beam_t          *b;
        !           641:        vec3_t          dist, org;
        !           642:        float           d;
        !           643:        entity_t        ent;
        !           644:        float           yaw, pitch;
        !           645:        float           forward;
        !           646: 
        !           647: // update beams
        !           648:        for (i=0, b=cl_beams ; i< MAX_BEAMS ; i++, b++)
        !           649:        {
        !           650:                if (!b->model || b->endtime < cl.time)
        !           651:                        continue;
        !           652: 
        !           653:        // if coming from the player, update the start position
        !           654:                if (b->entity == cl.playernum+1)        // entity 0 is the world
        !           655:                {
        !           656:                        VectorCopy (cl.refdef.vieworg, b->start);
        !           657:                        b->start[2] -= 22;      // adjust for view height
        !           658:                }
        !           659: 
        !           660:                VectorAdd (b->start, b->offset, org);
        !           661: 
        !           662:        // calculate pitch and yaw
        !           663:                VectorSubtract (b->end, org, dist);
        !           664: 
        !           665:                if (dist[1] == 0 && dist[0] == 0)
        !           666:                {
        !           667:                        yaw = 0;
        !           668:                        if (dist[2] > 0)
        !           669:                                pitch = 90;
        !           670:                        else
        !           671:                                pitch = 270;
        !           672:                }
        !           673:                else
        !           674:                {
        !           675:                        yaw = (int) (atan2(dist[1], dist[0]) * 180 / M_PI);
        !           676:                        if (yaw < 0)
        !           677:                                yaw += 360;
        !           678:        
        !           679:                        forward = sqrt (dist[0]*dist[0] + dist[1]*dist[1]);
        !           680:                        pitch = (int) (atan2(dist[2], forward) * -180 / M_PI);
        !           681:                        if (pitch < 0)
        !           682:                                pitch += 360;
        !           683:                }
        !           684: 
        !           685:        // add new entities for the beams
        !           686:                d = VectorNormalize(dist);
        !           687:                memset (&ent, 0, sizeof(ent));
        !           688:                while (d > 0)
        !           689:                {
        !           690:                        VectorCopy (org, ent.origin);
        !           691:                        ent.model = b->model;
        !           692:                        ent.angles[0] = pitch;
        !           693:                        ent.angles[1] = yaw;
        !           694:                        ent.angles[2] = rand()%360;
        !           695: 
        !           696:                        V_AddEntity (&ent);
        !           697: 
        !           698:                        for (j=0 ; j<3 ; j++)
        !           699:                                org[j] += dist[j]*30;
        !           700:                        d -= 30;
        !           701:                }
        !           702:        }
        !           703:        
        !           704: }
        !           705: 
        !           706: /*
        !           707: =================
        !           708: CL_AddExplosions
        !           709: =================
        !           710: */
        !           711: void CL_AddExplosions (void)
        !           712: {
        !           713:        entity_t        *ent;
        !           714:        int                     i;
        !           715:        explosion_t     *ex;
        !           716:        float           frac;
        !           717:        int                     f;
        !           718: 
        !           719:        memset (&ent, 0, sizeof(ent));
        !           720: 
        !           721:        for (i=0, ex=cl_explosions ; i< MAX_EXPLOSIONS ; i++, ex++)
        !           722:        {
        !           723:                if (ex->type == ex_free)
        !           724:                        continue;
        !           725:                frac = (cl.time - ex->start)/100.0;
        !           726:                f = floor(frac);
        !           727: 
        !           728:                ent = &ex->ent;
        !           729: 
        !           730:                switch (ex->type)
        !           731:                {
        !           732:                case ex_mflash:
        !           733:                        if (f >= ex->frames-1)
        !           734:                                ex->type = ex_free;
        !           735:                        break;
        !           736:                case ex_misc:
        !           737:                        if (f >= ex->frames-1)
        !           738:                        {
        !           739:                                ex->type = ex_free;
        !           740:                                break;
        !           741:                        }
        !           742:                        ent->alpha = 1.0 - frac/(ex->frames-1);
        !           743:                        break;
        !           744:                case ex_flash:
        !           745:                        if (f >= 1)
        !           746:                        {
        !           747:                                ex->type = ex_free;
        !           748:                                break;
        !           749:                        }
        !           750:                        ent->alpha = 1.0;
        !           751:                        break;
        !           752:                case ex_poly:
        !           753:                        if (f >= ex->frames-1)
        !           754:                        {
        !           755:                                ex->type = ex_free;
        !           756:                                break;
        !           757:                        }
        !           758: 
        !           759:                        ent->alpha = (16.0 - (float)f)/16.0;
        !           760: 
        !           761:                        if (f < 10)
        !           762:                        {
        !           763:                                ent->skinnum = (f>>1);
        !           764:                                if (ent->skinnum < 0)
        !           765:                                        ent->skinnum = 0;
        !           766:                        }
        !           767:                        else
        !           768:                        {
        !           769:                                ent->flags |= RF_TRANSLUCENT;
        !           770:                                if (f < 13)
        !           771:                                        ent->skinnum = 5;
        !           772:                                else
        !           773:                                        ent->skinnum = 6;
        !           774:                        }
        !           775:                        break;
        !           776:                }
        !           777: 
        !           778:                if (ex->type == ex_free)
        !           779:                        continue;
        !           780:                if (ex->light)
        !           781:                {
        !           782:                        V_AddLight (ent->origin, ex->light*ent->alpha,
        !           783:                                ex->lightcolor[0], ex->lightcolor[1], ex->lightcolor[2]);
        !           784:                }
        !           785: 
        !           786:                VectorCopy (ent->origin, ent->oldorigin);
        !           787: 
        !           788:                if (f < 0)
        !           789:                        f = 0;
        !           790:                ent->frame = ex->baseframe + f + 1;
        !           791:                ent->oldframe = ex->baseframe + f;
        !           792:                ent->backlerp = 1.0 - cl.lerpfrac;
        !           793: 
        !           794:                V_AddEntity (ent);
        !           795:        }
        !           796: }
        !           797: 
        !           798: 
        !           799: /*
        !           800: =================
        !           801: CL_AddLasers
        !           802: =================
        !           803: */
        !           804: void CL_AddLasers (void)
        !           805: {
        !           806:        laser_t         *l;
        !           807:        int                     i;
        !           808: 
        !           809:        for (i=0, l=cl_lasers ; i< MAX_LASERS ; i++, l++)
        !           810:        {
        !           811:                if (l->endtime >= cl.time)
        !           812:                        V_AddEntity (&l->ent);
        !           813:        }
        !           814: }
        !           815: 
        !           816: 
        !           817: /*
        !           818: =================
        !           819: CL_AddTEnts
        !           820: =================
        !           821: */
        !           822: void CL_AddTEnts (void)
        !           823: {
        !           824:        CL_AddBeams ();
        !           825:        CL_AddExplosions ();
        !           826:        CL_AddLasers ();
        !           827: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.