# include "trek.h" /** ** phaser control **/ CVNTAB Matab[] { "a", "utomatic", "m", "anual", 0 }; phaser() { register int i, k; int manual, flag, units, extra; int hit, reqd, n; double tot; int hits[MAXKLQUAD], hitreqd[MAXKLQUAD]; double dustfac, tothe; if (Status.cond == DOCKED) { printf("Phasers cannot fire through starbase shields.\n"); return; } if (Damage[PHASER]) { printf("Phaser control damaged.\n"); return; } if (Status.shldup) { printf("Scotty: we will have to divert power from the shields.\n"); if(!getynpar("Is that wise")) return; Move.shldchg = 1; } if (Status.cloaked) { printf("Sulu: Captain, you know that we cannot fire while cloaked.\n"); return; } manual = 0; if (Damage[COMPUTER]) if(lineended()) { printf("Computer damaged, manual mode selected\n"); manual = 1; } if (!manual) { if((manual=(getcodpar("Manual or automatic", Matab))) < 0) return; } if (!manual && Damage[COMPUTER]) { printf("Computer damaged, manual selected\n"); newline(); manual = 1; } /* set up hits[] with amount for each klingon */ flag = 1; n = Nkling; if (manual) { while (flag) { printf("%d units available\n", Status.energy); extra = 0; for (i = 0; i < n; i++) { printf("Klingon at %d,%d:", Kling[i].x, Kling[i].y); if(getintpar(" units to fire", &units)==0 || units < 0) return; hits[i] = units; extra =+ units; if (extra > Status.energy) { printf("Available energy exceeded. "); newline(); break; } } flag = i < n; if (extra <= 0) return; } Status.energy =- extra; extra = 0; } else { /* automatic distribution of power */ printf("Phasers locked on target. "); while (flag) { printf("%d units available\n", Status.energy); if(getintpar("Units to fire", &units)==0 || units < 0) return; if (units > Status.energy) { printf("Available energy exceeded. "); newline(); continue; } flag = 0; Status.energy =- units; extra = units; if (Nkling != 0) { tot = Nkling * (Nkling + 1) / 2; for (i = 0; i < Nkling; i++) { hits[i] = ((Nkling - i) / tot) * extra; extra =- hits[i]; dustfac = 0.90; tothe = Kling[i].dist; hitreqd[i] = Kling[i].power / pow(dustfac, tothe) + 0.5; if (hits[i] > hitreqd[i]) { extra =+ hits[i] - hitreqd[i]; hits[i] = hitreqd[i]; } } if (extra != 0) { for (i = 0; i < Nkling; i++) { reqd = hitreqd[i] - hits[i]; if (reqd <= 0) continue; if (reqd >= extra) { hits[i] =+ extra; extra = 0; break; } hits[i] = hitreqd[i]; extra =- reqd; } } } } } /* actually fire the shots */ Move.free = 0; k = 0; for (i = 0; i < n; i++) { if (hits[i] == 0) { k =+ 1; continue; } dustfac = 0.90 + 0.01 * franf(); tothe = Kling[k].dist; hit = hits[i] * pow(dustfac, tothe) + 0.5; Kling[k].power =- hit; printf("%d unit hit\t", hit); if (Kling[k].power <= 0) { extra =- Kling[k].power; killk(Kling[k].x, Kling[k].y); } else { printf("on Klingon at %d,%d\n", Kling[k].x, Kling[k].y); k =+ 1; } } if (extra > 0) printf("%d units expended on empty space\n", extra); }