Annotation of 43BSDReno/games/trek/events.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Copyright (c) 1980 Regents of the University of California.
                      3:  * All rights reserved.
                      4:  *
                      5:  * Redistribution and use in source and binary forms are permitted provided
                      6:  * that: (1) source distributions retain this entire copyright notice and
                      7:  * comment, and (2) distributions including binaries display the following
                      8:  * acknowledgement:  ``This product includes software developed by the
                      9:  * University of California, Berkeley and its contributors'' in the
                     10:  * documentation or other materials provided with the distribution and in
                     11:  * all advertising materials mentioning features or use of this software.
                     12:  * Neither the name of the University nor the names of its contributors may
                     13:  * be used to endorse or promote products derived from this software without
                     14:  * specific prior written permission.
                     15:  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
                     16:  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
                     17:  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
                     18:  */
                     19: 
                     20: #ifndef lint
                     21: static char sccsid[] = "@(#)events.c   5.4 (Berkeley) 6/1/90";
                     22: #endif /* not lint */
                     23: 
                     24: # include      "trek.h"
                     25: 
                     26: /*
                     27: **  CAUSE TIME TO ELAPSE
                     28: **
                     29: **     This routine does a hell of a lot.  It elapses time, eats up
                     30: **     energy, regenerates energy, processes any events that occur,
                     31: **     and so on.
                     32: */
                     33: 
                     34: 
                     35: events(warp)
                     36: int    warp;           /* set if called in a time warp */
                     37: {
                     38:        register int            i;
                     39:        int                     j;
                     40:        struct kling            *k;
                     41:        double                  rtime;
                     42:        double                  xdate;
                     43:        double                  idate;
                     44:        struct event            *ev, *xsched(), *schedule();
                     45:        int                     ix, iy;
                     46:        register struct quad    *q;
                     47:        register struct event   *e;
                     48:        int                     evnum;
                     49:        int                     restcancel;
                     50: 
                     51:        /* if nothing happened, just allow for any Klingons killed */
                     52:        if (Move.time <= 0.0)
                     53:        {
                     54:                Now.time = Now.resource / Now.klings;
                     55:                return (0);
                     56:        }
                     57: 
                     58:        /* indicate that the cloaking device is now working */
                     59:        Ship.cloakgood = 1;
                     60: 
                     61:        /* idate is the initial date */
                     62:        idate = Now.date;
                     63: 
                     64:        /* schedule attacks if resting too long */
                     65:        if (Move.time > 0.5 && Move.resting)
                     66:                schedule(E_ATTACK, 0.5, 0, 0, 0);
                     67: 
                     68:        /* scan the event list */
                     69:        while (1)
                     70:        {
                     71:                restcancel = 0;
                     72:                evnum = -1;
                     73:                /* xdate is the date of the current event */
                     74:                xdate = idate + Move.time;
                     75: 
                     76:                /* find the first event that has happened */
                     77:                for (i = 0; i < MAXEVENTS; i++)
                     78:                {
                     79:                        e = &Event[i];
                     80:                        if (e->evcode == 0 || (e->evcode & E_GHOST))
                     81:                                continue;
                     82:                        if (e->date < xdate)
                     83:                        {
                     84:                                xdate = e->date;
                     85:                                ev = e;
                     86:                                evnum = i;
                     87:                        }
                     88:                }
                     89:                e = ev;
                     90: 
                     91:                /* find the time between events */
                     92:                rtime = xdate - Now.date;
                     93: 
                     94:                /* decrement the magic "Federation Resources" pseudo-variable */
                     95:                Now.resource -= Now.klings * rtime;
                     96:                /* and recompute the time left */
                     97:                Now.time = Now.resource / Now.klings;
                     98: 
                     99:                /* move us up to the next date */
                    100:                Now.date = xdate;
                    101: 
                    102:                /* check for out of time */
                    103:                if (Now.time <= 0.0)
                    104:                        lose(L_NOTIME);
                    105: #              ifdef xTRACE
                    106:                if (evnum >= 0 && Trace)
                    107:                        printf("xdate = %.2f, evcode %d params %d %d %d\n",
                    108:                                xdate, e->evcode, e->x, e->y, e->systemname);
                    109: #              endif
                    110: 
                    111:                /* if evnum < 0, no events occurred  */
                    112:                if (evnum < 0)
                    113:                        break;
                    114: 
                    115:                /* otherwise one did.  Find out what it is */
                    116:                switch (e->evcode & E_EVENT)
                    117:                {
                    118: 
                    119:                  case E_SNOVA:                 /* supernova */
                    120:                        /* cause the supernova to happen */
                    121:                        snova(-1);
                    122:                        /* and schedule the next one */
                    123:                        xresched(e, E_SNOVA, 1);
                    124:                        break;
                    125: 
                    126:                  case E_LRTB:                  /* long range tractor beam */
                    127:                        /* schedule the next one */
                    128:                        xresched(e, E_LRTB, Now.klings);
                    129:                        /* LRTB cannot occur if we are docked */
                    130:                        if (Ship.cond != DOCKED)
                    131:                        {
                    132:                                /* pick a new quadrant */
                    133:                                i = ranf(Now.klings) + 1;
                    134:                                for (ix = 0; ix < NQUADS; ix++)
                    135:                                {
                    136:                                        for (iy = 0; iy < NQUADS; iy++)
                    137:                                        {
                    138:                                                q = &Quad[ix][iy];
                    139:                                                if (q->stars >= 0)
                    140:                                                        if ((i -= q->klings) <= 0)
                    141:                                                                break;
                    142:                                        }
                    143:                                        if (i <= 0)
                    144:                                                break;
                    145:                                }
                    146: 
                    147:                                /* test for LRTB to same quadrant */
                    148:                                if (Ship.quadx == ix && Ship.quady == iy)
                    149:                                        break;
                    150: 
                    151:                                /* nope, dump him in the new quadrant */
                    152:                                Ship.quadx = ix;
                    153:                                Ship.quady = iy;
                    154:                                printf("\n%s caught in long range tractor beam\n", Ship.shipname);
                    155:                                printf("*** Pulled to quadrant %d,%d\n", Ship.quadx, Ship.quady);
                    156:                                Ship.sectx = ranf(NSECTS);
                    157:                                Ship.secty = ranf(NSECTS);
                    158:                                initquad(0);
                    159:                                /* truncate the move time */
                    160:                                Move.time = xdate - idate;
                    161:                        }
                    162:                        break;
                    163: 
                    164:                  case E_KATSB:                 /* Klingon attacks starbase */
                    165:                        /* if out of bases, forget it */
                    166:                        if (Now.bases <= 0)
                    167:                        {
                    168:                                unschedule(e);
                    169:                                break;
                    170:                        }
                    171: 
                    172:                        /* check for starbase and Klingons in same quadrant */
                    173:                        for (i = 0; i < Now.bases; i++)
                    174:                        {
                    175:                                ix = Now.base[i].x;
                    176:                                iy = Now.base[i].y;
                    177:                                /* see if a Klingon exists in this quadrant */
                    178:                                q = &Quad[ix][iy];
                    179:                                if (q->klings <= 0)
                    180:                                        continue;
                    181: 
                    182:                                /* see if already distressed */
                    183:                                for (j = 0; j < MAXEVENTS; j++)
                    184:                                {
                    185:                                        e = &Event[j];
                    186:                                        if ((e->evcode & E_EVENT) != E_KDESB)
                    187:                                                continue;
                    188:                                        if (e->x == ix && e->y == iy)
                    189:                                                break;
                    190:                                }
                    191:                                if (j < MAXEVENTS)
                    192:                                        continue;
                    193: 
                    194:                                /* got a potential attack */
                    195:                                break;
                    196:                        }
                    197:                        e = ev;
                    198:                        if (i >= Now.bases)
                    199:                        {
                    200:                                /* not now; wait a while and see if some Klingons move in */
                    201:                                reschedule(e, 0.5 + 3.0 * franf());
                    202:                                break;
                    203:                        }
                    204:                        /* schedule a new attack, and a destruction of the base */
                    205:                        xresched(e, E_KATSB, 1);
                    206:                        e = xsched(E_KDESB, 1, ix, iy, 0);
                    207: 
                    208:                        /* report it if we can */
                    209:                        if (!damaged(SSRADIO))
                    210:                        {
                    211:                                printf("\nUhura:  Captain, we have recieved a distress signal\n");
                    212:                                printf("  from the starbase in quadrant %d,%d.\n",
                    213:                                        ix, iy);
                    214:                                restcancel++;
                    215:                        }
                    216:                        else
                    217:                                /* SSRADIO out, make it so we can't see the distress call */
                    218:                                /* but it's still there!!! */
                    219:                                e->evcode |= E_HIDDEN;
                    220:                        break;
                    221: 
                    222:                  case E_KDESB:                 /* Klingon destroys starbase */
                    223:                        unschedule(e);
                    224:                        q = &Quad[e->x][e->y];
                    225:                        /* if the base has mysteriously gone away, or if the Klingon
                    226:                           got tired and went home, ignore this event */
                    227:                        if (q->bases <=0 || q->klings <= 0)
                    228:                                break;
                    229:                        /* are we in the same quadrant? */
                    230:                        if (e->x == Ship.quadx && e->y == Ship.quady)
                    231:                        {
                    232:                                /* yep, kill one in this quadrant */
                    233:                                printf("\nSpock: ");
                    234:                                killb(Ship.quadx, Ship.quady);
                    235:                        }
                    236:                        else
                    237:                                /* kill one in some other quadrant */
                    238:                                killb(e->x, e->y);
                    239:                        break;
                    240: 
                    241:                  case E_ISSUE:         /* issue a distress call */
                    242:                        xresched(e, E_ISSUE, 1);
                    243:                        /* if we already have too many, throw this one away */
                    244:                        if (Ship.distressed >= MAXDISTR)
                    245:                                break;
                    246:                        /* try a whole bunch of times to find something suitable */
                    247:                        for (i = 0; i < 100; i++)
                    248:                        {
                    249:                                ix = ranf(NQUADS);
                    250:                                iy = ranf(NQUADS);
                    251:                                q = &Quad[ix][iy];
                    252:                                /* need a quadrant which is not the current one,
                    253:                                   which has some stars which are inhabited and
                    254:                                   not already under attack, which is not
                    255:                                   supernova'ed, and which has some Klingons in it */
                    256:                                if (!((ix == Ship.quadx && iy == Ship.quady) || q->stars < 0 ||
                    257:                                    (q->qsystemname & Q_DISTRESSED) ||
                    258:                                    (q->qsystemname & Q_SYSTEM) == 0 || q->klings <= 0))
                    259:                                        break;
                    260:                        }
                    261:                        if (i >= 100)
                    262:                                /* can't seem to find one; ignore this call */
                    263:                                break;
                    264: 
                    265:                        /* got one!!  Schedule its enslavement */
                    266:                        Ship.distressed++;
                    267:                        e = xsched(E_ENSLV, 1, ix, iy, q->qsystemname);
                    268:                        q->qsystemname = (e - Event) | Q_DISTRESSED;
                    269: 
                    270:                        /* tell the captain about it if we can */
                    271:                        if (!damaged(SSRADIO))
                    272:                        {
                    273:                                printf("\nUhura: Captain, starsystem %s in quadrant %d,%d is under attack\n",
                    274:                                        Systemname[e->systemname], ix, iy);
                    275:                                restcancel++;
                    276:                        }
                    277:                        else
                    278:                                /* if we can't tell him, make it invisible */
                    279:                                e->evcode |= E_HIDDEN;
                    280:                        break;
                    281: 
                    282:                  case E_ENSLV:         /* starsystem is enslaved */
                    283:                        unschedule(e);
                    284:                        /* see if current distress call still active */
                    285:                        q = &Quad[e->x][e->y];
                    286:                        if (q->klings <= 0)
                    287:                        {
                    288:                                /* no Klingons, clean up */
                    289:                                /* restore the system name */
                    290:                                q->qsystemname = e->systemname;
                    291:                                break;
                    292:                        }
                    293: 
                    294:                        /* play stork and schedule the first baby */
                    295:                        e = schedule(E_REPRO, Param.eventdly[E_REPRO] * franf(), e->x, e->y, e->systemname);
                    296: 
                    297:                        /* report the disaster if we can */
                    298:                        if (!damaged(SSRADIO))
                    299:                        {
                    300:                                printf("\nUhura:  We've lost contact with starsystem %s\n",
                    301:                                        Systemname[e->systemname]);
                    302:                                printf("  in quadrant %d,%d.\n",
                    303:                                        e->x, e->y);
                    304:                        }
                    305:                        else
                    306:                                e->evcode |= E_HIDDEN;
                    307:                        break;
                    308: 
                    309:                  case E_REPRO:         /* Klingon reproduces */
                    310:                        /* see if distress call is still active */
                    311:                        q = &Quad[e->x][e->y];
                    312:                        if (q->klings <= 0)
                    313:                        {
                    314:                                unschedule(e);
                    315:                                q->qsystemname = e->systemname;
                    316:                                break;
                    317:                        }
                    318:                        xresched(e, E_REPRO, 1);
                    319:                        /* reproduce one Klingon */
                    320:                        ix = e->x;
                    321:                        iy = e->y;
                    322:                        if (Now.klings == 127)
                    323:                                break;          /* full right now */
                    324:                        if (q->klings >= MAXKLQUAD)
                    325:                        {
                    326:                                /* this quadrant not ok, pick an adjacent one */
                    327:                                for (i = ix - 1; i <= ix + 1; i++)
                    328:                                {
                    329:                                        if (i < 0 || i >= NQUADS)
                    330:                                                continue;
                    331:                                        for (j = iy - 1; j <= iy + 1; j++)
                    332:                                        {
                    333:                                                if (j < 0 || j >= NQUADS)
                    334:                                                        continue;
                    335:                                                q = &Quad[i][j];
                    336:                                                /* check for this quad ok (not full & no snova) */
                    337:                                                if (q->klings >= MAXKLQUAD || q->stars < 0)
                    338:                                                        continue;
                    339:                                                break;
                    340:                                        }
                    341:                                        if (j <= iy + 1)
                    342:                                                break;
                    343:                                }
                    344:                                if (j > iy + 1)
                    345:                                        /* cannot create another yet */
                    346:                                        break;
                    347:                                ix = i;
                    348:                                iy = j;
                    349:                        }
                    350:                        /* deliver the child */
                    351:                        q->klings++;
                    352:                        Now.klings++;
                    353:                        if (ix == Ship.quadx && iy == Ship.quady)
                    354:                        {
                    355:                                /* we must position Klingon */
                    356:                                sector(&ix, &iy);
                    357:                                Sect[ix][iy] = KLINGON;
                    358:                                k = &Etc.klingon[Etc.nkling++];
                    359:                                k->x = ix;
                    360:                                k->y = iy;
                    361:                                k->power = Param.klingpwr;
                    362:                                k->srndreq = 0;
                    363:                                compkldist(Etc.klingon[0].dist == Etc.klingon[0].avgdist ? 0 : 1);
                    364:                        }
                    365: 
                    366:                        /* recompute time left */
                    367:                        Now.time = Now.resource / Now.klings;
                    368:                        break;
                    369: 
                    370:                  case E_SNAP:          /* take a snapshot of the galaxy */
                    371:                        xresched(e, E_SNAP, 1);
                    372:                        i = (int) Etc.snapshot;
                    373:                        i = bmove(Quad, i, sizeof (Quad));
                    374:                        i = bmove(Event, i, sizeof (Event));
                    375:                        i = bmove(&Now, i, sizeof (Now));
                    376:                        Game.snap = 1;
                    377:                        break;
                    378: 
                    379:                  case E_ATTACK:        /* Klingons attack during rest period */
                    380:                        if (!Move.resting)
                    381:                        {
                    382:                                unschedule(e);
                    383:                                break;
                    384:                        }
                    385:                        attack(1);
                    386:                        reschedule(e, 0.5);
                    387:                        break;
                    388: 
                    389:                  case E_FIXDV:
                    390:                        i = e->systemname;
                    391:                        unschedule(e);
                    392: 
                    393:                        /* de-damage the device */
                    394:                        printf("%s reports repair work on the %s finished.\n",
                    395:                                Device[i].person, Device[i].name);
                    396: 
                    397:                        /* handle special processing upon fix */
                    398:                        switch (i)
                    399:                        {
                    400: 
                    401:                          case LIFESUP:
                    402:                                Ship.reserves = Param.reserves;
                    403:                                break;
                    404: 
                    405:                          case SINS:
                    406:                                if (Ship.cond == DOCKED)
                    407:                                        break;
                    408:                                printf("Spock has tried to recalibrate your Space Internal Navigation System,\n");
                    409:                                printf("  but he has no standard base to calibrate to.  Suggest you get\n");
                    410:                                printf("  to a starbase immediately so that you can properly recalibrate.\n");
                    411:                                Ship.sinsbad = 1;
                    412:                                break;
                    413: 
                    414:                          case SSRADIO:
                    415:                                restcancel = dumpssradio();
                    416:                                break;
                    417:                        }
                    418:                        break;
                    419: 
                    420:                  default:
                    421:                        break;
                    422:                }
                    423: 
                    424:                if (restcancel && Move.resting && getynpar("Spock: Shall we cancel our rest period"))
                    425:                        Move.time = xdate - idate;
                    426: 
                    427:        }
                    428: 
                    429:        /* unschedule an attack during a rest period */
                    430:        if (e = Now.eventptr[E_ATTACK])
                    431:                unschedule(e);
                    432: 
                    433:        if (!warp)
                    434:        {
                    435:                /* eat up energy if cloaked */
                    436:                if (Ship.cloaked)
                    437:                        Ship.energy -= Param.cloakenergy * Move.time;
                    438: 
                    439:                /* regenerate resources */
                    440:                rtime = 1.0 - exp(-Param.regenfac * Move.time);
                    441:                Ship.shield += (Param.shield - Ship.shield) * rtime;
                    442:                Ship.energy += (Param.energy - Ship.energy) * rtime;
                    443: 
                    444:                /* decrement life support reserves */
                    445:                if (damaged(LIFESUP) && Ship.cond != DOCKED)
                    446:                        Ship.reserves -= Move.time;
                    447:        }
                    448:        return (0);
                    449: }

unix.superglobalmegacorp.com

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