Annotation of early-roguelike/srogue/things.c, Revision 1.1.1.1
1.1 rubenllo 1: /*
2: * Contains functions for dealing with things like
3: * potions and scrolls
4: *
5: * @(#)things.c 9.0 (rdk) 7/17/84
6: *
7: * Super-Rogue
8: * Copyright (C) 1984 Robert D. Kindelberger
9: * All rights reserved.
10: *
11: * Based on "Rogue: Exploring the Dungeons of Doom"
12: * Copyright (C) 1980, 1981 Michael Toy, Ken Arnold and Glenn Wichman
13: * All rights reserved.
14: *
15: * See the file LICENSE.TXT for full copyright and licensing information.
16: */
17:
18: #include <ctype.h>
19: #include <string.h>
20: #include "rogue.h"
21: #include "rogue.ext"
22:
23: void basic_init(struct object *cur);
24:
25: /*
26: * inv_name:
27: * Return the name of something as it would appear in an inventory.
28: */
29: char *
30: inv_name(struct object *obj, bool drop)
31: {
32: reg char *pb, *tn, *pl;
33: reg int wh, knowit;
34: char nm[3], *inm, *q;
35:
36: wh = obj->o_which;
37: knowit = FALSE;
38: if (obj->o_count > 1)
39: pl = "s";
40: else
41: pl = "";
42: if (obj->o_count > 1)
43: sprintf(nm, "%d", obj->o_count);
44: else
45: strcpy(nm, "A");
46: tn = obj->o_typname;
47: q = "";
48: switch(obj->o_type) {
49: case SCROLL:
50: sprintf(prbuf, "%s %s%s ", nm, tn, pl);
51: pb = &prbuf[strlen(prbuf)];
52: if (s_know[wh] || o_on(obj,ISPOST)) {
53: knowit = TRUE;
54: sprintf(pb, "of %s", s_magic[wh].mi_name);
55: }
56: else if (s_guess[wh])
57: sprintf(pb, "called %s", s_guess[wh]);
58: else
59: sprintf(pb, "titled '%s'", s_names[wh]);
60: when POTION:
61: sprintf(prbuf, "%s %s%s ", nm, tn, pl);
62: pb = &prbuf[strlen(prbuf)];
63: if (p_know[wh] || o_on(obj, ISPOST)) {
64: sprintf(pb, "of %s", p_magic[wh].mi_name);
65: knowit = TRUE;
66: if (p_know[wh]) {
67: pb = &prbuf[strlen(prbuf)];
68: sprintf(pb,"(%s)",p_colors[wh]);
69: }
70: }
71: else if (p_guess[wh])
72: sprintf(pb,"called %s(%s)", p_guess[wh],p_colors[wh]);
73: else if (obj->o_count == 1)
74: sprintf(prbuf,"%s%s %s %s%s", nm, vowelstr(p_colors[wh]),
75: p_colors[wh], tn, pl);
76: else
77: sprintf(prbuf,"%s %s %s%s", nm, p_colors[wh], tn, pl);
78: when FOOD:
79: if (wh == 1) {
80: if (obj->o_count == 1)
81: q = vowelstr(fruit);
82: sprintf(prbuf, "%s%s %.72s%s", nm, q, fruit, pl);
83: }
84: else {
85: if (obj->o_count == 1)
86: sprintf(prbuf, "Some %s", tn);
87: else
88: sprintf(prbuf, "%s rations of %s", nm, tn);
89: }
90: knowit = TRUE;
91: when WEAPON:
92: inm = w_magic[wh].mi_name;
93: strcpy(prbuf, nm);
94: if (obj->o_count == 1)
95: q = vowelstr(inm);
96: pb = &prbuf[strlen(prbuf)];
97: if (o_on(obj,ISKNOW | ISPOST)) {
98: knowit = TRUE;
99: sprintf(pb, " %s %s", num(obj->o_hplus, obj->o_dplus), inm);
100: }
101: else
102: sprintf(pb, "%s %s", q, inm);
103: strcat(prbuf, pl);
104: when ARMOR:
105: inm = a_magic[wh].mi_name;
106: if (o_on(obj,ISKNOW | ISPOST)) {
107: knowit = TRUE;
108: sprintf(prbuf, "%s %s",num(armors[wh].a_class - obj->o_ac, 0),
109: inm);
110: }
111: else
112: sprintf(prbuf, "%s", inm);
113: when AMULET:
114: strcpy(prbuf, "The Amulet of Yendor");
115: when STICK: {
116: struct rod *rd;
117:
118: rd = &ws_stuff[wh];
119: sprintf(prbuf, "A %s ", rd->ws_type);
120: pb = &prbuf[strlen(prbuf)];
121: if (ws_know[wh] || o_on(obj, ISPOST)) {
122: knowit = TRUE;
123: sprintf(pb,"of %s%s",ws_magic[wh].mi_name,charge_str(obj));
124: if (ws_know[wh]) {
125: pb = &prbuf[strlen(prbuf)];
126: sprintf(pb,"(%s)",rd->ws_made);
127: }
128: }
129: else if (ws_guess[wh])
130: sprintf(pb, "called %s(%s)", ws_guess[wh], rd->ws_made);
131: else
132: sprintf(prbuf, "A%s %s %s", vowelstr(rd->ws_made),
133: rd->ws_made, rd->ws_type);
134: }
135: when RING:
136: if (r_know[wh] || o_on(obj, ISPOST)) {
137: knowit = TRUE;
138: sprintf(prbuf, "A%s %s of %s", ring_num(obj), tn,
139: r_magic[wh].mi_name);
140: if (r_know[wh]) {
141: pb = &prbuf[strlen(prbuf)];
142: sprintf(pb,"(%s)", r_stones[wh]);
143: }
144: }
145: else if (r_guess[wh])
146: sprintf(prbuf,"A %s called %s(%s)",tn, r_guess[wh],
147: r_stones[wh]);
148: else
149: sprintf(prbuf,"A%s %s %s",vowelstr(r_stones[wh]),
150: r_stones[wh], tn);
151: otherwise:
152: sprintf(prbuf,"Something bizarre %s", unctrl(obj->o_type));
153: }
154: if (obj == cur_armor)
155: strcat(prbuf, " (being worn)");
156: if (obj == cur_weapon)
157: strcat(prbuf, " (weapon in hand)");
158: if (obj == cur_ring[LEFT])
159: strcat(prbuf, " (on left hand)");
160: else if (obj == cur_ring[RIGHT])
161: strcat(prbuf, " (on right hand)");
162: if (drop && isupper(prbuf[0]))
163: prbuf[0] = tolower(prbuf[0]);
164: else if (!drop && islower(*prbuf))
165: *prbuf = toupper(*prbuf);
166: if (o_on(obj, ISPROT))
167: strcat(prbuf, " [!]");
168: if (o_on(obj, ISPOST))
169: strcat(prbuf, " [$]");
170: if (knowit) {
171: if (o_on(obj, ISCURSED))
172: strcat(prbuf, " [-]");
173: else if (o_on(obj, ISBLESS))
174: strcat(prbuf, " [+]");
175: }
176: if (!drop)
177: strcat(prbuf, ".");
178: return prbuf;
179: }
180:
181: /*
182: * money:
183: * Add to characters purse
184: */
185: void
186: money(void)
187: {
188: reg struct room *rp;
189: reg struct linked_list *item;
190: reg struct thing *tp;
191:
192: rp = player.t_room;
193: if (rp != NULL && ce(hero, rp->r_gold)) {
194: msg("%d gold pieces.", rp->r_goldval);
195: purse += rp->r_goldval;
196: rp->r_goldval = 0;
197: cmov(rp->r_gold);
198: addch(FLOOR);
199: /*
200: * once gold is taken, all monsters will chase him
201: */
202: for (item = mlist; item != NULL; item = next(item)) {
203: tp = THINGPTR(item);
204: if (rnd(100) < 70 && tp->t_room == rp && !iswearing(R_STEALTH)
205: && ((tp->t_flags & (ISMEAN | ISGREED)) || rnd(1000) < 20))
206: runto(&tp->t_pos, &hero);
207: }
208: }
209: else
210: msg("That gold must have been counterfeit.");
211: }
212:
213:
214: /*
215: * drop:
216: * put something down
217: */
218: int
219: drop(struct linked_list *item)
220: {
221: reg char ch;
222: reg struct linked_list *ll, *nll;
223: reg struct object *op;
224:
225: if (item == NULL) {
226: ch = mvinch(hero.y, hero.x);
227: if (ch != FLOOR && ch != PASSAGE && ch != POOL) {
228: msg("There is something there already.");
229: after = FALSE;
230: return SOMTHERE;
231: }
232: if ((ll = get_item("drop", 0)) == NULL)
233: return FALSE;
234: }
235: else {
236: ll = item;
237: }
238: op = OBJPTR(ll);
239: if (!dropcheck(op))
240: return CANTDROP;
241: /*
242: * Take it out of the pack
243: */
244: if (op->o_count >= 2 && op->o_type != WEAPON) {
245: nll = new_item(sizeof *op);
246: op->o_count--;
247: op->o_vol = itemvol(op);
248: op = OBJPTR(nll);
249: *op = *(OBJPTR(ll));
250: op->o_count = 1;
251: op->o_vol = itemvol(op);
252: ll = nll;
253: }
254: else {
255: detach(pack, ll);
256: }
257: if (ch == POOL) {
258: msg("%s sinks out of sight.",inv_name(op, TRUE));
259: discard(ll);
260: }
261: else { /* put on dungeon floor */
262: if (levtype == POSTLEV) {
263: op->o_pos = hero; /* same place as hero */
264: fall(ll,FALSE);
265: if (item == NULL) /* if item wasn't sold */
266: msg("Thanks for your donation to the Fiend's flea market.");
267: }
268: else {
269: attach(lvl_obj, ll);
270: mvaddch(hero.y, hero.x, op->o_type);
271: op->o_pos = hero;
272: msg("Dropped %s", inv_name(op, TRUE));
273: }
274: }
275: updpack(); /* new pack weight */
276: return TRUE;
277: }
278:
279:
280: /*
281: * dropcheck:
282: * Do special checks for dropping or unweilding|unwearing|unringing
283: */
284: bool
285: dropcheck(struct object *op)
286: {
287: if (op == NULL)
288: return TRUE;
289: if (levtype == POSTLEV) {
290: if (o_on(op,ISCURSED) && o_on(op,ISKNOW)) {
291: msg("The trader does not accept shoddy merchandise.");
292: return FALSE;
293: }
294: else {
295: cur_null(op); /* update cur_weapon, etc */
296: return TRUE;
297: }
298: }
299: if (op != cur_armor && op != cur_weapon
300: && op != cur_ring[LEFT] && op != cur_ring[RIGHT])
301: return TRUE;
302: if (o_on(op,ISCURSED)) {
303: msg("You can't. It appears to be cursed.");
304: return FALSE;
305: }
306: if (op == cur_weapon)
307: cur_weapon = NULL;
308: else if (op == cur_armor) {
309: waste_time();
310: cur_armor = NULL;
311: }
312: else if (op == cur_ring[LEFT] || op == cur_ring[RIGHT])
313: toss_ring(op);
314: return TRUE;
315: }
316:
317:
318: /*
319: * new_thing:
320: * Return a new thing
321: */
322: struct linked_list *
323: new_thing(bool treas, int type, int which)
324: {
325: struct linked_list *item;
326: struct magic_item *mi;
327: struct object *cur;
328: int chance, whi;
329:
330: item = new_item(sizeof *cur);
331: cur = OBJPTR(item);
332: basic_init(cur);
333: if (type == DONTCARE) {
334: if (++no_food > 4 && !treas)
335: whi = TYP_FOOD;
336: else
337: whi = pick_one(things);
338: }
339: else {
340: whi = getindex(type);
341: }
342: mi = thnginfo[whi].mf_magic;
343: if (which == DONTCARE) {
344: which = 0;
345: if (mi != NULL)
346: which = pick_one(mi);
347: }
348: cur->o_typname = things[whi].mi_name;
349: cur->o_weight = things[whi].mi_wght;
350: switch (whi) {
351: case TYP_AMULET:
352: cur->o_type = AMULET;
353: cur->o_hplus = 500;
354: strcpy(cur->o_hurldmg,"80d8"); /* if thrown, WOW!!! */
355: cur->o_vol = itemvol(cur);
356: when TYP_POTION:
357: cur->o_type = POTION;
358: cur->o_which = which;
359: cur->o_count += extras();
360: cur->o_vol = itemvol(cur);
361: when TYP_SCROLL:
362: cur->o_type = SCROLL;
363: cur->o_which = which;
364: cur->o_count += extras();
365: cur->o_vol = itemvol(cur);
366: when TYP_FOOD:
367: no_food = 0;
368: initfood(cur);
369: when TYP_WEAPON:
370: cur->o_which = which;
371: init_weapon(cur, which);
372: if ((chance = rnd(100)) < 10) {
373: setoflg(cur,ISCURSED);
374: cur->o_hplus -= rnd(3)+1;
375: cur->o_dplus -= rnd(3)+1;
376: }
377: else if (chance < 15) {
378: cur->o_hplus += rnd(3)+1;
379: cur->o_dplus += rnd(3)+1;
380: }
381: when TYP_ARMOR:
382: cur->o_which = which;
383: initarmor(cur, which);
384: if ((chance = rnd(100)) < 20) {
385: setoflg(cur,ISCURSED);
386: cur->o_ac += rnd(3)+1;
387: }
388: else if (chance < 30)
389: cur->o_ac -= rnd(3)+1;
390: when TYP_RING:
391: cur->o_which = which;
392: init_ring(cur, FALSE);
393: when TYP_STICK:
394: default:
395: cur->o_which = which;
396: fix_stick(cur);
397: }
398: return item;
399: }
400:
401: /*
402: * basic_init:
403: * Set all params of an object to the basic values.
404: */
405: void
406: basic_init(struct object *cur)
407: {
408: cur->o_ac = 11;
409: cur->o_count = 1;
410: cur->o_launch = 0;
411: cur->o_typname = NULL;
412: cur->o_group = newgrp();
413: cur->o_weight = cur->o_vol = 0;
414: cur->o_hplus = cur->o_dplus = 0;
415: strcpy(cur->o_damage,"0d0");
416: strcpy(cur->o_hurldmg,"0d0");
417: cur->o_flags = cur->o_type = cur->o_which = 0;
418: }
419:
420: /*
421: * extras:
422: * Return the number of extra items to be created
423: */
424: int
425: extras(void)
426: {
427: reg int i;
428:
429: i = rnd(100);
430: if (i < 4) /* 4% for 2 more */
431: return 2;
432: else if (i < 11) /* 7% for 1 more */
433: return 1;
434: else /* otherwise no more */
435: return 0;
436: }
437:
438:
439: /*
440: * pick_one:
441: * Pick an item out of a list of nitems possible magic items
442: */
443: int
444: pick_one(struct magic_item *mag)
445: {
446: reg struct magic_item *start;
447: reg int i;
448:
449: start = mag;
450: for (i = rnd(1000); mag->mi_name != NULL; mag++) {
451: if (i < mag->mi_prob)
452: break;
453: if (mag->mi_name == NULL) {
454: if (author() || wizard) {
455: for (mag = start; mag->mi_name != NULL; mag++)
456: msg("%s: %d%%", mag->mi_name, mag->mi_prob);
457: }
458: mag = start;
459: }
460: }
461: return mag - start;
462: }
CVSweb