1: /* 2: * Copyright (c) 1980 Regents of the University of California. 3: * All rights reserved. The Berkeley software License Agreement 4: * specifies the terms and conditions for redistribution. 5: */ 6: 7: #ifndef lint 8: static char sccsid[] = "@(#)computer.c 4.3 (Berkeley) 1/29/86"; 9: #endif not lint 10: 11: # include "trek.h" 12: # include "getpar.h" 13: # include <stdio.h> 14: /* 15: ** On-Board Computer 16: ** 17: ** A computer request is fetched from the captain. The requests 18: ** are: 19: ** 20: ** chart -- print a star chart of the known galaxy. This includes 21: ** every quadrant that has ever had a long range or 22: ** a short range scan done of it, plus the location of 23: ** all starbases. This is of course updated by any sub- 24: ** space radio broadcasts (unless the radio is out). 25: ** The format is the same as that of a long range scan 26: ** except that ".1." indicates that a starbase exists 27: ** but we know nothing else. 28: ** 29: ** trajectory -- gives the course and distance to every know 30: ** Klingon in the quadrant. Obviously this fails if the 31: ** short range scanners are out. 32: ** 33: ** course -- gives a course computation from whereever you are 34: ** to any specified location. If the course begins 35: ** with a slash, the current quadrant is taken. 36: ** Otherwise the input is quadrant and sector coordi- 37: ** nates of the target sector. 38: ** 39: ** move -- identical to course, except that the move is performed. 40: ** 41: ** score -- prints out the current score. 42: ** 43: ** pheff -- "PHaser EFFectiveness" at a given distance. Tells 44: ** you how much stuff you need to make it work. 45: ** 46: ** warpcost -- Gives you the cost in time and units to move for 47: ** a given distance under a given warp speed. 48: ** 49: ** impcost -- Same for the impulse engines. 50: ** 51: ** distresslist -- Gives a list of the currently known starsystems 52: ** or starbases which are distressed, together with their 53: ** quadrant coordinates. 54: ** 55: ** If a command is terminated with a semicolon, you remain in 56: ** the computer; otherwise, you escape immediately to the main 57: ** command processor. 58: */ 59: 60: struct cvntab Cputab[] = 61: { 62: "ch", "art", (int (*)())1, 0, 63: "t", "rajectory", (int (*)())2, 0, 64: "c", "ourse", (int (*)())3, 0, 65: "m", "ove", (int (*)())3, 1, 66: "s", "core", (int (*)())4, 0, 67: "p", "heff", (int (*)())5, 0, 68: "w", "arpcost", (int (*)())6, 0, 69: "i", "mpcost", (int (*)())7, 0, 70: "d", "istresslist", (int (*)())8, 0, 71: 0 72: }; 73: 74: computer() 75: { 76: int ix, iy; 77: register int i, j; 78: int numout; 79: int tqx, tqy; 80: struct cvntab *r; 81: int cost; 82: int course; 83: double dist, time; 84: double warpfact; 85: struct quad *q; 86: register struct event *e; 87: 88: if (check_out(COMPUTER)) 89: return; 90: while (1) 91: { 92: r = getcodpar("\nRequest", Cputab); 93: switch (r->value) 94: { 95: 96: case 1: /* star chart */ 97: printf("Computer record of galaxy for all long range sensor scans\n\n"); 98: printf(" "); 99: /* print top header */ 100: for (i = 0; i < NQUADS; i++) 101: printf("-%d- ", i); 102: printf("\n"); 103: for (i = 0; i < NQUADS; i++) 104: { 105: printf("%d ", i); 106: for (j = 0; j < NQUADS; j++) 107: { 108: if (i == Ship.quadx && j == Ship.quady) 109: { 110: printf("$$$ "); 111: continue; 112: } 113: q = &Quad[i][j]; 114: /* 1000 or 1001 is special case */ 115: if (q->scanned >= 1000) 116: if (q->scanned > 1000) 117: printf(".1. "); 118: else 119: printf("/// "); 120: else 121: if (q->scanned < 0) 122: printf("... "); 123: else 124: printf("%3d ", q->scanned); 125: } 126: printf("%d\n", i); 127: } 128: printf(" "); 129: /* print bottom footer */ 130: for (i = 0; i < NQUADS; i++) 131: printf("-%d- ", i); 132: printf("\n"); 133: break; 134: 135: case 2: /* trajectory */ 136: if (check_out(SRSCAN)) 137: { 138: break; 139: } 140: if (Etc.nkling <= 0) 141: { 142: printf("No Klingons in this quadrant\n"); 143: break; 144: } 145: /* for each Klingon, give the course & distance */ 146: for (i = 0; i < Etc.nkling; i++) 147: { 148: printf("Klingon at %d,%d", Etc.klingon[i].x, Etc.klingon[i].y); 149: course = kalc(Ship.quadx, Ship.quady, Etc.klingon[i].x, Etc.klingon[i].y, &dist); 150: prkalc(course, dist); 151: } 152: break; 153: 154: case 3: /* course calculation */ 155: if (readdelim('/')) 156: { 157: tqx = Ship.quadx; 158: tqy = Ship.quady; 159: } 160: else 161: { 162: ix = getintpar("Quadrant"); 163: if (ix < 0 || ix >= NSECTS) 164: break; 165: iy = getintpar("q-y"); 166: if (iy < 0 || iy >= NSECTS) 167: break; 168: tqx = ix; 169: tqy = iy; 170: } 171: ix = getintpar("Sector"); 172: if (ix < 0 || ix >= NSECTS) 173: break; 174: iy = getintpar("s-y"); 175: if (iy < 0 || iy >= NSECTS) 176: break; 177: course = kalc(tqx, tqy, ix, iy, &dist); 178: if (r->value2) 179: { 180: warp(-1, course, dist); 181: break; 182: } 183: printf("%d,%d/%d,%d to %d,%d/%d,%d", 184: Ship.quadx, Ship.quady, Ship.sectx, Ship.secty, tqx, tqy, ix, iy); 185: prkalc(course, dist); 186: break; 187: 188: case 4: /* score */ 189: score(); 190: break; 191: 192: case 5: /* phaser effectiveness */ 193: dist = getfltpar("range"); 194: if (dist < 0.0) 195: break; 196: dist *= 10.0; 197: cost = pow(0.90, dist) * 98.0 + 0.5; 198: printf("Phasers are %d%% effective at that range\n", cost); 199: break; 200: 201: case 6: /* warp cost (time/energy) */ 202: dist = getfltpar("distance"); 203: if (dist < 0.0) 204: break; 205: warpfact = getfltpar("warp factor"); 206: if (warpfact <= 0.0) 207: warpfact = Ship.warp; 208: cost = (dist + 0.05) * warpfact * warpfact * warpfact; 209: time = Param.warptime * dist / (warpfact * warpfact); 210: printf("Warp %.2f distance %.2f cost %.2f stardates %d (%d w/ shlds up) units\n", 211: warpfact, dist, time, cost, cost + cost); 212: break; 213: 214: case 7: /* impulse cost */ 215: dist = getfltpar("distance"); 216: if (dist < 0.0) 217: break; 218: cost = 20 + 100 * dist; 219: time = dist / 0.095; 220: printf("Distance %.2f cost %.2f stardates %d units\n", 221: dist, time, cost); 222: break; 223: 224: case 8: /* distresslist */ 225: j = 1; 226: printf("\n"); 227: /* scan the event list */ 228: for (i = 0; i < MAXEVENTS; i++) 229: { 230: e = &Event[i]; 231: /* ignore hidden entries */ 232: if (e->evcode & E_HIDDEN) 233: continue; 234: switch (e->evcode & E_EVENT) 235: { 236: 237: case E_KDESB: 238: printf("Klingon is attacking starbase in quadrant %d,%d\n", 239: e->x, e->y); 240: j = 0; 241: break; 242: 243: case E_ENSLV: 244: case E_REPRO: 245: printf("Starsystem %s in quadrant %d,%d is distressed\n", 246: systemname(e), e->x, e->y); 247: j = 0; 248: break; 249: } 250: } 251: if (j) 252: printf("No known distress calls are active\n"); 253: break; 254: 255: } 256: 257: /* skip to next semicolon or newline. Semicolon 258: * means get new computer request; newline means 259: * exit computer mode. */ 260: while ((i = cgetc(0)) != ';') 261: { 262: if (i == '\0') 263: exit(1); 264: if (i == '\n') 265: { 266: ungetc(i, stdin); 267: return; 268: } 269: } 270: } 271: } 272: 273: 274: /* 275: ** Course Calculation 276: ** 277: ** Computes and outputs the course and distance from position 278: ** sqx,sqy/ssx,ssy to tqx,tqy/tsx,tsy. 279: */ 280: 281: kalc(tqx, tqy, tsx, tsy, dist) 282: int tqx; 283: int tqy; 284: int tsx; 285: int tsy; 286: double *dist; 287: { 288: double dx, dy; 289: double quadsize; 290: double angle; 291: register int course; 292: 293: /* normalize to quadrant distances */ 294: quadsize = NSECTS; 295: dx = (Ship.quadx + Ship.sectx / quadsize) - (tqx + tsx / quadsize); 296: dy = (tqy + tsy / quadsize) - (Ship.quady + Ship.secty / quadsize); 297: 298: /* get the angle */ 299: angle = atan2(dy, dx); 300: /* make it 0 -> 2 pi */ 301: if (angle < 0.0) 302: angle += 6.283185307; 303: /* convert from radians to degrees */ 304: course = angle * 57.29577951 + 0.5; 305: dx = dx * dx + dy * dy; 306: *dist = sqrt(dx); 307: return (course); 308: } 309: 310: 311: prkalc(course, dist) 312: int course; 313: double dist; 314: { 315: printf(": course %d dist %.3f\n", course, dist); 316: }