mirror of
https://github.com/KolibriOS/kolibrios.git
synced 2024-12-29 17:59:50 +03:00
3a4ccc4ac4
git-svn-id: svn://kolibrios.org@7185 a494cfbc-eb01-0410-851d-a64ba20cac60
811 lines
23 KiB
C
811 lines
23 KiB
C
#include "sst.h"
|
||
#include <math.h>
|
||
|
||
void events(void) {
|
||
|
||
int ictbeam=0, ipage=0, istract=0, line, i, j, k, l, ixhold, iyhold;
|
||
double fintim = d.date + Time, datemin, xtime, repair, yank;
|
||
|
||
|
||
#ifdef DEBUG
|
||
if (idebug) prout("EVENTS");
|
||
#endif
|
||
|
||
if (stdamtim == 1e30 && !REPORTS)
|
||
{
|
||
/* chart will no longer be updated because radio is dead */
|
||
stdamtim = d.date;
|
||
for (i=1; i <= 8 ; i++)
|
||
for (j=1; j <= 8; j++)
|
||
if (starch[i][j] == 1) starch[i][j] = d.galaxy[i][j]+1000;
|
||
}
|
||
|
||
for (;;) {
|
||
/* Select earliest extraneous event, line==0 if no events */
|
||
line = FSPY;
|
||
if (alldone) return;
|
||
datemin = fintim;
|
||
for (l=1; l<=NEVENTS; l++)
|
||
if (future[l] <= datemin) {
|
||
line = l;
|
||
datemin = future[l];
|
||
}
|
||
xtime = datemin-d.date;
|
||
#ifdef CLOAKING
|
||
if (iscloaking) {
|
||
energy -= xtime*500.0;
|
||
if (energy <= 0.) {
|
||
finish(FNRG);
|
||
return;
|
||
}
|
||
}
|
||
#endif
|
||
d.date = datemin;
|
||
/* Decrement Federation resources and recompute remaining time */
|
||
d.remres -= (d.remkl+4*d.remcom)*xtime;
|
||
d.remtime = d.remres/(d.remkl+4*d.remcom);
|
||
if (d.remtime <=0) {
|
||
finish(FDEPLETE);
|
||
return;
|
||
}
|
||
/* Is life support adequate? */
|
||
if (damage[DLIFSUP] && condit != IHDOCKED) {
|
||
if (lsupres < xtime && damage[DLIFSUP] > lsupres) {
|
||
finish(FLIFESUP);
|
||
return;
|
||
}
|
||
lsupres -= xtime;
|
||
if (damage[DLIFSUP] <= xtime) lsupres = inlsr;
|
||
}
|
||
/* Fix devices */
|
||
repair = xtime;
|
||
if (condit == IHDOCKED) repair /= docfac;
|
||
/* Don't fix Deathray here */
|
||
for (l=1; l<=ndevice; l++)
|
||
if (damage[l] > 0.0 && l != DDRAY)
|
||
damage[l] -= (damage[l]-repair > 0.0 ? repair : damage[l]);
|
||
/* Fix Deathray if docked */
|
||
if (damage[DDRAY] > 0.0 && condit == IHDOCKED)
|
||
damage[DDRAY] -= (damage[l] - xtime > 0.0 ? xtime : damage[DDRAY]);
|
||
/* If radio repaired, update star chart and attack reports */
|
||
if (stdamtim != 1e30 && REPORTS) {
|
||
stdamtim = 1e30;
|
||
/* prout("Lt. Uhura- \"Captain, the sub-space radio is working and");
|
||
prout(" surveillance reports are coming in.");*/
|
||
prout("<EFBFBD><EFBFBD><EFBFBD>⥭<EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>- \"<EFBFBD><EFBFBD><EFBFBD><EFBFBD>⠭, <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>࠭<EFBFBD>⢥<EFBFBD><E2A2A5><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> ࠡ<>⠥<EFBFBD>");
|
||
prout(" <20> <20><> <20>ਭ<EFBFBD><E0A8AD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> ࠧ<><E0A0A7><EFBFBD><EFBFBD><EFBFBD>.");
|
||
skip(1);
|
||
for (i=1; i <= 8 ; i++)
|
||
for (j=1; j <= 8; j++)
|
||
if (starch[i][j] > 999) starch[i][j] = 1;
|
||
if (iseenit==0) {
|
||
attakreport();
|
||
iseenit = 1;
|
||
}
|
||
skip(1);
|
||
/* prout(" The star chart is now up to date.\"");*/
|
||
prout(" <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>.\"");
|
||
skip(1);
|
||
}
|
||
/* Cause extraneous event LINE to occur */
|
||
Time -= xtime;
|
||
switch (line) {
|
||
case FSNOVA: /* Supernova */
|
||
if (ipage==0) pause(1);
|
||
ipage=1;
|
||
snova(0,0);
|
||
future[FSNOVA] = d.date + expran(0.5*intime);
|
||
if (d.galaxy[quadx][quady] == 1000) return;
|
||
break;
|
||
case FSPY: /* Check with spy to see if S.C. should tractor beam */
|
||
if (d.nscrem == 0 ||
|
||
#ifdef CLOAKING
|
||
iscloaked || /* Cannot tractor beam if we can't be seen! */
|
||
#endif
|
||
ictbeam+istract > 0 ||
|
||
condit==IHDOCKED || isatb==1 || iscate==1) return;
|
||
if (ientesc ||
|
||
(energy < 2000 && torps < 4 && shield < 1250) ||
|
||
(damage[DPHASER]>0 && (damage[DPHOTON]>0 || torps < 4)) ||
|
||
(damage[DSHIELD] > 0 &&
|
||
(energy < 2500 || damage[DPHASER] > 0) &&
|
||
(torps < 5 || damage[DPHOTON] > 0))) {
|
||
/* Tractor-beam her! */
|
||
istract=1;
|
||
yank = square(d.isx-quadx) + square(d.isy-quady);
|
||
/*********TBEAM CODE***********/
|
||
}
|
||
else return;
|
||
case FTBEAM: /* Tractor beam */
|
||
if (line==FTBEAM) {
|
||
if (d.remcom == 0) {
|
||
future[FTBEAM] = 1e30;
|
||
break;
|
||
}
|
||
i = Rand()*d.remcom+1.0;
|
||
yank = square(d.cx[i]-quadx) + square(d.cy[i]-quady);
|
||
if (istract || condit == IHDOCKED ||
|
||
#ifdef CLOAKING
|
||
iscloaked || /* cannot tractor beam if we can't be seen */
|
||
#endif
|
||
yank == 0) {
|
||
/* Drats! Have to reschedule */
|
||
future[FTBEAM] = d.date + Time +
|
||
expran(1.5*intime/d.remcom);
|
||
break;
|
||
}
|
||
}
|
||
/* tractor beaming cases merge here */
|
||
yank = sqrt(yank);
|
||
if (ipage==0) pause(1);
|
||
ipage=1;
|
||
Time = (10.0/(7.5*7.5))*yank; /* 7.5 is yank rate (warp 7.5) */
|
||
ictbeam = 1;
|
||
skip(1);
|
||
proutn("***");
|
||
crmshp();
|
||
/* prout(" caught in long range tractor beam--");*/
|
||
prout(" <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFA3A8><EFBFBD>騬 <20><>箬--");
|
||
/* If Kirk & Co. screwing around on planet, handle */
|
||
atover(1); /* atover(1) is Grab */
|
||
if (alldone) return;
|
||
if (icraft == 1) { /* Caught in Galileo? */
|
||
finish(FSTRACTOR);
|
||
return;
|
||
}
|
||
/* Check to see if shuttle is aboard */
|
||
if (iscraft==0) {
|
||
skip(1);
|
||
if (Rand() >0.5) {
|
||
/* prout("Galileo, left on the planet surface, is captured");
|
||
prout("by aliens and made into a flying McDonald's.");*/
|
||
prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><>⠢訩<E2A0A2><E8A8A9> <20><> <20><><EFBFBD><EFBFBD><EFBFBD>孮<EFBFBD><E5ADAE><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD> <20><>墠祭");
|
||
prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ﭠ<EFBFBD><EFBFBD> <20> <20>ॢ<EFBFBD><E0A5A2>饭 <20> <20><><EFBFBD><EFBFBD><EFBFBD>騩 <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>.");
|
||
damage[DSHUTTL] = -10;
|
||
iscraft = -1;
|
||
}
|
||
else {
|
||
/* prout("Galileo, left on the planet surface, is well hidden.");*/
|
||
prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><>⠢訩<E2A0A2><E8A8A9> <20><> <20><><EFBFBD><EFBFBD><EFBFBD>孮<EFBFBD><E5ADAE><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>⠭.");
|
||
}
|
||
}
|
||
if (line==0) {
|
||
quadx = d.isx;
|
||
quady = d.isy;
|
||
}
|
||
else {
|
||
quadx = d.cx[i];
|
||
quady = d.cy[i];
|
||
}
|
||
iran10(§x, §y);
|
||
crmshp();
|
||
proutn(" <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20> <20><><EFBFBD><EFBFBD><EFBFBD>");/*is pulled to*/
|
||
cramlc(1, quadx, quady);
|
||
proutn(", ");
|
||
cramlc(2, sectx, secty);
|
||
skip(1);
|
||
if (resting) {
|
||
/* prout("(Remainder of rest/repair period cancelled.)");*/
|
||
prout("(<28><><EFBFBD><EFBFBD><EFBFBD>/६<><E0A5AC><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>筮 <20><><EFBFBD>ࢠ<EFBFBD>.)");
|
||
resting = 0;
|
||
}
|
||
if (shldup==0) {
|
||
if (damage[DSHIELD]==0 && shield > 0) {
|
||
sheild(2); /* Shldsup */
|
||
shldchg=0;
|
||
}
|
||
else prout("(<28><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD> <20><> <20><>⮢<EFBFBD> <20> ࠡ<><E0A0A1><EFBFBD>.)");/*Shields not currently useable*/
|
||
}
|
||
newqad(0);
|
||
/* Adjust finish time to time of tractor beaming */
|
||
fintim = d.date+Time;
|
||
if (d.remcom <= 0) future[FTBEAM] = 1e30;
|
||
else future[FTBEAM] = d.date+Time+expran(1.5*intime/d.remcom);
|
||
break;
|
||
case FSNAP: /* Snapshot of the universe (for time warp) */
|
||
snapsht = d;
|
||
d.snap = 1;
|
||
future[FSNAP] = d.date + expran(0.5 * intime);
|
||
break;
|
||
case FBATTAK: /* Commander attacks starbase */
|
||
if (d.remcom==0 || d.rembase==0) {
|
||
/* no can do */
|
||
future[FBATTAK] = future[FCDBAS] = 1e30;
|
||
break;
|
||
}
|
||
i = 0;
|
||
for (j=1; j<=d.rembase; j++) {
|
||
for (k=1; k<=d.remcom; k++)
|
||
if (d.baseqx[j]==d.cx[k] && d.baseqy[j]==d.cy[k] &&
|
||
(d.baseqx[j]!=quadx || d.baseqy[j]!=quady) &&
|
||
(d.baseqx[j]!=d.isx || d.baseqy[j]!=d.isy)) {
|
||
i = 1;
|
||
break;
|
||
}
|
||
if (i == 1) break;
|
||
}
|
||
if (j>d.rembase) {
|
||
/* no match found -- try later */
|
||
future[FBATTAK] = d.date + expran(0.3*intime);
|
||
future[FCDBAS] = 1e30;
|
||
break;
|
||
}
|
||
/* commander + starbase combination found -- launch attack */
|
||
batx = d.baseqx[j];
|
||
baty = d.baseqy[j];
|
||
future[FCDBAS] = d.date+1.0+3.0*Rand();
|
||
if (isatb) /* extra time if SC already attacking */
|
||
future[FCDBAS] += future[FSCDBAS]-d.date;
|
||
future[FBATTAK] = future[FCDBAS] +expran(0.3*intime);
|
||
iseenit = 0;
|
||
if (!REPORTS)
|
||
break; /* No warning :-( */
|
||
iseenit = 1;
|
||
if (ipage==0) pause(1);
|
||
ipage = 1;
|
||
skip(1);
|
||
/* proutn("Lt. Uhura- \"Captain, the starbase in"); */
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD>⥭<EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>- \"<EFBFBD><EFBFBD><EFBFBD><EFBFBD>⠭, <20><><EFBFBD><EFBFBD><EFBFBD>㦥<EFBFBD><E3A6A5><EFBFBD><EFBFBD> <20>⠭<EFBFBD><E2A0AD><EFBFBD> <20> <20><>窥");
|
||
cramlc(1, batx, baty);
|
||
skip(1);
|
||
/* prout(" reports that it is under atttack and that it can");
|
||
proutn(" hold out only until stardate ");
|
||
*/ prout(" <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>뢠<EFBFBD><EBA2A0>, <20><><EFBFBD> <20><>室<EFBFBD><E5AEA4><EFBFBD><EFBFBD> <20><><EFBFBD> <20>⠪<EFBFBD><E2A0AA>");
|
||
proutn(" <20> <20>த<EFBFBD>ন<EFBFBD><E0A6A8><EFBFBD> <20><><EFBFBD>ᨬ<EFBFBD><E1A8AC> <20><> ");
|
||
cramf(future[FCDBAS],1,1);
|
||
prout(".\"");
|
||
if (resting) {
|
||
skip(1);
|
||
/* proutn("Mr. Spock- \"Captain, shall we cancel the rest period?\"");
|
||
*/ proutn("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>- \"<EFBFBD><EFBFBD><EFBFBD><EFBFBD>⠭, <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD>ࢠ<EFBFBD><E0A2A0> <20><><EFBFBD><EFBFBD><EFBFBD>?\"");
|
||
if (ja()) {
|
||
resting = 0;
|
||
Time = 0.0;
|
||
return;
|
||
}
|
||
}
|
||
break;
|
||
case FSCDBAS: /* Supercommander destroys base */
|
||
future[FSCDBAS] = 1e30;
|
||
isatb = 2;
|
||
if (d.galaxy[d.isx][d.isy]%100 < 10) break; /* WAS RETURN! */
|
||
ixhold = batx;
|
||
iyhold = baty;
|
||
batx = d.isx;
|
||
baty = d.isy;
|
||
case FCDBAS: /* Commander succeeds in destroying base */
|
||
if (line==FCDBAS) {
|
||
future[FCDBAS] = 1e30;
|
||
/* find the lucky pair */
|
||
for (i = 1; i <= d.remcom; i++)
|
||
if (d.cx[i]==batx && d.cy[i]==baty) break;
|
||
if (i > d.remcom || d.rembase == 0 ||
|
||
d.galaxy[batx][baty] % 100 < 10) {
|
||
/* No action to take after all */
|
||
batx = baty = 0;
|
||
break;
|
||
}
|
||
}
|
||
/* Code merges here for any commander destroying base */
|
||
/* Not perfect, but will have to do */
|
||
if (starch[batx][baty] == -1) starch[batx][baty] = 0;
|
||
/* Handle case where base is in same quadrant as starship */
|
||
if (batx==quadx && baty==quady) {
|
||
if (starch[batx][baty] > 999) starch[batx][baty] -= 10;
|
||
quad[basex][basey]= IHDOT;
|
||
basex=basey=0;
|
||
newcnd();
|
||
skip(1);
|
||
/* prout("Spock- \"Captain, I believe the starbase has been destroyed.\""); */
|
||
prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD>- \"<EFBFBD><EFBFBD><EFBFBD><EFBFBD>⠭, <20> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD> <20>⠭<EFBFBD><E2A0AD><EFBFBD> <20>뫠 㭨<>⮦<EFBFBD><E2AEA6><EFBFBD>.\"");
|
||
}
|
||
else if (d.rembase != 1 && REPORTS) {
|
||
/* Get word via subspace radio */
|
||
if (ipage==0) pause(1);
|
||
ipage = 1;
|
||
skip(1);
|
||
/* prout("Lt. Uhura- \"Captain, Starfleet Command reports that");
|
||
proutn(" the starbase in"); */
|
||
prout("<EFBFBD><EFBFBD><EFBFBD>⥭<EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>- \"<EFBFBD><EFBFBD><EFBFBD><EFBFBD>⠭, <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> ᮮ<>頥<EFBFBD>,");
|
||
proutn(" <20>⠭<EFBFBD><E2A0AD><EFBFBD> <20>");
|
||
cramlc(1, batx, baty);
|
||
prout(" <20>뫠 㭨<>⮦<EFBFBD><E2AEA6><EFBFBD>");/* has been destroyed by */
|
||
if (isatb==2) prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>᪨<EFBFBD> <20>㯥<EFBFBD><E3AFA5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>");/* the Klingon Super-Commander */
|
||
else prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>᪨<EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>");/* the Klingon Commander */
|
||
}
|
||
/* Remove Starbase from galaxy */
|
||
d.galaxy[batx][baty] -= 10;
|
||
for (i=1; i <= d.rembase; i++)
|
||
if (d.baseqx[i]==batx && d.baseqy[i]==baty) {
|
||
d.baseqx[i]=d.baseqx[d.rembase];
|
||
d.baseqy[i]=d.baseqy[d.rembase];
|
||
}
|
||
d.rembase--;
|
||
if (isatb == 2) {
|
||
/* reinstate a commander's base attack */
|
||
batx = ixhold;
|
||
baty = iyhold;
|
||
isatb = 0;
|
||
}
|
||
else {
|
||
batx = baty = 0;
|
||
}
|
||
break;
|
||
case FSCMOVE: /* Supercommander moves */
|
||
future[FSCMOVE] = d.date+0.2777;
|
||
if (ientesc+istract==0 &&
|
||
isatb!=1 &&
|
||
(iscate!=1 || justin==1)) scom(&ipage);
|
||
break;
|
||
case FDSPROB: /* Move deep space probe */
|
||
future[FDSPROB] = d.date + 0.01;
|
||
probex += probeinx;
|
||
probey += probeiny;
|
||
i = (int)(probex/10 +0.05);
|
||
j = (int)(probey/10 + 0.05);
|
||
if (probecx != i || probecy != j) {
|
||
probecx = i;
|
||
probecy = j;
|
||
if (i < 1 || i > 8 || j < 1 || j > 8 ||
|
||
d.galaxy[probecx][probecy] == 1000) {
|
||
// Left galaxy or ran into supernova
|
||
if (REPORTS) {
|
||
if (ipage==0) pause(1);
|
||
ipage = 1;
|
||
skip(1);
|
||
/* proutn("Lt. Uhura- \"The deep space probe "); */
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD>⥭<EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>- \"<EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD>쭥<EFBFBD> ࠧ<><E0A0A7><EFBFBD><EFBFBD><EFBFBD> ");
|
||
if (i < 1 ||i > 8 || j < 1 || j > 8)
|
||
/* proutn("has left the galaxy"); */
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>⨪<EFBFBD>");
|
||
else
|
||
/* proutn("is no longer transmitting"); */
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>㯥<EFBFBD>");
|
||
prout(".\"");
|
||
}
|
||
future[FDSPROB] = 1e30;
|
||
break;
|
||
}
|
||
if (REPORTS) {
|
||
if (ipage==0) pause(1);
|
||
ipage = 1;
|
||
skip(1);
|
||
/* proutn("Lt. Uhura- \"The deep space probe is now in "); */
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD>⥭<EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>- \"<EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD>쭥<EFBFBD> ࠧ<><E0A0A7><EFBFBD><EFBFBD><EFBFBD> ᥩ<><E1A5A9><EFBFBD> <20>");
|
||
cramlc(1, probecx, probecy);
|
||
prout(".\"");
|
||
}
|
||
}
|
||
/* Update star chart if Radio is working or have access to
|
||
radio. */
|
||
if (REPORTS)
|
||
starch[probecx][probecy] = damage[DRADIO] > 0.0 ?
|
||
d.galaxy[probecx][probecy]+1000 : 1;
|
||
proben--; // One less to travel
|
||
if (proben == 0 && isarmed &&
|
||
d.galaxy[probecx][probecy] % 10 > 0) {
|
||
/* lets blow the sucker! */
|
||
snova(1,0);
|
||
future[FDSPROB] = 1e30;
|
||
if (d.galaxy[quadx][quady] == 1000) return;
|
||
}
|
||
break;
|
||
}
|
||
}
|
||
}
|
||
|
||
|
||
void waiting(void) {
|
||
int key;
|
||
double temp, delay, origTime;
|
||
|
||
ididit = 0;
|
||
for (;;) {
|
||
key = scan();
|
||
if (key != IHEOL) break;
|
||
proutn("How long? ");
|
||
}
|
||
chew();
|
||
if (key != IHREAL) {
|
||
huh();
|
||
return;
|
||
}
|
||
origTime = delay = aaitem;
|
||
if (delay <= 0.0) return;
|
||
if (delay >= d.remtime || nenhere != 0) {
|
||
/* prout("Are you sure? "); */
|
||
prout("<EFBFBD><EFBFBD> 㢥७<E3A2A5>? ");
|
||
if (ja() == 0) return;
|
||
}
|
||
|
||
/* Alternate resting periods (events) with attacks */
|
||
|
||
resting = 1;
|
||
do {
|
||
if (delay <= 0) resting = 0;
|
||
if (resting == 0) {
|
||
cramf(d.remtime, 0, 2);
|
||
/* prout(" stardates left."); */
|
||
prout(" <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD> <20><>⠫<EFBFBD><E2A0AB><EFBFBD>.");
|
||
return;
|
||
}
|
||
temp = Time = delay;
|
||
|
||
if (nenhere) {
|
||
double rtime = 1.0 + Rand();
|
||
if (rtime < temp) temp = rtime;
|
||
Time = temp;
|
||
}
|
||
if (Time < delay) attack(0);
|
||
if (nenhere==0) movetho();
|
||
if (alldone) return;
|
||
events();
|
||
ididit = 1;
|
||
if (alldone) return;
|
||
delay -= temp;
|
||
} while (d.galaxy[quadx][quady] != 1000); // leave if quadrant supernovas
|
||
|
||
resting = 0;
|
||
Time = 0;
|
||
}
|
||
|
||
void nova(int ix, int iy) {
|
||
static double course[] =
|
||
{0.0, 10.5, 12.0, 1.5, 9.0, 0.0, 3.0, 7.5, 6.0, 4.5};
|
||
int bot, top, top2, burst, hits[11][3], kount, icx, icy, mm, nn, j;
|
||
int iquad, iquad1, i, ll, newcx, newcy, ii, jj;
|
||
if (Rand() < 0.05) {
|
||
/* Wow! We've supernova'ed */
|
||
snova(ix, iy);
|
||
return;
|
||
}
|
||
|
||
/* handle initial nova */
|
||
quad[ix][iy] = IHDOT;
|
||
crmena(1, IHSTAR, 2, ix, iy);
|
||
prout(" <20><><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>.");/*novas*/
|
||
d.galaxy[quadx][quady] -= 1;
|
||
d.starkl++;
|
||
|
||
/* Set up stack to recursively trigger adjacent stars */
|
||
bot = top = top2 = 1;
|
||
kount = 0;
|
||
icx = icy = 0;
|
||
hits[1][1] = ix;
|
||
hits[1][2] = iy;
|
||
while (1) {
|
||
for (mm = bot; mm <= top; mm++)
|
||
for (nn = 1; nn <= 3; nn++) /* nn,j represents coordinates around current */
|
||
for (j = 1; j <= 3; j++) {
|
||
if (j==2 && nn== 2) continue;
|
||
ii = hits[mm][1]+nn-2;
|
||
jj = hits[mm][2]+j-2;
|
||
if (ii < 1 || ii > 10 || jj < 1 || jj > 10) continue;
|
||
iquad = quad[ii][jj];
|
||
switch (iquad) {
|
||
// case IHDOT: /* Empty space ends reaction
|
||
// case IHQUEST:
|
||
// case IHBLANK:
|
||
// case IHT:
|
||
// case IHWEB:
|
||
default:
|
||
break;
|
||
case IHSTAR: /* Affect another star */
|
||
if (Rand() < 0.05) {
|
||
/* This star supernovas */
|
||
snova(ii,jj);
|
||
return;
|
||
}
|
||
top2++;
|
||
hits[top2][1]=ii;
|
||
hits[top2][2]=jj;
|
||
d.galaxy[quadx][quady] -= 1;
|
||
d.starkl++;
|
||
crmena(1, IHSTAR, 2, ii, jj);
|
||
prout(" <20><><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>.");/*novas*/
|
||
quad[ii][jj] = IHDOT;
|
||
break;
|
||
case IHP: /* Destroy planet */
|
||
d.newstuf[quadx][quady] -= 1;
|
||
d.nplankl++;
|
||
crmena(1, IHP, 2, ii, jj);
|
||
prout(" 㭨<>⮦<EFBFBD><E2AEA6><EFBFBD>.");/*destroyed*/
|
||
d.plnets[iplnet] = nulplanet;
|
||
iplnet = plnetx = plnety = 0;
|
||
if (landed == 1) {
|
||
finish(FPNOVA);
|
||
return;
|
||
}
|
||
quad[ii][jj] = IHDOT;
|
||
break;
|
||
case IHB: /* Destroy base */
|
||
d.galaxy[quadx][quady] -= 10;
|
||
for (i = 1; i <= d.rembase; i++)
|
||
if (d.baseqx[i]==quadx && d.baseqy[i]==quady) break;
|
||
d.baseqx[i] = d.baseqx[d.rembase];
|
||
d.baseqy[i] = d.baseqy[d.rembase];
|
||
d.rembase--;
|
||
basex = basey = 0;
|
||
d.basekl++;
|
||
newcnd();
|
||
crmena(1, IHB, 2, ii, jj);
|
||
prout(" 㭨<>⮦<EFBFBD><E2AEA6><EFBFBD>.");/*destroyed*/
|
||
quad[ii][jj] = IHDOT;
|
||
break;
|
||
case IHE: /* Buffet ship */
|
||
case IHF:
|
||
prout("***<2A><>ࠡ<EFBFBD><E0A0A1> <20><><EFBFBD><EFBFBD><EFBFBD>襭 <20><><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>.");/*Starship buffeted by nova*/
|
||
if (shldup) {
|
||
if (shield >= 2000.0) shield -= 2000.0;
|
||
else {
|
||
double diff = 2000.0 - shield;
|
||
energy -= diff;
|
||
shield = 0.0;
|
||
shldup = 0;
|
||
prout("***<2A><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD> <20><><EFBFBD>०<EFBFBD><E0A5A6><EFBFBD><EFBFBD>.");/*Shields knocked out*/
|
||
damage[DSHIELD] += 0.005*damfac*Rand()*diff;
|
||
}
|
||
}
|
||
else energy -= 2000.0;
|
||
if (energy <= 0) {
|
||
finish(FNOVA);
|
||
return;
|
||
}
|
||
/* add in course nova contributes to kicking starship*/
|
||
icx += sectx-hits[mm][1];
|
||
icy += secty-hits[mm][2];
|
||
kount++;
|
||
break;
|
||
case IHK: /* kill klingon */
|
||
deadkl(ii,jj,iquad, ii, jj);
|
||
break;
|
||
case IHC: /* Damage/destroy big enemies */
|
||
case IHS:
|
||
case IHR:
|
||
for (ll = 1; ll <= nenhere; ll++)
|
||
if (kx[ll]==ii && ky[ll]==jj) break;
|
||
kpower[ll] -= 800.0; /* If firepower is lost, die */
|
||
if (kpower[ll] <= 0.0) {
|
||
deadkl(ii, jj, iquad, ii, jj);
|
||
break;
|
||
}
|
||
newcx = ii + ii - hits[mm][1];
|
||
newcy = jj + jj - hits[mm][2];
|
||
crmena(1, iquad, 2, ii, jj);
|
||
proutn(" <20><><EFBFBD>०<EFBFBD><E0A5A6><EFBFBD><EFBFBD>");/*damaged*/
|
||
if (newcx<1 || newcx>10 || newcy<1 || newcy>10) {
|
||
/* can't leave quadrant */
|
||
skip(1);
|
||
break;
|
||
}
|
||
iquad1 = quad[newcx][newcy];
|
||
if (iquad1 == IHBLANK) {
|
||
proutn(", <20><><EFBFBD><EFBFBD><EFBFBD> <20> <20><>窥");/*blasted into*/
|
||
crmena(0, IHBLANK, 2, newcx, newcy);
|
||
skip(1);
|
||
deadkl(ii, jj, iquad, newcx, newcy);
|
||
break;
|
||
}
|
||
if (iquad1 != IHDOT) {
|
||
/* can't move into something else */
|
||
skip(1);
|
||
break;
|
||
}
|
||
proutn(", <20><><EFBFBD><EFBFBD><EFBFBD>襭 <20>");/*buffeted to*/
|
||
cramlc(2, newcx, newcy);
|
||
quad[ii][jj] = IHDOT;
|
||
quad[newcx][newcy] = iquad;
|
||
kx[ll] = newcx;
|
||
ky[ll] = newcy;
|
||
kavgd[ll] = sqrt(square(sectx-newcx)+square(secty-newcy));
|
||
kdist[ll] = kavgd[ll];
|
||
skip(1);
|
||
break;
|
||
}
|
||
}
|
||
if (top == top2) break;
|
||
bot = top + 1;
|
||
top = top2;
|
||
}
|
||
if (kount==0) return;
|
||
|
||
/* Starship affected by nova -- kick it away. */
|
||
dist = kount*0.1;
|
||
if (icx) icx = (icx < 0 ? -1 : 1);
|
||
if (icy) icy = (icy < 0 ? -1 : 1);
|
||
direc = course[3*(icx+1)+icy+2];
|
||
if (direc == 0.0) dist = 0.0;
|
||
if (dist == 0.0) return;
|
||
Time = 10.0*dist/16.0;
|
||
skip(1);
|
||
/* prout("Force of nova displaces starship."); */
|
||
prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><>६<EFBFBD><E0A5AC>⨫<EFBFBD> <20><>ࠡ<EFBFBD><E0A0A1>.");
|
||
iattak=2; /* Eliminates recursion problem */
|
||
lmove();
|
||
Time = 10.0*dist/16.0;
|
||
return;
|
||
}
|
||
|
||
|
||
void snova(int insx, int insy) {
|
||
int comdead, nqx, nqy, nsx, nsy, num, kldead, iscdead;
|
||
int nrmdead, npdead;
|
||
int insipient=0;
|
||
|
||
nsx = insx;
|
||
nsy = insy;
|
||
|
||
if (insy== 0) {
|
||
if (insx == 1) {
|
||
/* NOVAMAX being used */
|
||
nqx = probecx;
|
||
nqy = probecy;
|
||
}
|
||
else {
|
||
int stars = 0;
|
||
/* Scheduled supernova -- select star */
|
||
/* logic changed here so that we won't favor quadrants in top
|
||
left of universe */
|
||
for (nqx = 1; nqx<=8; nqx++) {
|
||
for (nqy = 1; nqy<=8; nqy++) {
|
||
stars += d.galaxy[nqx][nqy] % 10;
|
||
}
|
||
}
|
||
if (stars == 0) return; /* nothing to supernova exists */
|
||
num = Rand()*stars + 1;
|
||
for (nqx = 1; nqx<=8; nqx++) {
|
||
for (nqy = 1; nqy<=8; nqy++) {
|
||
num -= d.galaxy[nqx][nqy] % 10;
|
||
if (num <= 0) break;
|
||
}
|
||
if (num <=0) break;
|
||
}
|
||
#ifdef DEBUG
|
||
if (idebug) {
|
||
proutn("Super nova here?");
|
||
if (ja()==1) {
|
||
nqx = quadx;
|
||
nqy = quady;
|
||
}
|
||
}
|
||
#endif
|
||
}
|
||
|
||
if (nqx != quady || nqy != quady || justin != 0) {
|
||
/* it isn't here, or we just entered (treat as inroute) */
|
||
if (REPORTS) {
|
||
skip(1);
|
||
/* proutn("Message from Starfleet Command Stardate "); */
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD><EFBFBD>饭<EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD> ");
|
||
cramf(d.date, 0, 1);
|
||
skip(1);
|
||
proutn(" <20><><EFBFBD>୮<EFBFBD><E0ADAE><EFBFBD> <20> <20><>窥");/*Supernova in*/
|
||
cramlc(1, nqx, nqy);
|
||
prout("; <20><><EFBFBD><EFBFBD><EFBFBD><E0AEA6>.");/*caution advised*/
|
||
}
|
||
}
|
||
else {
|
||
/* we are in the quadrant! */
|
||
insipient = 1;
|
||
num = Rand()* (d.galaxy[nqx][nqy]%10) + 1;
|
||
for (nsx=1; nsx < 10; nsx++) {
|
||
for (nsy=1; nsy < 10; nsy++) {
|
||
if (quad[nsx][nsy]==IHSTAR) {
|
||
num--;
|
||
if (num==0) break;
|
||
}
|
||
}
|
||
if (num==0) break;
|
||
}
|
||
}
|
||
}
|
||
else {
|
||
insipient = 1;
|
||
}
|
||
|
||
if (insipient) {
|
||
skip(1);
|
||
/* prouts("***RED ALERT! RED ALERT!"); */
|
||
prouts("***<2A><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>! <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>!");
|
||
skip(1);
|
||
/* proutn("***Incipient supernova detected at"); */
|
||
proutn("***<2A><><EFBFBD><EFBFBD><EFBFBD> ᢥ<>孮<EFBFBD><E5ADAE><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>㦥<EFBFBD> <20>");
|
||
cramlc(2, nsx, nsy);
|
||
skip(1);
|
||
nqx = quadx;
|
||
nqy = quady;
|
||
if (square(nsx-sectx) + square(nsy-secty) <= 2.1) {
|
||
/* proutn("Emergency override attempts t"); */
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD><EFBFBD>⪠ <20><><EFBFBD><EFBFBD>७<EFBFBD><E0A5AD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>墠<EFBFBD><E5A2A0> <20><>ࠢ<EFBFBD><E0A0A2><EFBFBD><EFBFBD><EFBFBD>");
|
||
prouts("***************");
|
||
skip(1);
|
||
stars();
|
||
alldone=1;
|
||
}
|
||
}
|
||
/* destroy any Klingons in supernovaed quadrant */
|
||
num=d.galaxy[nqx][nqy];
|
||
kldead = num/100;
|
||
d.remkl -= kldead; // Moved here to correctly set remaining Klingon count
|
||
comdead = iscdead = 0;
|
||
if (nqx==d.isx && nqy == d.isy) {
|
||
/* did in the Supercommander! */
|
||
d.nscrem = d.isx = d.isy = isatb = iscate = 0;
|
||
iscdead = 1;
|
||
kldead--; /* Get proper kill credit */
|
||
future[FSCMOVE] = future[FSCDBAS] = 1e30;
|
||
}
|
||
|
||
if (d.remcom) {
|
||
int maxloop = d.remcom, l;
|
||
for (l = 1; l <= maxloop; l++) {
|
||
if (d.cx[l] == nqx && d.cy[l] == nqy) {
|
||
d.cx[l] = d.cx[d.remcom];
|
||
d.cy[l] = d.cy[d.remcom];
|
||
d.cx[d.remcom] = d.cy[d.remcom] = 0;
|
||
d.remcom--;
|
||
kldead--;
|
||
comdead++;
|
||
if (d.remcom==0) future[FTBEAM] = 1e30;
|
||
break;
|
||
}
|
||
}
|
||
}
|
||
/* destroy Romulans and planets in supernovaed quadrant */
|
||
num = d.newstuf[nqx][nqy];
|
||
d.newstuf[nqx][nqy] = 0;
|
||
nrmdead = num/10;
|
||
d.nromrem -= nrmdead;
|
||
npdead = num - nrmdead*10;
|
||
if (npdead) {
|
||
int l;
|
||
for (l = 1; l <= inplan; l++)
|
||
if (d.plnets[l].x == nqx && d.plnets[l].y == nqy) {
|
||
d.plnets[l] = nulplanet;
|
||
}
|
||
}
|
||
/* Destroy any base in supernovaed quadrant */
|
||
if (d.rembase) {
|
||
int maxloop = d.rembase, l;
|
||
for (l = 1; l <= maxloop; l++)
|
||
if (d.baseqx[l]==nqx && d.baseqy[l]==nqy) {
|
||
d.baseqx[l] = d.baseqx[d.rembase];
|
||
d.baseqy[l] = d.baseqy[d.rembase];
|
||
d.baseqx[d.rembase] = d.baseqy[d.rembase] = 0;
|
||
d.rembase--;
|
||
break;
|
||
}
|
||
}
|
||
/* If starship caused supernova, tally up destruction */
|
||
if (insx) {
|
||
num = d.galaxy[nqx][nqy] % 100;
|
||
d.starkl += num % 10;
|
||
d.basekl += num/10;
|
||
d.killk += kldead;
|
||
d.killc += comdead;
|
||
d.nromkl += nrmdead;
|
||
d.nplankl += npdead;
|
||
d.nsckill += iscdead;
|
||
}
|
||
/* mark supernova in galaxy and in star chart */
|
||
if ((quadx == nqx && quady == nqy) || REPORTS)
|
||
starch[nqx][nqy] = 1;
|
||
d.galaxy[nqx][nqy] = 1000;
|
||
/* If supernova destroys last klingons give special message */
|
||
if (d.remkl==0 && (nqx != quadx || nqy != quady)) {
|
||
skip(2);
|
||
if (insx == 0) prout("<EFBFBD><EFBFBD><EFBFBD><EFBFBD>⫨<EFBFBD>稪<EFBFBD>!");/*Lucky you*/
|
||
proutn("<EFBFBD><EFBFBD><EFBFBD>୮<EFBFBD><EFBFBD><EFBFBD> <20> <20><>窥");/*A supernova in*/
|
||
cramlc(1, nqx, nqy);
|
||
/* prout(" has just destroyed the last Klingons."); */
|
||
prout(" ⮫쪮 <20><><EFBFBD> 㭨<>⮦<EFBFBD><E2AEA6><EFBFBD> <20><><EFBFBD><E1ABA5><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>.");
|
||
finish(FWON);
|
||
return;
|
||
}
|
||
/* if some Klingons remain, continue or die in supernova */
|
||
if (alldone) finish(FSNOVAED);
|
||
return;
|
||
}
|
||
|
||
|