1: /*
   2:  * func0.c	Phantasia support routines
   3:  */
   4: 
   5: #include "phant.h"
   6: 
   7: void    treasure(stat,treastyp,size)        /* select a treasure */
   8: reg struct  stats   *stat;
   9: short   treastyp;
  10: reg int size;
  11: {
  12: reg int which;
  13: int ch;
  14: double  temp, temp2;
  15: char    aline[35];
  16: FILE    *fp;
  17: 
  18:     which = roll(1,3);
  19:     move(3,0);
  20:     clrtobot();
  21:     move(5,0);
  22:     if (rnd() > 0.65)   /* gold and gems */
  23:         if (treastyp > 7)   /* gems */
  24:             {
  25:             temp = roll(1,(treastyp - 7)*(treastyp - 7)*(size - 1)/4);
  26:             printw("You have discovered %.0f gems!  Will you pick them up ? ",temp);
  27:             ch = rgetch();
  28:             addch('\n');
  29:             if (toupper(ch) == 'Y')
  30:                 if (rnd() < treastyp/40 + 0.05) /* cursed */
  31:                     {
  32:                     addstr("They were cursed!\n");
  33:                     goto CURSE;
  34:                     }
  35:                 else
  36:                     stat->gem += temp;
  37:             return;
  38:             }
  39:         else    /* gold */
  40:             {
  41:             temp = roll(treastyp*10,treastyp*treastyp*10*(size - 1));
  42:             printw("You have found %.0f gold pieces.  Do you want to pick them up ? ",temp);
  43:             ch = rgetch();
  44:             addch('\n');
  45:             if (toupper(ch) == 'Y')
  46:                 if (rnd() < treastyp/35 + 0.04) /* cursed */
  47:                     {
  48:                     addstr("They were cursed!\n");
  49:                     goto CURSE;
  50:                     }
  51:                 else
  52:                     {
  53:                     stat->gld += floor(0.9 * temp);
  54:                     fp = fopen(goldfile,"r");
  55:                     fread((char *) &temp2,sizeof(double),1,fp);
  56:                     fclose(fp);
  57:                     fp = fopen(goldfile,"w");
  58:                     temp2 += floor(temp/10);
  59:                     fwrite((char *) &temp2,sizeof(double),1,fp);
  60:                     fclose(fp);
  61:                     }
  62:             return;
  63:             }
  64:     else    /* other treasures */
  65:         {
  66:         addstr("You have found some treasure.  Do you want to inspect it ? ");
  67:         ch = rgetch();
  68:         addch('\n');
  69:         if (toupper(ch) != 'Y')
  70:             return;
  71:         else
  72:             if (rnd() < 0.08 && treastyp != 4)
  73:                 {
  74:                 addstr("It was cursed!\n");
  75:                 goto CURSE;
  76:                 }
  77:             else
  78:                 switch(treastyp)
  79:                     {
  80:                     case 1:
  81:                         switch(which)
  82:                             {
  83:                             case 1:
  84:                                 addstr("You've discovered a power booster!\n");
  85:                                 stat->man += roll(size*4,size*30);
  86:                                 break;
  87:                             case 2:
  88:                                 addstr("You have encountered a druid.\n");
  89:                                 stat->exp += roll(0,2000 + size*400);
  90:                                 break;
  91:                             case 3:
  92:                                 addstr("You have found a holy orb.\n");
  93:                                 stat->sin = max(0,stat->sin - 0.25);
  94:                                 break;
  95:                             }
  96:                         break;
  97:                     case 2:
  98:                         switch (which)
  99:                             {
 100:                             case 1:
 101:                                 addstr("You have found an amulet.\n");
 102:                                 ++stat->amu;
 103:                                 break;
 104:                             case 2:
 105:                                 addstr("You've found some holy water!\n");
 106:                                 ++stat->hw;
 107:                                 break;
 108:                             case 3:
 109:                                 addstr("You've met a hermit!\n");
 110:                                 stat->sin *= 0.75;
 111:                                 stat->man += 12*size;
 112:                                 break;
 113:                             }
 114:                         break;
 115:                     case 3:
 116:                         switch (which)
 117:                             {
 118:                             case 1:
 119:                                 temp = roll(7,30 + size/10);
 120:                                 printw("You've found a +%.0f shield!\n",temp);
 121:                                 if (temp >= stat->shd)
 122:                                     stat->shd = temp;
 123:                                 else
 124:                                     somebetter();
 125:                                 break;
 126:                             case 2:
 127:                                 addstr("You have rescued a virgin.  Will you be honorable ? ");
 128:                                 ch = rgetch();
 129:                                 if (toupper(ch) == 'Y')
 130:                                     stat->vrg = TRUE;
 131:                                 else
 132:                                     {
 133:                                     stat->exp += 2000*size;
 134:                                     ++stat->sin;
 135:                                     }
 136:                                 break;
 137:                             case 3:
 138:                                 addstr("You've discovered some athelas!\n");
 139:                                 --stat->psn;
 140:                                 break;
 141:                             }
 142:                         break;
 143:                     case 4:
 144:                         addstr("You've found a scroll.  Will you read it ? ");
 145:                         ch = rgetch();
 146:                         addch('\n');
 147:                         if (toupper(ch) == 'Y')
 148:                             switch ((int) roll(1,6))
 149:                                 {
 150:                                 case 1:
 151:                                     addstr("It throws up a shield for you next monster.\n");
 152:                                     paws(8);
 153:                                     longjmp(fightenv,2);
 154:                                     /*NOTREACHED*/
 155:                                 case 2:
 156:                                     addstr("It makes you invisible for you next monster.\n");
 157:                                     paws(8);
 158:                                     speed = 1e6;
 159:                                     longjmp(fightenv,0);
 160:                                     /*NOTREACHED*/
 161:                                 case 3:
 162:                                     addstr("It increases your strength ten fold to fight your next monster.\n");
 163:                                     paws(8);
 164:                                     strength *= 10;
 165:                                     longjmp(fightenv,0);
 166:                                     /*NOTREACHED*/
 167:                                 case 4:
 168:                                     addstr("It is a general knowledge scroll.\n");
 169:                                     stat->brn += roll(2,size);
 170:                                     stat->mag += roll(1,size/2);
 171:                                     break;
 172:                             case 5:
 173:                                 addstr("It tells you how to pick your next monster.\n");
 174:                                 addstr("Which monster do you want [0-99] ? ");
 175:                                 which = inflt();
 176:                                 which = min(99,max(0,which));
 177:                                 fight(stat,which);
 178:                                 break;
 179:                             case 6:
 180:                                 addstr("It was cursed!\n");
 181:                                 goto CURSE;
 182:                             }
 183:                         break;
 184:                     case 5:
 185:                         switch (which)
 186:                             {
 187:                             case 1:
 188:                                 temp = roll(size/4+5,size/2 + 9);
 189:                                 printw("You've discovered a +%.0f dagger.\n",temp);
 190:                                 if (temp >= stat->swd)
 191:                                     stat->swd = temp;
 192:                                 else
 193:                                     somebetter();
 194:                                 break;
 195:                             case 2:
 196:                                 temp = roll(7.5 + size*3,size * 2 + 160);
 197:                                 printw("You have found some +%.0f armour!\n",temp);
 198:                                 if (temp >= stat->shd)
 199:                                     stat->shd = temp;
 200:                                 else
 201:                                     somebetter();
 202:                                 break;
 203:                             case 3:
 204:                                 addstr("You've found a tablet.\n");
 205:                                 stat->brn += 4.5*size;
 206:                                 break;
 207:                             }
 208:                         break;
 209:                     case 6:
 210:                         switch (which)
 211:                             {
 212:                             case 1:
 213:                                 addstr("You've found a priest.\n");
 214:                                 stat->nrg = stat->mxn + stat->shd;
 215:                                 stat->sin /= 2;
 216:                                 stat->man += 24*size;
 217:                                 stat->brn += size;
 218:                                 break;
 219:                             case 2:
 220:                                 addstr("You have come upon Robin Hood!\n");
 221:                                 stat->shd += size*2;
 222:                                 stat->str += size/2.5 + 1;
 223:                                 break;
 224:                             case 3:
 225:                                     temp = roll(2 + size/4,size/1.2 + 10);
 226:                                 printw("You have found a +%.0f axe!\n",temp);
 227:                                 if (temp >= stat->swd)
 228:                                     stat->swd = temp;
 229:                                 else
 230:                                     somebetter();
 231:                                 break;
 232:                             }
 233:                         break;
 234:                     case 7:
 235:                         switch (which)
 236:                             {
 237:                             case 1:
 238:                                 addstr("You've discovered a charm!\n");
 239:                                 ++stat->chm;
 240:                                 break;
 241:                             case 2:
 242:                                 addstr("You have encountered Merlyn!\n");
 243:                                 stat->brn += size + 5;
 244:                                 stat->mag += size/3 + 5;
 245:                                 stat->man += size*10;
 246:                                 break;
 247:                             case 3:
 248:                                 temp = roll(5+size/3,size/1.5 + 20);
 249:                                 printw("You have found a +%.0f war hammer!\n",temp);
 250:                                 if (temp >= stat->swd)
 251:                                     stat->swd = temp;
 252:                                 else
 253:                                     somebetter();
 254:                                 break;
 255:                             }
 256:                         break;
 257:                     case 8:
 258:                         switch (which)
 259:                             {
 260:                             case 1:
 261:                                 addstr("You have found a healing potion.\n");
 262:                                 stat->psn = min(-2,stat->psn-2);
 263:                                 break;
 264:                             case 2:
 265:                                 addstr("You have discovered a transporter.  Do you wish to go anywhere ? ");
 266:                                 ch = rgetch();
 267:                                 addch('\n');
 268:                                 if (toupper(ch) == 'Y')
 269:                                     {
 270:                                     addstr("X Y Coordinates ? ");
 271:                                     getstring(aline,80);
 272:                                     sscanf(aline,"%F %F",&stat->x,&stat->y);
 273:                                     stat->x = floor(stat->x);
 274:                                     stat->y = floor(stat->y);
 275:                                     }
 276:                                 break;
 277:                             case 3:
 278:                                 temp = roll(10 + size/1.2,size*3 + 30);
 279:                                 printw("You've found a +%.0f sword!\n",temp);
 280:                                 if (temp >= stat->swd)
 281:                                     stat->swd = temp;
 282:                                 else
 283:                                     somebetter();
 284:                                 break;
 285:                             }
 286:                         break;
 287:                     case 10:
 288:                     case 11:
 289:                     case 12:
 290:                     case 13:
 291:                         if (rnd() < 0.33)
 292:                             {
 293:                             if (treastyp == 10)
 294:                                 {
 295:                                 addstr("You've found a pair of elven boots!\n");
 296:                                 stat->quk += 2;
 297:                                 break;
 298:                                 }
 299:                             else if (treastyp == 11 && !stat->pal)
 300:                                 {
 301:                                 addstr("You've acquired Saruman's palantir.\n");
 302:                                 stat->pal = TRUE;
 303:                                 break;
 304:                                 }
 305:                             else if (!stat->rng.type && stat->typ < 20 && (treastyp == 12 || treastyp == 13))
 306:                                 {
 307:                                 if (treastyp == 12)
 308:                                     if (rnd() < 0.8)
 309:                                         {
 310:                                         which = NAZREG;
 311:                                         temp = 15;
 312:                                         }
 313:                                     else
 314:                                         {
 315:                                         which = NAZBAD;
 316:                                         temp = 10 + rngcalc(stat->typ) + roll(0,5);
 317:                                         }
 318:                                 else
 319:                                     if (rnd() > 0.9)
 320:                                         {
 321:                                         which = DLREG;
 322:                                         temp = 0;
 323:                                         }
 324:                                     else
 325:                                         {
 326:                                         which = DLBAD;
 327:                                         temp = 15 + rngcalc(stat->typ) + roll(0,5);
 328:                                         }
 329:                                     addstr("You've discovered a ring.  Will you pick it up ? ");
 330:                                     ch = rgetch();
 331:                                     addch('\n');
 332:                                     if (toupper(ch) == 'Y')
 333:                                         {
 334:                                         stat->rng.type = which;
 335:                                         stat->rng.duration = temp;
 336:                                         }
 337:                                 }
 338:                             break;
 339:                             }
 340:                         case 9:
 341:                             switch (which)
 342:                                 {
 343:                                 case 1:
 344:                                     if (!(stat->lvl > 1000 || stat->crn > floor((double) stat->lvl/100)
 345:                                             || stat->lvl < 10))
 346:                                         {
 347:                                         addstr("You have found a golden crown!\n");
 348:                                         ++stat->crn;
 349:                                         break;
 350:                                         }
 351:                                 case 2:
 352:                                     addstr("You've been blessed!\n");
 353:                                     stat->bls = TRUE;
 354:                                     stat->sin /=3;
 355:                                     stat->nrg = stat->mxn + stat->shd;
 356:                                     stat->man += 100*size;
 357:                                     break;
 358:                                 case 3:
 359:                                     temp = roll(1,size/5+5);
 360:                                     temp = min(temp,99);
 361:                                     printw("You have discovered some +%.0f quicksilver!\n",temp);
 362:                                     if (temp >= stat->quks)
 363:                                         stat->quks = temp;
 364:                                     else
 365:                                         somebetter();
 366:                                     break;
 367:                                 }
 368:                             break;
 369:                         }
 370:         refresh();
 371:         return;
 372:         }
 373: CURSE:  if (stat->chm)
 374:         {
 375:         addstr("But your charm saved you!\n");
 376:         --stat->chm;
 377:         }
 378:     else if (stat->amu)
 379:         {
 380:         addstr("But your amulet saved you!\n");
 381:         --stat->amu;
 382:         }
 383:     else
 384:         {
 385:         stat->nrg = (stat->mxn + stat->shd)/10;
 386:         stat->psn += 0.25;
 387:         }
 388: }
 389: 
 390: void    callmonster(which,size,mons)        /* fill a structure with monster 'which' of size 'size' */
 391: reg int which, size;
 392: reg struct  mstats  *mons;
 393: {
 394: FILE    *fp;
 395: char    instr[100];
 396: 
 397:     which = min(which,99);
 398:     fp = fopen(monsterfile,"r");
 399:     for (++which; which; --which)
 400:         fgets(instr,100,fp);
 401:     strncpy(mons->name,instr,24);
 402:     mons->name[24] = '\0';
 403:     sscanf(instr + 24,"%F%F%F%F%F%d%d%d",&mons->str,&mons->brn,&mons->spd,&mons->hit,
 404:         &mons->exp,&mons->trs,&mons->typ,&mons->flk);
 405:     if (mons->typ == 2) /* Modnar */
 406:         {
 407:         mons->str *= rnd() + 0.5;
 408:         mons->brn *= rnd() + 0.5;
 409:         mons->spd *= rnd() + 0.5;
 410:         mons->hit *= rnd() + 0.5;
 411:         mons->exp *= rnd() + 0.5;
 412:         mons->trs *= rnd();
 413:         }
 414:     else if (mons->typ == 3)    /* mimic */
 415:         {
 416:         fseek(fp,0L,0);
 417:         for (which = roll(0,100); which; --which)
 418:             fgets(instr,100,fp);
 419:         strncpy(mons->name,instr,24);
 420:         }
 421:     trunc(mons->name);
 422:     mons->str += (size-1)*mons->str/2;
 423:     mons->brn *= size;
 424:     mons->spd += size * 1.e-9;
 425:     mons->hit *= size;
 426:     mons->exp *= size;
 427:     fclose(fp);
 428: }
 429: 
 430: struct  /* lookup table for rolling stats and making increases upon gaining levels */
 431:     {
 432:     struct
 433:         {
 434:         int base;
 435:         int interval;
 436:         float   increase;
 437:         } quick,      strength,      manna,     energy,    brains,    magic;
 438:     } table[7] =
 439:         {
 440: /* mag. usr: */ 30, 6, 0.0,   20, 6, 2.0,    50,51,75.0,    30,16,20.0,    60,26, 6.0,    5, 5,2.75,
 441: /* fighter:  */ 30, 6, 0.0,   40,16, 3.0,    30,21,40.0,    45,26,30.0,    25,21, 3.0,    3, 4, 1.5,
 442: /* elf:      */ 32, 7, 0.0,   35,11, 2.5,    45,46,65.0,    30,21,25.0,    40,26, 4.0,    4, 4, 2.0,
 443: /* dwarf:    */ 25, 6, 0.0,   45,21, 5.0,    25,21,30.0,    60,41,35.0,    20,21, 2.5,    2, 4, 1.0,
 444: /* halfling: */ 34, 0, 0.0,   20, 6, 2.0,    25,21,30.0,    55,36,30.0,    40,36, 4.5,    1, 4, 1.0,
 445: /* exprmnto: */ 27, 0, 0.0,   25, 0, 0.0,    100,0, 0.0,    35, 0, 0.0,    25, 0, 0.0,    2, 0, 0.0,
 446: /* super:    */ 38, 0, 0.0,   65, 0, 0.0,    100,0, 0.0,    80, 0, 0.0,    85, 0, 0.0,    9, 0, 0.0
 447:         };
 448: 
 449: void    genchar(res,type)               /* init a charac struct */
 450: int type;
 451: reg struct  stats   *res;
 452: {
 453: register int    subscript;
 454: 
 455:     if (type < '1' || type > '6')
 456:         if (type != '7' || !su)
 457:             type = '2'; /* fighter is default */
 458:     subscript = type - '1';
 459:     res->quk = roll(table[subscript].quick.base,table[subscript].quick.interval);
 460:     res->str = roll(table[subscript].strength.base,table[subscript].strength.interval);
 461:     res->man = roll(table[subscript].manna.base,table[subscript].manna.interval);
 462:     res->mxn = res->nrg = roll(table[subscript].energy.base,table[subscript].energy.interval);
 463:     res->brn = roll(table[subscript].brains.base,table[subscript].brains.interval);
 464:     res->mag = roll(table[subscript].magic.base,table[subscript].magic.interval);
 465:     res->typ = subscript;
 466:     if (subscript < 6)
 467:         ++res->typ;
 468:     if (type == '5')
 469:         res->exp = roll(600,200);   /* give halfling some exp. */
 470: }
 471: 
 472: void    movelvl(stat)               /* update stats for new level */
 473: reg struct  stats   *stat;
 474: {
 475: reg int type;
 476: reg unsigned new;
 477: double  inc;
 478: 
 479:     changed = TRUE;
 480:     type = abs(stat->typ);
 481:     if (type < 6)
 482:         ;   /* normal */
 483:     else if (type < 10)
 484:         type = roll(1,5);   /* experimento */
 485:     else if (type < 20)
 486:         {
 487:         type -= 10; /* king */
 488:         if (type > 5)
 489:             type = roll(1,5);   /* experimento */
 490:         }
 491:     else if (type < 26)
 492:         type -= 20; /* council of wise */
 493:     else
 494:         type = roll(1,5);   /* everything else */
 495:     new = level(stat->exp);
 496:     inc = new - stat->lvl;
 497:     --type;         /* set up for subscripting into table */
 498:     stat->str += table[type].strength.increase * inc;
 499:     stat->man += table[type].manna.increase * inc;
 500:     stat->brn += table[type].brains.increase * inc;
 501:     stat->mag += table[type].magic.increase * inc;
 502:     stat->mxn += table[type].energy.increase * inc;
 503:     stat->nrg = stat->mxn + stat->shd;
 504:     if ((stat->lvl = min(10000,new)) >= 1000)
 505:         {   /* no longer able to be king */
 506:         stat->gld += stat->crn * 5000;
 507:         stat->crn = 0;
 508:         stat->typ = abs(stat->typ);
 509:         }
 510:     if (stat->lvl >= 3000 && stat->typ < 20)
 511:         {   /* make a member of the council */
 512:         mvaddstr(6,0,"You have made it to the Council of the Wise.\nGood Luck on your search for the Holy Grail.\n");
 513:         stat->rng.type = 0;
 514:         stat->rng.duration = 3;
 515:         stat->typ = abs(stat->typ) + (stat->typ > 10 ? 10 :20);
 516:         }
 517: }
 518: 
 519: char    *printloc(x,y)          /* return a pointer to a string specifying location */
 520: double  x,y;        /* also, set some global flags */
 521: {
 522: reg int size, loc;
 523: reg char    *label;
 524: static  char    res[80],
 525:         *nametable[4][4] =   /* names of places */
 526:         {
 527:         "Anorien",  "Ithilien", "Rohan",    "Lorien",
 528:         "Gondor",   "Mordor",   "Dunland",  "Rovanion",
 529:         "South Gondor", "Khand",    "Eriador",  "The Iron Hills",
 530:         "Far Harad",    "Near Harad",   "The Northern Waste", "Rhun"
 531:         };
 532: 
 533:     throne = beyond = marsh = FALSE;
 534:     if (wmhl)
 535:         return (strcpy(res," is in the Wormholes"));
 536:     else if (valhala)
 537:         return (strcpy(res," is in Valhala"));
 538:     else if ((size = circ(x,y)) >= 1000)
 539:         {
 540:         if (max(abs(x),abs(y)) > 1100000)
 541:             {
 542:             label = "The Point of No Return";
 543:             beyond = TRUE;
 544:             }
 545:         else
 546:             label = "The Ashen Mountains";
 547:         }
 548:     else if (size >= 55)
 549:         label = "Morannon";
 550:     else if (size >= 35)
 551:         label = "Kennaquahair";
 552:     else if (size >= 20)
 553:         {
 554:         label = "The Dead Marshes";
 555:         marsh = TRUE;
 556:         }
 557:     else if (size >= 9)
 558:         label = "The Outer Waste";
 559:     else if (size >= 5)
 560:         label = "The Moors Adventurous";
 561:     else
 562:         {
 563:         if (!x && !y)
 564:             {
 565:             label = "The Lord's Chamber";
 566:             throne = TRUE;
 567:             }
 568:         else
 569:             {
 570:             loc = (x > 0) + 2 * (y >= 0);
 571:             label = nametable[size-1][loc];
 572:             }
 573:         }
 574:     sprintf(res," is in %s  (%.0f,%.0f)",label,x,y);
 575:     return (res);
 576: }
 577: 
 578: void    initchar(stat)              /* put in some default values */
 579: reg struct  stats   *stat;
 580: {
 581:     stat->x = roll(-125,251);
 582:     stat->y = roll(-125,251);
 583:     stat->exp = stat->lvl = stat->sin = 0;
 584:     stat->crn = stat->psn = 0;
 585:     stat->rng.type = NONE;
 586:     stat->rng.duration = 0;
 587:     stat->blind = stat->vrg = stat->pal = FALSE;
 588:     stat->hw = stat->amu = stat->bls = 0;
 589:     stat->chm = 0;
 590:     stat->gem = 0.1;
 591:     stat->gld = roll(25,50) + roll(0,25) + 0.1;
 592:     stat->quks = stat->swd = stat->shd = 0;
 593:     stat->typ = 0;
 594:     stat->status = stat->tampered = OFF;
 595:     stat->scratch1 = stat->scratch2 = 0.0;
 596:     stat->wormhole = 0;
 597:     stat->age = 0;
 598:     stat->degen = 1;
 599: }
 600: 
 601: void    trade(stat)             /* trading post */
 602: reg struct  stats   *stat;
 603: {
 604: static  struct
 605:         {
 606:         char    *item;
 607:         int cost;
 608:         }   menu[] =
 609:             {
 610:             "Manna",1,
 611:             "Shield",5,
 612:             "Book",200,
 613:             "Sword",500,
 614:             "Charm",1000,
 615:             "Quiksilver",2500,
 616:             "Blessing",7000,
 617:             "Gem",1000  /* this is only to ease changing the value of gems */
 618:             };
 619: double  temp;
 620: int ch;
 621: reg int size, loop;
 622: bool    cheat = FALSE;
 623: 
 624:     changed = TRUE;
 625:     clear();
 626:     addstr("You are at a trading post. All purchases must be made with gold.");
 627:     size = sqrt(abs(stat->x/100)) + 1;
 628:     size = min(7,size);
 629:     mvprintw(4,0,"L:Leave  P:Purchase  S:Sell Gems ? ");
 630:     move(6,0);
 631:     for (loop = 0; loop < size; ++loop)
 632:         printw("(%d) %-10s: %6d\n",loop+1,menu[loop].item,menu[loop].cost);
 633: PROMPT: mvprintw(1,0,"Gold:  %9.0f  Gems:  %9.0f  Level:   %6u  Charms: %6d\n",stat->gld,stat->gem,stat->lvl,stat->chm);
 634:     printw("Shield:%9.0f  Sword: %9.0f  Quicksilver:%3d  Blessed: %s",
 635:         stat->shd,stat->swd,stat->quks,(stat->bls ? " True" : "False"));
 636:     move(4,36);
 637:     ch = rgetch();
 638:     move(15,0);
 639:     clrtobot();
 640:     switch(toupper(ch))
 641:         {
 642:         case 'L':
 643:         case '\n':
 644:             stat->x -= floor(stat->x/10);
 645:             stat->y -= floor(stat->y/10);
 646:             return;
 647:         case 'P':
 648:             mvaddstr(15,0,"What what would you like to buy ? ");
 649:             ch = rgetch();
 650:             move(15,0);
 651:             clrtoeol();
 652:             if (ch - '0' > size)
 653:                 addstr("Sorry, this merchant doesn't have that.");
 654:             else
 655:                 switch (toupper(ch))
 656:                     {
 657:                     case '1':
 658:                         printw("Manna is one per %d gold piece.  How many do you want (%.0f max) ? ",menu[0].cost,floor(stat->gld/menu[0].cost));
 659:                         temp = inflt();
 660:                         if (temp * menu[0].cost > stat->gld || temp < 0)
 661:                             goto CHEAT;
 662:                         else
 663:                             {
 664:                             stat->gld -= floor(temp) * menu[0].cost;
 665:                             if (rnd() < 0.02)
 666:                                 goto DISHON;
 667:                             else
 668:                                 stat->man += floor(temp);
 669:                             }
 670:                         break;
 671:                     case '2':
 672:                         printw("Shields are %d per +1.  How many do you want (%.0f max) ? ",menu[1].cost,floor(stat->gld/menu[1].cost));
 673:                         temp = inflt();
 674:                         if (!temp)
 675:                             break;
 676:                         if (temp * menu[1].cost > stat->gld || temp < 0)
 677:                             goto CHEAT;
 678:                         else
 679:                             {
 680:                             stat->gld -= floor(temp) * menu[1].cost;
 681:                             if (rnd() < 0.02)
 682:                                 goto DISHON;
 683:                             else
 684:                                 stat->shd = floor(temp);
 685:                             }
 686:                         break;
 687:                     case '3':
 688:                         printw("A book costs %d gp.  How many do you want (%.0f max) ? ",menu[2].cost,floor(stat->gld/menu[2].cost));
 689:                         temp = inflt();
 690:                         if (temp * menu[2].cost > stat->gld || temp < 0)
 691:                             goto CHEAT;
 692:                         else
 693:                             {
 694:                             stat->gld -= floor(temp) * menu[2].cost;
 695:                             if (rnd() < 0.02)
 696:                                 goto DISHON;
 697:                             else
 698:                                 if (rnd()*temp > stat->lvl/10 && temp != 1)
 699:                                     {
 700:                                     printw("\nYou blew your mind!\n");
 701:                                     stat->brn /= 5;
 702:                                     }
 703:                                 else
 704:                                     stat->brn += floor(temp)*roll(25,10);
 705:                             }
 706:                         break;
 707:                     case '4':
 708:                         printw("Swords are %d gp per +1.  How many + do you want (%.0f max) ? ",menu[3].cost,floor(stat->gld/menu[3].cost));
 709:                         temp = inflt();
 710:                         if (!temp)
 711:                             break;
 712:                         if (temp * menu[3].cost > stat->gld || temp < 0)
 713:                             goto CHEAT;
 714:                         else
 715:                             {
 716:                             stat->gld -= floor(temp) * menu[3].cost;
 717:                             if (rnd() < 0.02)
 718:                                 goto DISHON;
 719:                             else
 720:                                 stat->swd = floor(temp);
 721:                             }
 722:                         break;
 723:                     case '5':
 724:                         printw("A charm costs %d gp.  How many do you want (%.0f max) ? ",menu[4].cost,floor(stat->gld/menu[4].cost));
 725:                         temp = inflt();
 726:                         if (temp * menu[4].cost > stat->gld || temp < 0)
 727:                             goto CHEAT;
 728:                         else
 729:                             {
 730:                             stat->gld -= floor(temp) * menu[4].cost;
 731:                             if (rnd() < 0.02)
 732:                                 goto DISHON;
 733:                             else
 734:                                 stat->chm += floor(temp);
 735:                             }
 736:                         break;
 737:                     case '6':
 738:                         printw("Quicksilver is %d gp per +1.  How many + do you want (%.0f max) ? ",menu[5].cost,floor(stat->gld/menu[5].cost));
 739:                         temp = inflt();
 740:                         if (!temp)
 741:                             break;
 742:                         if (temp * menu[5].cost > stat->gld || temp < 0)
 743:                             goto CHEAT;
 744:                         else
 745:                             {
 746:                             stat->gld -= floor(temp) * menu[5].cost;
 747:                             if (rnd() < 0.02)
 748:                                 goto DISHON;
 749:                             else
 750:                                 stat->quks = min(99,floor(temp));
 751:                             }
 752:                         break;
 753:                     case '7':
 754:                         printw("A blessing requires a %d gp donation.  Still want one ? ",menu[6].cost);
 755:                         ch = rgetch();
 756:                         if (toupper(ch) == 'Y')
 757:                             if (stat->gld < menu[6].cost)
 758:                                 goto CHEAT;
 759:                             else
 760:                                 {
 761:                                 stat->gld -= menu[6].cost;
 762:                                 if (rnd() < 0.02)
 763:                                     goto DISHON;
 764:                                 else
 765:                                     stat->bls = TRUE;
 766:                                 }
 767:                         break;
 768:                     }
 769:             break;
 770:         case 'S':
 771:             mvprintw(15,0,"A gem is worth %d gp.  How many do you want to sell (%.0f max) ? ",menu[7].cost,stat->gem);
 772:             temp = inflt();
 773:             if (temp > stat->gem || temp < 0)
 774:                 goto CHEAT;
 775:             else
 776:                 {
 777:                 stat->gem -= floor(temp);
 778:                 stat->gld += floor(temp) * menu[7].cost;
 779:                 }
 780:         }
 781:     goto PROMPT;
 782: 
 783: CHEAT:  move(17,0);
 784:     if (!cheat)
 785:         {
 786:         addstr("Come on, merchants aren't stupid.  Stop cheating.\n");
 787:         cheat = TRUE;
 788:         goto PROMPT;
 789:         }
 790:     else
 791:         {
 792:         addstr("You had your chance.  This merchant happens to be\n");
 793:         printw("a %.0f level magic user, and you made %s mad!\n",roll(size*10,size*20),(rnd() < 0.5) ? "him" : "her");
 794:         stat->x += roll(-250,500)*size;
 795:         stat->y += roll(-250,500)*size;
 796:         stat->nrg = min(size*20,stat->mxn);
 797:         ++stat->sin;
 798:         paws(23);
 799:         }
 800:     return;
 801: 
 802: DISHON: mvaddstr(17,0,"The merchant stole your money!");
 803:     refresh();
 804:     stat->x -= floor(stat->x/10);
 805:     stat->y -= floor(stat->y/10);
 806:     sleep(2);
 807: }
 808: 
 809: void    printstats(stat)                /* show characteristics */
 810: reg struct  stats   *stat;
 811: {
 812:     mvprintw(0,0,"%s%s\n",stat->name,printloc(stat->x,stat->y));
 813:     mvprintw(1,0,"Level :%7u   Energy  :%9.0f(%9.0f)  Manna:%9.0f  Users:%3d\n",
 814:         stat->lvl,stat->nrg,stat->mxn + stat->shd,stat->man,users);
 815:     mvprintw(2,0,"Quick :%3.0f(%3d)  Strength:%9.0f(%9.0f)  Gold :%9.0f    ",
 816:         speed,stat->quk + stat->quks,strength,stat->str + stat->swd,stat->gld);
 817:     switch (stat->status)
 818:         {
 819:         case PLAYING:
 820:             if (stat->nrg < 0.2 * (stat->mxn + stat->shd))
 821:                 addstr("Low Energy\n");
 822:             else if (stat->blind)
 823:                 addstr("Blind\n");
 824:             else
 825:                 clrtoeol();
 826:             break;
 827:         case CLOAKED:
 828:             addstr("Cloaked\n");
 829:             break;
 830:         case INBATTLE:
 831:             addstr("In Battle\n");
 832:             break;
 833:         case OFF:
 834:             addstr("Off\n");
 835:         }
 836: }
 837: 
 838: void    showall(stat)               /* show special items */
 839: reg struct  stats   *stat;
 840: {
 841: static  char    *flags[] =
 842:             {
 843:             "False",
 844:             " True"
 845:             };
 846: 
 847:     mvprintw(6,0,"Type: %3d  --  ",stat->typ);
 848:     switch (abs(stat->typ))
 849:         {
 850:         case 1:
 851:         case 11:
 852:         case 21:
 853:             addstr("Magic User");
 854:             break;
 855:         case 2:
 856:         case 12:
 857:         case 22:
 858:             addstr("Fighter");
 859:             break;
 860:         case 3:
 861:         case 13:
 862:         case 23:
 863:             addstr("Elf");
 864:             break;
 865:         case 4:
 866:         case 14:
 867:         case 24:
 868:             addstr("Dwarf");
 869:             break;
 870:         case 5:
 871:         case 15:
 872:         case 25:
 873:             addstr("Halfling");
 874:             break;
 875:         case 6:
 876:         case 16:
 877:         case 26:
 878:             addstr("Experimento");
 879:             break;
 880:         case 90:
 881:             addstr("Ex-Valar");
 882:             break;
 883:         case 99:
 884:             addstr("Valar");
 885:         }
 886:     if (stat->typ > 10 && stat->typ < 90)
 887:         if (stat->typ > 20)
 888:             addstr(" (Council of Wise)");
 889:         else
 890:             addstr(" (King)");
 891:         addch('\n');
 892:     mvprintw(7,0,"Experience: %9.0f",stat->exp);
 893:     mvprintw(8,0,"Brains    : %9.0f",stat->brn);
 894:     mvprintw(9,0,"Magic Lvl : %9.0f",stat->mag);
 895:     mvprintw(10,0,"Sin       : %9.5f",stat->sin);
 896:     mvprintw(11,0,"Poison    : %9.5f",stat->psn);
 897:     mvprintw(12,0,"Gems      : %9.0f",stat->gem);
 898:     mvprintw(13,0,"Age       : %9d",stat->age);
 899:     mvprintw(7,40,"Holy Water: %9d",stat->hw);
 900:     mvprintw(8,40,"Amulets   : %9d",stat->amu);
 901:     mvprintw(9,40,"Charms    : %9d",stat->chm);
 902:     mvprintw(10,40,"Crowns    : %9d",stat->crn);
 903:     mvprintw(11,40,"Shield    : %9.0f",stat->shd);
 904:     mvprintw(12,40,"Sword     : %9.0f",stat->swd);
 905:     mvprintw(13,40,"Quickslver: %9d",stat->quks);
 906: 
 907:     mvprintw(14,0,"Blessing: %s   Ring: %s   Virgin: %s   Palantir: %s",
 908:         flags[stat->bls],flags[stat->rng.type != 0],flags[stat->vrg],flags[stat->pal]);
 909: }
 910: 
 911: void    neatstuff(stat)             /* random things */
 912: reg struct  stats   *stat;
 913: {
 914: double  temp;
 915: int ch;
 916: 
 917:     switch ((int) roll(0,100))
 918:         {
 919:         case 1:
 920:         case 2:
 921:             if (stat->psn > 0)
 922:                 {
 923:                 mvaddstr(5,0,"You've found a medic!  How much will you offer to be cured ? ");
 924:                 temp = inflt();
 925:                 if (temp < 0 || temp > stat->gld)
 926:                     {
 927:                     mvaddstr(6,0,"He was not amused, and made you worse.\n");
 928:                     ++stat->psn;
 929:                     }
 930:                 else if (rnd()/2.0 > (temp + 1)/max(stat->gld,1))
 931:                     mvaddstr(6,0,"Sorry, he wasn't interested.\n");
 932:                 else
 933:                     {
 934:                     mvaddstr(6,0,"He accepted.");
 935:                     stat->psn = max(0,stat->psn-1);
 936:                     stat->gld -= floor(temp);
 937:                     }
 938:                 }
 939:             break;
 940:         case 3:
 941:             mvaddstr(6,0,"You've been caught raping and pillaging!\n");
 942:             stat->exp += 4000;
 943:             stat->sin += 0.5;
 944:             break;
 945:         case 4:
 946:             temp = roll(6,50);
 947:             mvprintw(5,0,"You've found %.0f gold pieces, want them ? ",temp);
 948:             clrtoeol();
 949:             ch = rgetch();
 950:             if (toupper(ch) == 'Y')
 951:                 stat->gld += temp;
 952:             break;
 953:         case 5:
 954:             if (stat->sin > 1)
 955:                 {
 956:                 mvaddstr(6,0,"You've found a Holy Orb!\n");
 957:                 stat->sin -= 0.25;
 958:                 }
 959:             break;
 960:         case 6:
 961:             if (stat->psn < 1)
 962:                 {
 963:                 mvaddstr(6,0,"You've been hit with a plague!\n");
 964:                 ++stat->psn;
 965:                 }
 966:             break;
 967:         case 7:
 968:             mvaddstr(6,0,"You've found some holy water.\n");
 969:             ++stat->hw;
 970:             break;
 971:         case 8:
 972:             mvaddstr(6,0,"You've met a Guru. . .");
 973:             if (rnd()*stat->sin > 1)
 974:                 addstr("You disgusted him with your sins!\n");
 975:             else if (stat->psn > 0)
 976:                 {
 977:                 addstr("He looked kindly upon you, and cured you.\n");
 978:                 stat->psn = 0;
 979:                 }
 980:             else
 981:                 {
 982:                 addstr("He rewarded you for your virtue.\n");
 983:                 stat->man += 50;
 984:                 stat->shd += 2;
 985:                 }
 986:             break;
 987:         case 9:
 988:             mvaddstr(6,0,"You've found an amulet.\n");
 989:             ++stat->amu;
 990:             break;
 991:         case 10:
 992:             if (stat->blind)
 993:                 {
 994:                 mvaddstr(6,0,"You've regained your sight!\n");
 995:                 stat->blind = FALSE;
 996:                 }
 997:             break;
 998:         default:
 999:             if (stat->psn > 0)
1000:                 stat->nrg -= min(stat->psn*stat->mxn/45,0.9*stat->mxn);
1001:             stat->nrg = max(stat->nrg,floor(stat->mxn/11));
1002:         }
1003: }
Last modified: 1986-05-20
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 5916
Valid CSS Valid XHTML 1.0 Strict