Fandom

Wikihack

Source:Attrib.c

2,034pages on
this wiki
Add New Page
Talk0

Ad blocker interference detected!


Wikia is a free-to-use site that makes money from advertising. We have a modified experience for viewers using ad blockers

Wikia is not accessible if you’ve made further modifications. Remove the custom ad blocker rule(s) and the page will load as expected.

Below is the full text to src/attrib.c from NetHack 3.4.3. To link to a particular line, write [[attrib.c#line123]], for example.

Top of file Edit

1.    /*	SCCS Id: @(#)attrib.c	3.4	2002/10/07	*/
2.    /*	Copyright 1988, 1989, 1990, 1992, M. Stephenson		  */
3.    /* NetHack may be freely redistributed.  See license for details. */
4.    
The NetHack General Public License applies to screenshots, source code and other content from NetHack.
5.    /*  attribute modification routines. */
6.    
7.    #include "hack.h"
8.    
9.    /* #define DEBUG */	/* uncomment for debugging info */
10.   
11.   #ifdef OVLB
12.   
13.   	/* part of the output on gain or loss of attribute */
14.   static
15.   const char	* const plusattr[] = {
16.   	"strong", "smart", "wise", "agile", "tough", "charismatic"
17.   },
18.   		* const minusattr[] = {
19.   	"weak", "stupid", "foolish", "clumsy", "fragile", "repulsive"
20.   };
21.   
22.   

innate Edit

23.   static
24.   const struct innate {
25.   	schar	ulevel;
26.   	long	*ability;
27.   	const char *gainstr, *losestr;
28.   }	arc_abil[] = { {	 1, &(HStealth), "", "" },
29.   		     {   1, &(HFast), "", "" },
30.   		     {  10, &(HSearching), "perceptive", "" },
31.   		     {	 0, 0, 0, 0 } },
32.   
33.   	bar_abil[] = { {	 1, &(HPoison_resistance), "", "" },
34.   		     {   7, &(HFast), "quick", "slow" },
35.   		     {  15, &(HStealth), "stealthy", "" },
36.   		     {	 0, 0, 0, 0 } },
37.   
38.   	cav_abil[] = { {	 7, &(HFast), "quick", "slow" },
39.   		     {	15, &(HWarning), "sensitive", "" },
40.   		     {	 0, 0, 0, 0 } },
41.   
42.   	hea_abil[] = { {	 1, &(HPoison_resistance), "", "" },
43.   		     {	15, &(HWarning), "sensitive", "" },
44.   		     {	 0, 0, 0, 0 } },
45.   
46.   	kni_abil[] = { {	 7, &(HFast), "quick", "slow" },
47.   		     {	 0, 0, 0, 0 } },
48.   
49.   	mon_abil[] = { {   1, &(HFast), "", "" },
50.   		     {   1, &(HSleep_resistance), "", "" },
51.   		     {   1, &(HSee_invisible), "", "" },
52.   		     {   3, &(HPoison_resistance), "healthy", "" },
53.   		     {   5, &(HStealth), "stealthy", "" },
54.   		     {   7, &(HWarning), "sensitive", "" },
55.   		     {   9, &(HSearching), "perceptive", "unaware" },
56.   		     {  11, &(HFire_resistance), "cool", "warmer" },
57.   		     {  13, &(HCold_resistance), "warm", "cooler" },
58.   		     {  15, &(HShock_resistance), "insulated", "conductive" },
59.   		     {  17, &(HTeleport_control), "controlled","uncontrolled" },
60.   		     {   0, 0, 0, 0 } },
61.   
62.   	pri_abil[] = { {	15, &(HWarning), "sensitive", "" },
63.   		     {  20, &(HFire_resistance), "cool", "warmer" },
64.   		     {	 0, 0, 0, 0 } },
65.   
66.   	ran_abil[] = { {   1, &(HSearching), "", "" },
67.   		     {	 7, &(HStealth), "stealthy", "" },
68.   		     {	15, &(HSee_invisible), "", "" },
69.   		     {	 0, 0, 0, 0 } },
70.   
71.   	rog_abil[] = { {	 1, &(HStealth), "", ""  },
72.   		     {  10, &(HSearching), "perceptive", "" },
73.   		     {	 0, 0, 0, 0 } },
74.   
75.   	sam_abil[] = { {	 1, &(HFast), "", "" },
76.   		     {  15, &(HStealth), "stealthy", "" },
77.   		     {	 0, 0, 0, 0 } },
78.   
79.   	tou_abil[] = { {	10, &(HSearching), "perceptive", "" },
80.   		     {	20, &(HPoison_resistance), "hardy", "" },
81.   		     {	 0, 0, 0, 0 } },
82.   
83.   	val_abil[] = { {	 1, &(HCold_resistance), "", "" },
84.   		     {	 1, &(HStealth), "", "" },
85.   		     {   7, &(HFast), "quick", "slow" },
86.   		     {	 0, 0, 0, 0 } },
87.   
88.   	wiz_abil[] = { {	15, &(HWarning), "sensitive", "" },
89.   		     {  17, &(HTeleport_control), "controlled","uncontrolled" },
90.   		     {	 0, 0, 0, 0 } },
91.   
92.   	/* Intrinsics conferred by race */
93.   	elf_abil[] = { {	4, &(HSleep_resistance), "awake", "tired" },
94.   		     {	 0, 0, 0, 0 } },
95.   
96.   	orc_abil[] = { {	1, &(HPoison_resistance), "", "" },
97.   		     {	 0, 0, 0, 0 } };
98.   
99.   static long next_check = 600L;	/* arbitrary first setting */
100.  STATIC_DCL void NDECL(exerper);
101.  STATIC_DCL void FDECL(postadjabil, (long *));
102.  

adjattrib Edit

103.  /* adjust an attribute; return TRUE if change is made, FALSE otherwise */
104.  boolean
105.  adjattrib(ndx, incr, msgflg)
106.  	int	ndx, incr;
107.  	int	msgflg;	    /* positive => no message, zero => message, and */
108.  {			    /* negative => conditional (msg if change made) */
109.  	if (Fixed_abil || !incr) return FALSE;
110.  
111.  	if ((ndx == A_INT || ndx == A_WIS)
112.  				&& uarmh && uarmh->otyp == DUNCE_CAP) {
113.  		if (msgflg == 0)
114.  		    Your("cap constricts briefly, then relaxes again.");
115.  		return FALSE;
116.  	}
117.  
118.  	if (incr > 0) {
119.  	    if ((AMAX(ndx) >= ATTRMAX(ndx)) && (ACURR(ndx) >= AMAX(ndx))) {
120.  		if (msgflg == 0 && flags.verbose)
121.  		    pline("You're already as %s as you can get.",
122.  			  plusattr[ndx]);
123.  		ABASE(ndx) = AMAX(ndx) = ATTRMAX(ndx); /* just in case */
124.  		return FALSE;
125.  	    }
126.  
127.  	    ABASE(ndx) += incr;
128.  	    if(ABASE(ndx) > AMAX(ndx)) {
129.  		incr = ABASE(ndx) - AMAX(ndx);
130.  		AMAX(ndx) += incr;
131.  		if(AMAX(ndx) > ATTRMAX(ndx))
132.  		    AMAX(ndx) = ATTRMAX(ndx);
133.  		ABASE(ndx) = AMAX(ndx);
134.  	    }
135.  	} else {
136.  	    if (ABASE(ndx) <= ATTRMIN(ndx)) {
137.  		if (msgflg == 0 && flags.verbose)
138.  		    pline("You're already as %s as you can get.",
139.  			  minusattr[ndx]);
140.  		ABASE(ndx) = ATTRMIN(ndx); /* just in case */
141.  		return FALSE;
142.  	    }
143.  
144.  	    ABASE(ndx) += incr;
145.  	    if(ABASE(ndx) < ATTRMIN(ndx)) {
146.  		incr = ABASE(ndx) - ATTRMIN(ndx);
147.  		ABASE(ndx) = ATTRMIN(ndx);
148.  		AMAX(ndx) += incr;
149.  		if(AMAX(ndx) < ATTRMIN(ndx))
150.  		    AMAX(ndx) = ATTRMIN(ndx);
151.  	    }
152.  	}
153.  	if (msgflg <= 0)
154.  	    You_feel("%s%s!",
155.  		  (incr > 1 || incr < -1) ? "very ": "",
156.  		  (incr > 0) ? plusattr[ndx] : minusattr[ndx]);
157.  	flags.botl = 1;
158.  	if (moves > 1 && (ndx == A_STR || ndx == A_CON))
159.  		(void)encumber_msg();
160.  	return TRUE;
161.  }
162.  

gainstr Edit

163.  void
164.  gainstr(otmp, incr)
165.  	register struct obj *otmp;
166.  	register int incr;
167.  {
168.  	int num = 1;
169.  
170.  	if(incr) num = incr;
171.  	else {
172.  	    if(ABASE(A_STR) < 18) num = (rn2(4) ? 1 : rnd(6) );
173.  	    else if (ABASE(A_STR) < STR18(85)) num = rnd(10);
174.  	}
175.  	(void) adjattrib(A_STR, (otmp && otmp->cursed) ? -num : num, TRUE);
176.  }
177.  

losestr Edit

178.  void
179.  losestr(num)	/* may kill you; cause may be poison or monster like 'a' */
180.  	register int num;
181.  {
182.  	int ustr = ABASE(A_STR) - num;
183.  
184.  	while(ustr < 3) {
185.  	    ++ustr;
186.  	    --num;
187.  	    if (Upolyd) {
188.  		u.mh -= 6;
189.  		u.mhmax -= 6;
190.  	    } else {
191.  		u.uhp -= 6;
192.  		u.uhpmax -= 6;
193.  	    }
194.  	}
195.  	(void) adjattrib(A_STR, -num, TRUE);
196.  }
197.  

change_luck Edit

198.  void
199.  change_luck(n)
200.  	register schar n;
201.  {
202.  	u.uluck += n;
203.  	if (u.uluck < 0 && u.uluck < LUCKMIN)	u.uluck = LUCKMIN;
204.  	if (u.uluck > 0 && u.uluck > LUCKMAX)	u.uluck = LUCKMAX;
205.  }
206.  

stone_luck Edit

207.  int
208.  stone_luck(parameter)
209.  boolean parameter; /* So I can't think up of a good name.  So sue me. --KAA */
210.  {
211.  	register struct obj *otmp;
212.  	register long bonchance = 0;
213.  
214.  	for (otmp = invent; otmp; otmp = otmp->nobj)
215.  	    if (confers_luck(otmp)) {
216.  		if (otmp->cursed) bonchance -= otmp->quan;
217.  		else if (otmp->blessed) bonchance += otmp->quan;
218.  		else if (parameter) bonchance += otmp->quan;
219.  	    }
220.  
221.  	return sgn((int)bonchance);
222.  }
223.  

set_moreluck Edit

224.  /* there has just been an inventory change affecting a luck-granting item */
225.  void
226.  set_moreluck()
227.  {
228.  	int luckbon = stone_luck(TRUE);
229.  
230.  	if (!luckbon && !carrying(LUCKSTONE)) u.moreluck = 0;
231.  	else if (luckbon >= 0) u.moreluck = LUCKADD;
232.  	else u.moreluck = -LUCKADD;
233.  }
234.  
235.  #endif /* OVLB */

restore_attrib Edit

236.  #ifdef OVL1
237.  
238.  void
239.  restore_attrib()
240.  {
241.  	int	i;
242.  
243.  	for(i = 0; i < A_MAX; i++) {	/* all temporary losses/gains */
244.  
245.  	   if(ATEMP(i) && ATIME(i)) {
246.  		if(!(--(ATIME(i)))) { /* countdown for change */
247.  		    ATEMP(i) += ATEMP(i) > 0 ? -1 : 1;
248.  
249.  		    if(ATEMP(i)) /* reset timer */
250.  			ATIME(i) = 100 / ACURR(A_CON);
251.  		}
252.  	    }
253.  	}
254.  	(void)encumber_msg();
255.  }
256.  
257.  #endif /* OVL1 */

exercise Edit

258.  #ifdef OVLB
259.  
260.  #define AVAL	50		/* tune value for exercise gains */
261.  
262.  void
263.  exercise(i, inc_or_dec)
264.  int	i;
265.  boolean	inc_or_dec;
266.  {
267.  #ifdef DEBUG
268.  	pline("Exercise:");
269.  #endif
270.  	if (i == A_INT || i == A_CHA) return;	/* can't exercise these */
271.  
272.  	/* no physical exercise while polymorphed; the body's temporary */
273.  	if (Upolyd && i != A_WIS) return;
274.  
275.  	if(abs(AEXE(i)) < AVAL) {
276.  		/*
277.  		 *	Law of diminishing returns (Part I):
278.  		 *
279.  		 *	Gain is harder at higher attribute values.
280.  		 *	79% at "3" --> 0% at "18"
281.  		 *	Loss is even at all levels (50%).
282.  		 *
283.  		 *	Note: *YES* ACURR is the right one to use.
284.  		 */
285.  		AEXE(i) += (inc_or_dec) ? (rn2(19) > ACURR(i)) : -rn2(2);
286.  #ifdef DEBUG
287.  		pline("%s, %s AEXE = %d",
288.  			(i == A_STR) ? "Str" : (i == A_WIS) ? "Wis" :
289.  			(i == A_DEX) ? "Dex" : "Con",
290.  			(inc_or_dec) ? "inc" : "dec", AEXE(i));
291.  #endif
292.  	}
293.  	if (moves > 0 && (i == A_STR || i == A_CON)) (void)encumber_msg();
294.  }
295.  

exercise() is called whenever one of Hero's attributes is being exercised. This means there's a change that attribute will go up or down. Takes two parameters, first is the attribute to exercise (A_STR, A_WIS, A_DEX or A_CON) and the second is TRUE if it should go up or FALSE if down.

exerper Edit

296.  /* hunger values - from eat.c */
297.  #define SATIATED	0
298.  #define NOT_HUNGRY	1
299.  #define HUNGRY		2
300.  #define WEAK		3
301.  #define FAINTING	4
302.  #define FAINTED		5
303.  #define STARVED		6
304.  
305.  STATIC_OVL void
306.  exerper()
307.  {
308.  	if(!(moves % 10)) {
309.  		/* Hunger Checks */
310.  
311.  		int hs = (u.uhunger > 1000) ? SATIATED :
312.  			 (u.uhunger > 150) ? NOT_HUNGRY :
313.  			 (u.uhunger > 50) ? HUNGRY :
314.  			 (u.uhunger > 0) ? WEAK : FAINTING;
315.  
316.  #ifdef DEBUG
317.  		pline("exerper: Hunger checks");
318.  #endif
319.  		switch (hs) {
320.  		    case SATIATED:	exercise(A_DEX, FALSE);
321.  					if (Role_if(PM_MONK))
322.  					    exercise(A_WIS, FALSE);
323.  					break;
324.  		    case NOT_HUNGRY:	exercise(A_CON, TRUE); break;
325.  		    case WEAK:		exercise(A_STR, FALSE);
326.  					if (Role_if(PM_MONK))	/* fasting */
327.  					    exercise(A_WIS, TRUE);
328.  					break;
329.  		    case FAINTING:
330.  		    case FAINTED:	exercise(A_CON, FALSE); break;
331.  		}
332.  
333.  		/* Encumberance Checks */
334.  #ifdef DEBUG
335.  		pline("exerper: Encumber checks");
336.  #endif
337.  		switch (near_capacity()) {
338.  		    case MOD_ENCUMBER:	exercise(A_STR, TRUE); break;
339.  		    case HVY_ENCUMBER:	exercise(A_STR, TRUE);
340.  					exercise(A_DEX, FALSE); break;
341.  		    case EXT_ENCUMBER:	exercise(A_DEX, FALSE);
342.  					exercise(A_CON, FALSE); break;
343.  		}
344.  
345.  	}
346.  
347.  	/* status checks */
348.  	if(!(moves % 5)) {
349.  #ifdef DEBUG
350.  		pline("exerper: Status checks");
351.  #endif
352.  		if ((HClairvoyant & (INTRINSIC|TIMEOUT)) &&
353.  			!BClairvoyant)                      exercise(A_WIS, TRUE);
354.  		if (HRegeneration)			exercise(A_STR, TRUE);
355.  
356.  		if(Sick || Vomiting)     exercise(A_CON, FALSE);
357.  		if(Confusion || Hallucination)		exercise(A_WIS, FALSE);
358.  		if((Wounded_legs 
359.  #ifdef STEED
360.  		    && !u.usteed
361.  #endif
362.  			    ) || Fumbling || HStun)	exercise(A_DEX, FALSE);
363.  	}
364.  }
365.  

exerchk Edit

366.  void
367.  exerchk()
368.  {
369.  	int	i, mod_val;
370.  
371.  	/*	Check out the periodic accumulations */
372.  	exerper();
373.  
374.  #ifdef DEBUG
375.  	if(moves >= next_check)
376.  		pline("exerchk: ready to test. multi = %d.", multi);
377.  #endif
378.  	/*	Are we ready for a test?	*/
379.  	if(moves >= next_check && !multi) {
380.  #ifdef DEBUG
381.  	    pline("exerchk: testing.");
382.  #endif
383.  	    /*
384.  	     *	Law of diminishing returns (Part II):
385.  	     *
386.  	     *	The effects of "exercise" and "abuse" wear
387.  	     *	off over time.  Even if you *don't* get an
388.  	     *	increase/decrease, you lose some of the
389.  	     *	accumulated effects.
390.  	     */
391.  	    for(i = 0; i < A_MAX; AEXE(i++) /= 2) {
392.  
393.  		if(ABASE(i) >= 18 || !AEXE(i)) continue;
394.  		if(i == A_INT || i == A_CHA) continue;/* can't exercise these */
395.  
396.  #ifdef DEBUG
397.  		pline("exerchk: testing %s (%d).",
398.  			(i == A_STR) ? "Str" : (i == A_WIS) ? "Wis" :
399.  			(i == A_DEX) ? "Dex" : "Con", AEXE(i));
400.  #endif
401.  		/*
402.  		 *	Law of diminishing returns (Part III):
403.  		 *
404.  		 *	You don't *always* gain by exercising.
405.  		 *	[MRS 92/10/28 - Treat Wisdom specially for balance.]
406.  		 */
407.  		if(rn2(AVAL) > ((i != A_WIS) ? abs(AEXE(i)*2/3) : abs(AEXE(i))))
408.  		    continue;
409.  		mod_val = sgn(AEXE(i));
410.  
411.  #ifdef DEBUG
412.  		pline("exerchk: changing %d.", i);
413.  #endif
414.  		if(adjattrib(i, mod_val, -1)) {
415.  #ifdef DEBUG
416.  		    pline("exerchk: changed %d.", i);
417.  #endif
418.  		    /* if you actually changed an attrib - zero accumulation */
419.  		    AEXE(i) = 0;
420.  		    /* then print an explanation */
421.  		    switch(i) {
422.  		    case A_STR: You((mod_val >0) ?
423.  				    "must have been exercising." :
424.  				    "must have been abusing your body.");
425.  				break;
426.  		    case A_WIS: You((mod_val >0) ?
427.  				    "must have been very observant." :
428.  				    "haven't been paying attention.");
429.  				break;
430.  		    case A_DEX: You((mod_val >0) ?
431.  				    "must have been working on your reflexes." :
432.  				    "haven't been working on reflexes lately.");
433.  				break;
434.  		    case A_CON: You((mod_val >0) ?
435.  				    "must be leading a healthy life-style." :
436.  				    "haven't been watching your health.");
437.  				break;
438.  		    }
439.  		}
440.  	    }
441.  	    next_check += rn1(200,800);
442.  #ifdef DEBUG
443.  	    pline("exerchk: next check at %ld.", next_check);
444.  #endif
445.  	}
446.  }
447.  

reset_attribute_clock Edit

448.  /* next_check will otherwise have its initial 600L after a game restore */
449.  void
450.  reset_attribute_clock()
451.  {
452.  	if (moves > 600L) next_check = moves + rn1(50,800);
453.  }
454.  
455.  

init_attr Edit

456.  void
457.  init_attr(np)
458.  	register int	np;
459.  {
460.  	register int	i, x, tryct;
461.  
462.  
463.  	for(i = 0; i < A_MAX; i++) {
464.  	    ABASE(i) = AMAX(i) = urole.attrbase[i];
465.  	    ATEMP(i) = ATIME(i) = 0;
466.  	    np -= urole.attrbase[i];
467.  	}
468.  
469.  	tryct = 0;
470.  	while(np > 0 && tryct < 100) {
471.  
472.  	    x = rn2(100);
473.  	    for (i = 0; (i < A_MAX) && ((x -= urole.attrdist[i]) > 0); i++) ;
474.  	    if(i >= A_MAX) continue; /* impossible */
475.  
476.  	    if(ABASE(i) >= ATTRMAX(i)) {
477.  
478.  		tryct++;
479.  		continue;
480.  	    }
481.  	    tryct = 0;
482.  	    ABASE(i)++;
483.  	    AMAX(i)++;
484.  	    np--;
485.  	}
486.  
487.  	tryct = 0;
488.  	while(np < 0 && tryct < 100) {		/* for redistribution */
489.  
490.  	    x = rn2(100);
491.  	    for (i = 0; (i < A_MAX) && ((x -= urole.attrdist[i]) > 0); i++) ;
492.  	    if(i >= A_MAX) continue; /* impossible */
493.  
494.  	    if(ABASE(i) <= ATTRMIN(i)) {
495.  
496.  		tryct++;
497.  		continue;
498.  	    }
499.  	    tryct = 0;
500.  	    ABASE(i)--;
501.  	    AMAX(i)--;
502.  	    np++;
503.  	}
504.  }
505.  

redist_attr Edit

506.  void
507.  redist_attr()
508.  {
509.  	register int i, tmp;
510.  
511.  	for(i = 0; i < A_MAX; i++) {
512.  	    if (i==A_INT || i==A_WIS) continue;
513.  		/* Polymorphing doesn't change your mind */
514.  	    tmp = AMAX(i);
515.  	    AMAX(i) += (rn2(5)-2);
516.  	    if (AMAX(i) > ATTRMAX(i)) AMAX(i) = ATTRMAX(i);
517.  	    if (AMAX(i) < ATTRMIN(i)) AMAX(i) = ATTRMIN(i);
518.  	    ABASE(i) = ABASE(i) * AMAX(i) / tmp;
519.  	    /* ABASE(i) > ATTRMAX(i) is impossible */
520.  	    if (ABASE(i) < ATTRMIN(i)) ABASE(i) = ATTRMIN(i);
521.  	}
522.  	(void)encumber_msg();
523.  }
524.  

postadjabil Edit

525.  STATIC_OVL
526.  void
527.  postadjabil(ability)
528.  long *ability;
529.  {
530.  	if (!ability) return;
531.  	if (ability == &(HWarning) || ability == &(HSee_invisible))
532.  		see_monsters();
533.  }
534.  

adjabil Edit

535.  void
536.  adjabil(oldlevel,newlevel)
537.  int oldlevel, newlevel;
538.  {
539.  	register const struct innate *abil, *rabil;
540.  	long mask = FROMEXPER;
541.  
542.  
543.  	switch (Role_switch) {
544.  	case PM_ARCHEOLOGIST:   abil = arc_abil;	break;
545.  	case PM_BARBARIAN:      abil = bar_abil;	break;
546.  	case PM_CAVEMAN:        abil = cav_abil;	break;
547.  	case PM_HEALER:         abil = hea_abil;	break;
548.  	case PM_KNIGHT:         abil = kni_abil;	break;
549.  	case PM_MONK:           abil = mon_abil;	break;
550.  	case PM_PRIEST:         abil = pri_abil;	break;
551.  	case PM_RANGER:         abil = ran_abil;	break;
552.  	case PM_ROGUE:          abil = rog_abil;	break;
553.  	case PM_SAMURAI:        abil = sam_abil;	break;
554.  #ifdef TOURIST
555.  	case PM_TOURIST:        abil = tou_abil;	break;
556.  #endif
557.  	case PM_VALKYRIE:       abil = val_abil;	break;
558.  	case PM_WIZARD:         abil = wiz_abil;	break;
559.  	default:                abil = 0;		break;
560.  	}
561.  
562.  	switch (Race_switch) {
563.  	case PM_ELF:            rabil = elf_abil;	break;
564.  	case PM_ORC:            rabil = orc_abil;	break;
565.  	case PM_HUMAN:
566.  	case PM_DWARF:
567.  	case PM_GNOME:
568.  	default:                rabil = 0;		break;
569.  	}
570.  
571.  	while (abil || rabil) {
572.  	    long prevabil;
573.  	    /* Have we finished with the intrinsics list? */
574.  	    if (!abil || !abil->ability) {
575.  	    	/* Try the race intrinsics */
576.  	    	if (!rabil || !rabil->ability) break;
577.  	    	abil = rabil;
578.  	    	rabil = 0;
579.  	    	mask = FROMRACE;
580.  	    }
581.  		prevabil = *(abil->ability);
582.  		if(oldlevel < abil->ulevel && newlevel >= abil->ulevel) {
583.  			/* Abilities gained at level 1 can never be lost
584.  			 * via level loss, only via means that remove _any_
585.  			 * sort of ability.  A "gain" of such an ability from
586.  			 * an outside source is devoid of meaning, so we set
587.  			 * FROMOUTSIDE to avoid such gains.
588.  			 */
589.  			if (abil->ulevel == 1)
590.  				*(abil->ability) |= (mask|FROMOUTSIDE);
591.  			else
592.  				*(abil->ability) |= mask;
593.  			if(!(*(abil->ability) & INTRINSIC & ~mask)) {
594.  			    if(*(abil->gainstr))
595.  				You_feel("%s!", abil->gainstr);
596.  			}
597.  		} else if (oldlevel >= abil->ulevel && newlevel < abil->ulevel) {
598.  			*(abil->ability) &= ~mask;
599.  			if(!(*(abil->ability) & INTRINSIC)) {
600.  			    if(*(abil->losestr))
601.  				You_feel("%s!", abil->losestr);
602.  			    else if(*(abil->gainstr))
603.  				You_feel("less %s!", abil->gainstr);
604.  			}
605.  		}
606.  	    if (prevabil != *(abil->ability))	/* it changed */
607.  		postadjabil(abil->ability);
608.  	    abil++;
609.  	}
610.  
611.  	if (oldlevel > 0) {
612.  	    if (newlevel > oldlevel)
613.  		add_weapon_skill(newlevel - oldlevel);
614.  	    else
615.  		lose_weapon_skill(oldlevel - newlevel);
616.  	}
617.  }
618.  
619.  

newhp Edit

620.  int
621.  newhp()
622.  {
623.  	int	hp, conplus;
624.  
625.  
626.  	if (u.ulevel == 0) {
627.  	    /* Initialize hit points */
628.  	    hp = urole.hpadv.infix + urace.hpadv.infix;
629.  	    if (urole.hpadv.inrnd > 0) hp += rnd(urole.hpadv.inrnd);
630.  	    if (urace.hpadv.inrnd > 0) hp += rnd(urace.hpadv.inrnd);
631.  
632.  	    /* Initialize alignment stuff */
633.  	    u.ualign.type = aligns[flags.initalign].value;
634.  	    u.ualign.record = urole.initrecord;
635.  
636.  		return hp;
637.  	} else {
638.  	    if (u.ulevel < urole.xlev) {
639.  	    	hp = urole.hpadv.lofix + urace.hpadv.lofix;
640.  	    	if (urole.hpadv.lornd > 0) hp += rnd(urole.hpadv.lornd);
641.  	    	if (urace.hpadv.lornd > 0) hp += rnd(urace.hpadv.lornd);
642.  	    } else {
643.  	    	hp = urole.hpadv.hifix + urace.hpadv.hifix;
644.  	    	if (urole.hpadv.hirnd > 0) hp += rnd(urole.hpadv.hirnd);
645.  	    	if (urace.hpadv.hirnd > 0) hp += rnd(urace.hpadv.hirnd);
646.  	    }
647.  	}
648.  
649.  	if (ACURR(A_CON) <= 3) conplus = -2;
650.  	else if (ACURR(A_CON) <= 6) conplus = -1;
651.  	else if (ACURR(A_CON) <= 14) conplus = 0;
652.  	else if (ACURR(A_CON) <= 16) conplus = 1;
653.  	else if (ACURR(A_CON) == 17) conplus = 2;
654.  	else if (ACURR(A_CON) == 18) conplus = 3;
655.  	else conplus = 4;
656.  	
657.  	hp += conplus;
658.  	return((hp <= 0) ? 1 : hp);
659.  }
660.  
661.  #endif /* OVLB */

acurr Edit

662.  #ifdef OVL0
663.  
664.  schar
665.  acurr(x)
666.  int x;
667.  {
668.  	register int tmp = (u.abon.a[x] + u.atemp.a[x] + u.acurr.a[x]);
669.  
670.  	if (x == A_STR) {
671.  		if (uarmg && uarmg->otyp == GAUNTLETS_OF_POWER) return(125);
672.  #ifdef WIN32_BUG
673.  		else return(x=((tmp >= 125) ? 125 : (tmp <= 3) ? 3 : tmp));
674.  #else
675.  		else return((schar)((tmp >= 125) ? 125 : (tmp <= 3) ? 3 : tmp));
676.  #endif
677.  	} else if (x == A_CHA) {
678.  		if (tmp < 18 && (youmonst.data->mlet == S_NYMPH ||
679.  		    u.umonnum==PM_SUCCUBUS || u.umonnum == PM_INCUBUS))
680.  		    return 18;
681.  	} else if (x == A_INT || x == A_WIS) {
682.  		/* yes, this may raise int/wis if player is sufficiently
683.  		 * stupid.  there are lower levels of cognition than "dunce".
684.  		 */
685.  		if (uarmh && uarmh->otyp == DUNCE_CAP) return(6);
686.  	}
687.  #ifdef WIN32_BUG
688.  	return(x=((tmp >= 25) ? 25 : (tmp <= 3) ? 3 : tmp));
689.  #else
690.  	return((schar)((tmp >= 25) ? 25 : (tmp <= 3) ? 3 : tmp));
691.  #endif
692.  }
693.  

acurrstr Edit

694.  /* condense clumsy ACURR(A_STR) value into value that fits into game formulas
695.   */
696.  schar
697.  acurrstr()
698.  {
699.  	register int str = ACURR(A_STR);
700.  
701.  	if (str <= 18) return((schar)str);
702.  	if (str <= 121) return((schar)(19 + str / 50)); /* map to 19-21 */
703.  	else return((schar)(str - 100));
704.  }
705.  
706.  #endif /* OVL0 */

adjalign Edit

707.  #ifdef OVL2
708.  
709.  /* avoid possible problems with alignment overflow, and provide a centralized
710.   * location for any future alignment limits
711.   */
712.  void
713.  adjalign(n)
714.  register int n;
715.  {
716.  	register int newalign = u.ualign.record + n;
717.  
718.  	if(n < 0) {
719.  		if(newalign < u.ualign.record)
720.  			u.ualign.record = newalign;
721.  	} else
722.  		if(newalign > u.ualign.record) {
723.  			u.ualign.record = newalign;
724.  			if(u.ualign.record > ALIGNLIM)
725.  				u.ualign.record = ALIGNLIM;
726.  		}
727.  }
728.  
729.  #endif /* OVL2 */
730.  
731.  /*attrib.c*/

Also on Fandom

Random Wiki