1*32689Sbostic /* 2*32689Sbostic * ring.c 3*32689Sbostic * 4*32689Sbostic * This source herein may be modified and/or distributed by anybody who 5*32689Sbostic * so desires, with the following restrictions: 6*32689Sbostic * 1.) No portion of this notice shall be removed. 7*32689Sbostic * 2.) Credit shall not be taken for the creation of this source. 8*32689Sbostic * 3.) This code is not to be traded, sold, or used for personal 9*32689Sbostic * gain or profit. 10*32689Sbostic * 11*32689Sbostic */ 12*32689Sbostic 13*32689Sbostic #ifndef lint 14*32689Sbostic static char sccsid[] = "@(#)ring.c 5.1 (Berkeley) 11/25/87"; 15*32689Sbostic #endif /* not lint */ 16*32689Sbostic 17*32689Sbostic #include "rogue.h" 18*32689Sbostic 19*32689Sbostic char *left_or_right = "left or right hand?"; 20*32689Sbostic char *no_ring = "there's no ring on that hand"; 21*32689Sbostic short stealthy; 22*32689Sbostic short r_rings; 23*32689Sbostic short add_strength; 24*32689Sbostic short e_rings; 25*32689Sbostic short regeneration; 26*32689Sbostic short ring_exp; 27*32689Sbostic short auto_search; 28*32689Sbostic boolean r_teleport; 29*32689Sbostic boolean r_see_invisible; 30*32689Sbostic boolean sustain_strength; 31*32689Sbostic boolean maintain_armor; 32*32689Sbostic 33*32689Sbostic extern char *curse_message; 34*32689Sbostic extern boolean wizard; 35*32689Sbostic 36*32689Sbostic put_on_ring() 37*32689Sbostic { 38*32689Sbostic short ch; 39*32689Sbostic char desc[DCOLS]; 40*32689Sbostic object *ring; 41*32689Sbostic 42*32689Sbostic if (r_rings == 2) { 43*32689Sbostic message("wearing two rings already", 0); 44*32689Sbostic return; 45*32689Sbostic } 46*32689Sbostic if ((ch = pack_letter("put on what?", RING)) == CANCEL) { 47*32689Sbostic return; 48*32689Sbostic } 49*32689Sbostic if (!(ring = get_letter_object(ch))) { 50*32689Sbostic message("no such item.", 0); 51*32689Sbostic return; 52*32689Sbostic } 53*32689Sbostic if (!(ring->what_is & RING)) { 54*32689Sbostic message("that's not a ring", 0); 55*32689Sbostic return; 56*32689Sbostic } 57*32689Sbostic if (ring->in_use_flags & (ON_LEFT_HAND | ON_RIGHT_HAND)) { 58*32689Sbostic message("that ring is already being worn", 0); 59*32689Sbostic return; 60*32689Sbostic } 61*32689Sbostic if (r_rings == 1) { 62*32689Sbostic ch = (rogue.left_ring ? 'r' : 'l'); 63*32689Sbostic } else { 64*32689Sbostic message(left_or_right, 0); 65*32689Sbostic do { 66*32689Sbostic ch = rgetchar(); 67*32689Sbostic } while ((ch != CANCEL) && (ch != 'l') && (ch != 'r') && (ch != '\n') && 68*32689Sbostic (ch != '\r')); 69*32689Sbostic } 70*32689Sbostic if ((ch != 'l') && (ch != 'r')) { 71*32689Sbostic check_message(); 72*32689Sbostic return; 73*32689Sbostic } 74*32689Sbostic if (((ch == 'l') && rogue.left_ring)||((ch == 'r') && rogue.right_ring)) { 75*32689Sbostic check_message(); 76*32689Sbostic message("there's already a ring on that hand", 0); 77*32689Sbostic return; 78*32689Sbostic } 79*32689Sbostic if (ch == 'l') { 80*32689Sbostic do_put_on(ring, 1); 81*32689Sbostic } else { 82*32689Sbostic do_put_on(ring, 0); 83*32689Sbostic } 84*32689Sbostic ring_stats(1); 85*32689Sbostic check_message(); 86*32689Sbostic get_desc(ring, desc); 87*32689Sbostic message(desc, 0); 88*32689Sbostic (void) reg_move(); 89*32689Sbostic } 90*32689Sbostic 91*32689Sbostic /* 92*32689Sbostic * Do not call ring_stats() from within do_put_on(). It will cause 93*32689Sbostic * serious problems when do_put_on() is called from read_pack() in restore(). 94*32689Sbostic */ 95*32689Sbostic 96*32689Sbostic do_put_on(ring, on_left) 97*32689Sbostic object *ring; 98*32689Sbostic boolean on_left; 99*32689Sbostic { 100*32689Sbostic if (on_left) { 101*32689Sbostic ring->in_use_flags |= ON_LEFT_HAND; 102*32689Sbostic rogue.left_ring = ring; 103*32689Sbostic } else { 104*32689Sbostic ring->in_use_flags |= ON_RIGHT_HAND; 105*32689Sbostic rogue.right_ring = ring; 106*32689Sbostic } 107*32689Sbostic } 108*32689Sbostic 109*32689Sbostic remove_ring() 110*32689Sbostic { 111*32689Sbostic boolean left = 0, right = 0; 112*32689Sbostic short ch; 113*32689Sbostic char buf[DCOLS]; 114*32689Sbostic object *ring; 115*32689Sbostic 116*32689Sbostic if (r_rings == 0) { 117*32689Sbostic inv_rings(); 118*32689Sbostic } else if (rogue.left_ring && !rogue.right_ring) { 119*32689Sbostic left = 1; 120*32689Sbostic } else if (!rogue.left_ring && rogue.right_ring) { 121*32689Sbostic right = 1; 122*32689Sbostic } else { 123*32689Sbostic message(left_or_right, 0); 124*32689Sbostic do { 125*32689Sbostic ch = rgetchar(); 126*32689Sbostic } while ((ch != CANCEL) && (ch != 'l') && (ch != 'r') && 127*32689Sbostic (ch != '\n') && (ch != '\r')); 128*32689Sbostic left = (ch == 'l'); 129*32689Sbostic right = (ch == 'r'); 130*32689Sbostic check_message(); 131*32689Sbostic } 132*32689Sbostic if (left || right) { 133*32689Sbostic if (left) { 134*32689Sbostic if (rogue.left_ring) { 135*32689Sbostic ring = rogue.left_ring; 136*32689Sbostic } else { 137*32689Sbostic message(no_ring, 0); 138*32689Sbostic } 139*32689Sbostic } else { 140*32689Sbostic if (rogue.right_ring) { 141*32689Sbostic ring = rogue.right_ring; 142*32689Sbostic } else { 143*32689Sbostic message(no_ring, 0); 144*32689Sbostic } 145*32689Sbostic } 146*32689Sbostic if (ring->is_cursed) { 147*32689Sbostic message(curse_message, 0); 148*32689Sbostic } else { 149*32689Sbostic un_put_on(ring); 150*32689Sbostic (void) strcpy(buf, "removed "); 151*32689Sbostic get_desc(ring, buf + 8); 152*32689Sbostic message(buf, 0); 153*32689Sbostic (void) reg_move(); 154*32689Sbostic } 155*32689Sbostic } 156*32689Sbostic } 157*32689Sbostic 158*32689Sbostic un_put_on(ring) 159*32689Sbostic object *ring; 160*32689Sbostic { 161*32689Sbostic if (ring && (ring->in_use_flags & ON_LEFT_HAND)) { 162*32689Sbostic ring->in_use_flags &= (~ON_LEFT_HAND); 163*32689Sbostic rogue.left_ring = 0; 164*32689Sbostic } else if (ring && (ring->in_use_flags & ON_RIGHT_HAND)) { 165*32689Sbostic ring->in_use_flags &= (~ON_RIGHT_HAND); 166*32689Sbostic rogue.right_ring = 0; 167*32689Sbostic } 168*32689Sbostic ring_stats(1); 169*32689Sbostic } 170*32689Sbostic 171*32689Sbostic gr_ring(ring, assign_wk) 172*32689Sbostic object *ring; 173*32689Sbostic boolean assign_wk; 174*32689Sbostic { 175*32689Sbostic ring->what_is = RING; 176*32689Sbostic if (assign_wk) { 177*32689Sbostic ring->which_kind = get_rand(0, (RINGS - 1)); 178*32689Sbostic } 179*32689Sbostic ring->class = 0; 180*32689Sbostic 181*32689Sbostic switch(ring->which_kind) { 182*32689Sbostic /* 183*32689Sbostic case STEALTH: 184*32689Sbostic break; 185*32689Sbostic case SLOW_DIGEST: 186*32689Sbostic break; 187*32689Sbostic case REGENERATION: 188*32689Sbostic break; 189*32689Sbostic case R_SEE_INVISIBLE: 190*32689Sbostic break; 191*32689Sbostic case SUSTAIN_STRENGTH: 192*32689Sbostic break; 193*32689Sbostic case R_MAINTAIN_ARMOR: 194*32689Sbostic break; 195*32689Sbostic case SEARCHING: 196*32689Sbostic break; 197*32689Sbostic */ 198*32689Sbostic case R_TELEPORT: 199*32689Sbostic ring->is_cursed = 1; 200*32689Sbostic break; 201*32689Sbostic case ADD_STRENGTH: 202*32689Sbostic case DEXTERITY: 203*32689Sbostic while ((ring->class = (get_rand(0, 4) - 2)) == 0) ; 204*32689Sbostic ring->is_cursed = (ring->class < 0); 205*32689Sbostic break; 206*32689Sbostic case ADORNMENT: 207*32689Sbostic ring->is_cursed = coin_toss(); 208*32689Sbostic break; 209*32689Sbostic } 210*32689Sbostic } 211*32689Sbostic 212*32689Sbostic inv_rings() 213*32689Sbostic { 214*32689Sbostic char buf[DCOLS]; 215*32689Sbostic 216*32689Sbostic if (r_rings == 0) { 217*32689Sbostic message("not wearing any rings", 0); 218*32689Sbostic } else { 219*32689Sbostic if (rogue.left_ring) { 220*32689Sbostic get_desc(rogue.left_ring, buf); 221*32689Sbostic message(buf, 0); 222*32689Sbostic } 223*32689Sbostic if (rogue.right_ring) { 224*32689Sbostic get_desc(rogue.right_ring, buf); 225*32689Sbostic message(buf, 0); 226*32689Sbostic } 227*32689Sbostic } 228*32689Sbostic if (wizard) { 229*32689Sbostic sprintf(buf, "ste %d, r_r %d, e_r %d, r_t %d, s_s %d, a_s %d, reg %d, r_e %d, s_i %d, m_a %d, aus %d", 230*32689Sbostic stealthy, r_rings, e_rings, r_teleport, sustain_strength, 231*32689Sbostic add_strength, regeneration, ring_exp, r_see_invisible, 232*32689Sbostic maintain_armor, auto_search); 233*32689Sbostic message(buf, 0); 234*32689Sbostic } 235*32689Sbostic } 236*32689Sbostic 237*32689Sbostic ring_stats(pr) 238*32689Sbostic boolean pr; 239*32689Sbostic { 240*32689Sbostic short i; 241*32689Sbostic object *ring; 242*32689Sbostic 243*32689Sbostic stealthy = 0; 244*32689Sbostic r_rings = 0; 245*32689Sbostic e_rings = 0; 246*32689Sbostic r_teleport = 0; 247*32689Sbostic sustain_strength = 0; 248*32689Sbostic add_strength = 0; 249*32689Sbostic regeneration = 0; 250*32689Sbostic ring_exp = 0; 251*32689Sbostic r_see_invisible = 0; 252*32689Sbostic maintain_armor = 0; 253*32689Sbostic auto_search = 0; 254*32689Sbostic 255*32689Sbostic for (i = 0; i < 2; i++) { 256*32689Sbostic if (!(ring = ((i == 0) ? rogue.left_ring : rogue.right_ring))) { 257*32689Sbostic continue; 258*32689Sbostic } 259*32689Sbostic r_rings++; 260*32689Sbostic e_rings++; 261*32689Sbostic switch(ring->which_kind) { 262*32689Sbostic case STEALTH: 263*32689Sbostic stealthy++; 264*32689Sbostic break; 265*32689Sbostic case R_TELEPORT: 266*32689Sbostic r_teleport = 1; 267*32689Sbostic break; 268*32689Sbostic case REGENERATION: 269*32689Sbostic regeneration++; 270*32689Sbostic break; 271*32689Sbostic case SLOW_DIGEST: 272*32689Sbostic e_rings -= 2; 273*32689Sbostic break; 274*32689Sbostic case ADD_STRENGTH: 275*32689Sbostic add_strength += ring->class; 276*32689Sbostic break; 277*32689Sbostic case SUSTAIN_STRENGTH: 278*32689Sbostic sustain_strength = 1; 279*32689Sbostic break; 280*32689Sbostic case DEXTERITY: 281*32689Sbostic ring_exp += ring->class; 282*32689Sbostic break; 283*32689Sbostic case ADORNMENT: 284*32689Sbostic break; 285*32689Sbostic case R_SEE_INVISIBLE: 286*32689Sbostic r_see_invisible = 1; 287*32689Sbostic break; 288*32689Sbostic case MAINTAIN_ARMOR: 289*32689Sbostic maintain_armor = 1; 290*32689Sbostic break; 291*32689Sbostic case SEARCHING: 292*32689Sbostic auto_search += 2; 293*32689Sbostic break; 294*32689Sbostic } 295*32689Sbostic } 296*32689Sbostic if (pr) { 297*32689Sbostic print_stats(STAT_STRENGTH); 298*32689Sbostic relight(); 299*32689Sbostic } 300*32689Sbostic } 301