- [+] press ] then \ - CRASH.
- [+] if sound is behind walls: - [+] you hear a muffled explosion - [+] int canhear() needs one more optional argument: &numwallspassed - [+] if supplied, fill it in. - [+] in noise(), check numwallspassed. if there were any, then say 'muffled'. or maybe if more than 2? play around with this. - [+] listen skill should also give more info about NON monster sounds - [+] ie. direction, distance. - [+] set user->changinglev when CHECKING stairs in the same way as when we use them. - [+] monk abil - iron fist - use all remaining stamina as damage + knockback * [+] HITCONFER - this should only work if you were attacked through a BITE or CLAW etc. - [+] bug... werewolves etc not attacking properly after shapehifting - [+] some tech/tools should be usable with hands (ie. watch). f_operwithouthands - [+] werewolves sohuld keep f_hitconfer after shapeshifting - [+] done - [+] summoned creatures from ai should never attack their masters!!! - [+] only the PLAYER can be infected by a werewolf? or only HUMANS ? - [+] when a werewolf changes to animal form, no longer hide true race as 'human' - [+] lycanthropy? - [+] how to get it: - [+] drink were-xxx blood (->potion of lycanthropy, never appears randomly) - [+] bitten by a lycanthrope (chance) with hitconfer and fail a con check - [+] change f_lycanthrope so text = racename. - [+] effects when you get it: - [+] right away, add diseased with lycanthropy. incubatino infinite ? - [+] if you are incubating lycanthropy, you always change at the full moon (and get rage, and lose control). - [+] at this point, complete the incubation and... - [+] add f_hatesall - [+] lose control for a while - [+] after you change back the first time, you can change at will. (but there is a risk each time of losing control) - [+] player regains control - [+] remove aicontrolled, hatesall, rage - [+] actually add f_lycanthrope, text=xxx, v0=4 - [+] when f_lycanthrope v0 drops to 0 or less... - [+] canwill shapeshift with race:xxx - [+] how to remove it - [+] remove curse scroll - [+] drink holy water - [+] these will: - [+] cure any incubating curse - [+] cure any f_poisoned curse - [+] cure lycanthropy, and any flags FROMLYCANTHROPY - [+] other effect - [+] wont/cant walk into holy circle? - [+] holy circle hurts you - [+] shouldn't be able to get critical hits on you (ie. injuries) if you ahve heavenly armour - [+] bug in f_poisoned text. i think i've fixed this now. Died on level 2 of the dungeon. Killed by venom poisoning from 5-10 - [+] donated objects count towards xp! - [+] -50% of value if not known. - [+] -25% of value if not id'd - [+] donating objects will anger felix
This commit is contained in:
parent
e5c6d8b094
commit
af3116f6d4
21
ai.c
21
ai.c
|
@ -199,8 +199,11 @@ enum OBTYPE aigetattackspell(lifeform_t *lf, lifeform_t *victim) {
|
|||
if (ok) {
|
||||
// lycanthropes always change to animal form at midnight.
|
||||
if (gettimephase() == TP_MIDNIGHT) {
|
||||
flag_t *lyf;
|
||||
|
||||
lyf = lfhasflag(lf, F_LYCANTHROPE);
|
||||
if ((f->val[0] == OT_S_SHAPESHIFT) &&
|
||||
lfhasflag(lf, F_LYCANTHROPE)) {
|
||||
lyf && (lyf->val[0] != 0)) {
|
||||
if (ispolymorphed(lf)) {
|
||||
// never change to human form.
|
||||
ok = B_FALSE;
|
||||
|
@ -1775,6 +1778,7 @@ int aimovetolf(lifeform_t *lf, lifeform_t *target, int wantattack) {
|
|||
}
|
||||
|
||||
if (!movetowards(lf, target->cell, DT_ORTH, B_FALSE)) {
|
||||
dblog(".oO { successfully moved towards target. }");
|
||||
turntoface(lf, target->cell);
|
||||
// success
|
||||
return B_FALSE;
|
||||
|
@ -2615,9 +2619,6 @@ int aispellok(lifeform_t *lf, enum OBTYPE spellid, lifeform_t *victim, enum FLAG
|
|||
specificcheckok = B_FALSE;
|
||||
}
|
||||
}
|
||||
if ((ot->id == OT_S_INVISIBILITY) && lfhasflag(victim, F_INVISIBLE)) {
|
||||
specificcheckok = B_FALSE;
|
||||
}
|
||||
if ((ot->id == OT_S_PAIN) && lfhasflag(victim, F_PAIN)) {
|
||||
specificcheckok = B_FALSE;
|
||||
}
|
||||
|
@ -2627,6 +2628,12 @@ int aispellok(lifeform_t *lf, enum OBTYPE spellid, lifeform_t *victim, enum FLAG
|
|||
if ((ot->id == OT_S_HEALINGMIN) && (lf->hp >= lf->maxhp)) {
|
||||
specificcheckok = B_FALSE;
|
||||
}
|
||||
if ((ot->id == OT_S_INVISIBILITY) && lfhasflag(victim, F_INVISIBLE)) {
|
||||
specificcheckok = B_FALSE;
|
||||
}
|
||||
if ((ot->id == OT_A_IRONFIST) && getweapon(lf)) {
|
||||
specificcheckok = B_FALSE;
|
||||
}
|
||||
if ((ot->id == OT_S_PARALYZE) && lfhasflag(victim, F_PARALYZED)) {
|
||||
specificcheckok = B_FALSE;
|
||||
}
|
||||
|
@ -3126,6 +3133,12 @@ void makewantedoblist(lifeform_t *lf, int *noids, enum OBTYPE *oid, int *oidcove
|
|||
// returns B_FALSE if successful
|
||||
int useitemwithflag(lifeform_t *lf, enum FLAG whichflag) {
|
||||
object_t *o;
|
||||
|
||||
// can't use anything if enraged
|
||||
if (lfhasflag(lf, F_RAGE)) return B_TRUE;
|
||||
// aicontrolled human won't use items
|
||||
if (lfhasflag(lf, F_AICONTROLLED)) return B_TRUE;
|
||||
|
||||
for (o = lf->pack->first ; o ; o = o->next) {
|
||||
if (hasflag(o->flags, whichflag)) {
|
||||
if (aiobok(lf, o, lf)) {
|
||||
|
|
69
attack.c
69
attack.c
|
@ -205,6 +205,15 @@ int attackcell(lifeform_t *lf, cell_t *c, int force) {
|
|||
if (c->lf) {
|
||||
// warnings
|
||||
if (!force && isplayer(lf)) {
|
||||
int h,m,s;
|
||||
splittime(&h,&m,&s);
|
||||
|
||||
if (godprayedto(R_GODLIFE) && (h == 6)) {
|
||||
if (!warnabout("Really attack during Glorana's Peace?")) {
|
||||
return B_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
if (isprone(lf)) {
|
||||
if (!warnabout("Really attack while prone (-4 accuracy)?")) {
|
||||
return B_TRUE;
|
||||
|
@ -463,8 +472,14 @@ int attackcell(lifeform_t *lf, cell_t *c, int force) {
|
|||
if (nweps <= 0) {
|
||||
if (isplayer(lf)) {
|
||||
msg("You cannot attack!");
|
||||
} else if (lfhasflag(lf, F_DEBUG)) {
|
||||
msg("DB: %s cannot attack!",lf->race->name);
|
||||
}
|
||||
if (op) killobpile(op);
|
||||
if (!isplayer(lf)) {
|
||||
// avoid infinite loops
|
||||
taketime(lf, getactspeed(lf));
|
||||
}
|
||||
return B_TRUE;
|
||||
}
|
||||
|
||||
|
@ -639,6 +654,8 @@ int attackcell(lifeform_t *lf, cell_t *c, int force) {
|
|||
if (isplayer(lf) && attacktarget) {
|
||||
if (attacktype == AT_LF) {
|
||||
if (!isgod(attacktarget)) {
|
||||
int h,m,s;
|
||||
splittime(&h,&m,&s);
|
||||
if (attackedfriend) {
|
||||
angergodmaybe(R_GODMERCY, 25, GA_ATTACKALLY);
|
||||
angergodmaybe(R_GODPURITY, 100, GA_ATTACKALLY);
|
||||
|
@ -686,6 +703,9 @@ int attackcell(lifeform_t *lf, cell_t *c, int force) {
|
|||
killflagsofid(lf->flags, F_USEDPOISON);
|
||||
if (isplayer(lf)) god_usepoison_response();
|
||||
}
|
||||
if (godprayedto(R_GODLIFE) && (h == 6)) {
|
||||
angergodmaybe(R_GODLIFE, 30, GA_PEACEHOUR);
|
||||
}
|
||||
}
|
||||
} else if (attacktype == AT_OB) {
|
||||
angergodmaybe(R_GODNATURE, 10, GA_ATTACKOBJECT);
|
||||
|
@ -865,6 +885,9 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
|||
ndam = 0;
|
||||
|
||||
hit = rolltohit(lf, victim, wep, &critical, &fumble);
|
||||
if (lfhasflag(victim, F_HEAVENARM)) {
|
||||
critical = B_FALSE;
|
||||
}
|
||||
|
||||
if (critical && !lfhasflag(lf, F_PHANTASM)) {
|
||||
object_t *armour;
|
||||
|
@ -1397,7 +1420,7 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
|||
if (!isdead(victim) && !blocked && !dodged) {
|
||||
// special weapon effects, as long as you're not doing a heavy blow
|
||||
if (!lfhasflag(lf, F_HEAVYBLOW) && dam[0]) {
|
||||
wepeffects(wep->flags, victim->cell, damflag, dam[0]);
|
||||
wepeffects(wep->flags, victim->cell, damflag, dam[0], isunarmed);
|
||||
}
|
||||
if (isunarmed) {
|
||||
f = lfhasflag(lf, F_FREEZINGTOUCH);
|
||||
|
@ -1423,7 +1446,7 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
|||
|
||||
// confer flags from attacker?
|
||||
if (dam[0]) {
|
||||
wepeffects(lf->flags, victim->cell, damflag, dam[0]);
|
||||
wepeffects(lf->flags, victim->cell, damflag, dam[0], isunarmed);
|
||||
}
|
||||
|
||||
// special lifeform-based effects
|
||||
|
@ -1471,7 +1494,7 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
|||
if (cansee(player, lf) || cansee(player, victim)) {
|
||||
char wepname[BUFLEN];
|
||||
real_getobname(wep, wepname, 1, B_PREMODS, B_NOCONDITION, B_NOBLINDADJUST, B_BLESSINGS, B_NOUSED, B_NOSHOWALL);
|
||||
msg("^%d%s%s %s %s to %s!", getlfcol(lf, CC_BAD),
|
||||
msg("^%c%s%s %s %s to %s!", getlfcol(lf, CC_BAD),
|
||||
attackername, getpossessive(attackername), noprefix(wepname),
|
||||
(wep->amt == 1) ? "sticks" : "stick", victimname);
|
||||
}
|
||||
|
@ -1542,9 +1565,9 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
|||
if (fumble) {
|
||||
if (wep && !isunarmed) {
|
||||
if (isplayer(lf)) {
|
||||
msg("^%dYou fumble your attack!", getlfcol(lf, CC_BAD));
|
||||
msg("^%cYou fumble your attack!", getlfcol(lf, CC_BAD));
|
||||
} else if (cansee(player, lf)) {
|
||||
msg("^%d%s fumbles its attack!", getlfcol(lf, CC_BAD), attackername);
|
||||
msg("^%c%s fumbles its attack!", getlfcol(lf, CC_BAD), attackername);
|
||||
}
|
||||
drop(wep, ALL);
|
||||
wep = NULL;
|
||||
|
@ -1771,7 +1794,7 @@ int attackob(lifeform_t *lf, object_t *o, object_t *wep, flag_t *damflag) {
|
|||
if (!isdeadob(o)) {
|
||||
// special weapon effects, as long as you're not doing a heavy blow
|
||||
if (!lfhasflag(lf, F_HEAVYBLOW) && dam[0]) {
|
||||
wepeffects(wep->flags, obloc, damflag, dam[0]);
|
||||
wepeffects(wep->flags, obloc, damflag, dam[0], isunarmed);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2006,7 +2029,7 @@ int check_for_block(lifeform_t *lf, lifeform_t *victim, int dam, enum DAMTYPE da
|
|||
if (cansee(player, lf) || cansee(player, victim)) {
|
||||
char attname[BUFLEN];
|
||||
getlfname(lf, attname);
|
||||
msg("^%d%s%s %s %s to %s!", getlfcol(victim, CC_BAD),
|
||||
msg("^%c%s%s %s %s to %s!", getlfcol(victim, CC_BAD),
|
||||
victimname, getpossessive(victimname), noprefix(shname),
|
||||
(shield[i]->amt == 1) ? "sticks" : "stick", attname);
|
||||
}
|
||||
|
@ -2073,7 +2096,7 @@ void criticalhit(lifeform_t *lf, lifeform_t *victim, enum BODYPART hitpos, objec
|
|||
} else {
|
||||
strcpy(lfname, "Something");
|
||||
}
|
||||
msg("^%d%s slice%s off %s%s %s!", getlfcol(victim, CC_VBAD),
|
||||
msg("^%c%s slice%s off %s%s %s!", getlfcol(victim, CC_VBAD),
|
||||
lfname, isplayer(lf) ? "" : "s", vname, getpossessive(vname), bpname);
|
||||
}
|
||||
// take extra damage based on number of severable limbs
|
||||
|
@ -2848,7 +2871,7 @@ int rolltohit(lifeform_t *lf, lifeform_t *victim, object_t *wep, int *critical,
|
|||
return gothit;
|
||||
}
|
||||
|
||||
void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam) {
|
||||
void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam, int isunarmed) {
|
||||
flag_t *f;
|
||||
lifeform_t *victim;
|
||||
lifeform_t *owner = NULL;
|
||||
|
@ -2888,6 +2911,12 @@ void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam) {
|
|||
// ie "a poisoned short sword"
|
||||
snprintf(frombuf, BUFLEN, "%s", wepname);
|
||||
}
|
||||
} else {
|
||||
if (owner) {
|
||||
real_getlfname(owner, frombuf, NULL, B_SHOWALL, B_REALRACE);
|
||||
} else {
|
||||
strcpy(frombuf, "something unknown");
|
||||
}
|
||||
}
|
||||
|
||||
getflags(fp, retflag, &nretflags, F_FLAMESTRIKE, F_HEAVYBLOW, F_HITCONFER, F_RACESLAY, F_REVENGE, F_RUSTED, F_NONE);
|
||||
|
@ -2982,6 +3011,14 @@ void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam) {
|
|||
|
||||
fid = f->val[0];
|
||||
ftext = f->text;
|
||||
|
||||
// hitconfer from owner can't be conferred if this was a weapon attack
|
||||
// ie. if something has poisonous claws and hits you with a weapon, you
|
||||
// don't get poisoned.
|
||||
if (fp->owner && !isunarmed) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// the f_poisoned flag stacks, others don't.
|
||||
if (!lfhasflag(victim, fid) || (fid == F_POISONED)) {
|
||||
int passedcheck = B_FALSE;
|
||||
|
@ -3009,6 +3046,7 @@ void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam) {
|
|||
enum POISONTYPE ptype;
|
||||
int ppower;
|
||||
|
||||
assert(valflag);
|
||||
if (valflag) {
|
||||
ptype = valflag->val[0];
|
||||
if (valflag->val[1] == NA) {
|
||||
|
@ -3016,15 +3054,20 @@ void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam) {
|
|||
} else {
|
||||
ppower = valflag->val[1];
|
||||
}
|
||||
} else {
|
||||
// should never happen.
|
||||
ptype = P_VENOM;
|
||||
ppower = 1;
|
||||
}
|
||||
|
||||
if (!wep && strlen(ftext)) {
|
||||
strcpy(frombuf, ftext);
|
||||
} else if (ptype == P_LYCANTHROPY) {
|
||||
char *p;
|
||||
// special case - we need to remember what kind of
|
||||
// creature to change into. since lycanthropy isn't fatal
|
||||
// as such we can use the 'what caused you damage' field for
|
||||
// this information
|
||||
p = readuntil(frombuf, valflag->text, '^');
|
||||
readuntil(frombuf, p, '^');
|
||||
}
|
||||
|
||||
poison(victim, howlong, ptype, ppower, frombuf, owner ? owner->race->id : R_NONE);
|
||||
} else {
|
||||
// flag values
|
||||
|
|
2
attack.h
2
attack.h
|
@ -30,4 +30,4 @@ int ismeleedam(enum DAMTYPE damtype);
|
|||
int isphysicaldam(enum DAMTYPE damtype);
|
||||
void modifyforsize(int *val, lifeform_t *lf, lifeform_t *victim, int howmuch, enum MODTYPE how);
|
||||
int rolltohit(lifeform_t *lf, lifeform_t *victim, object_t *wep, int *critical, int *fumble);
|
||||
void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam);
|
||||
void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam, int isunarmed);
|
||||
|
|
39
data.c
39
data.c
|
@ -533,7 +533,7 @@ void initjobs(void) {
|
|||
addflag(lastjob->flags, F_LEVFLAG, 5, F_DISEASEIMMUNE, B_TRUE, NULL);
|
||||
// 6: waterawlk via 'body equilibrium' (innate)
|
||||
addflag(lastjob->flags, F_LEVABIL, 6, OT_A_AIMEDSTRIKE, NA, NULL);
|
||||
// 7: iron fist - converts all remaining stamina to damage+knockback.
|
||||
addflag(lastjob->flags, F_LEVABIL, 7, OT_A_IRONFIST, NA, NULL);
|
||||
// 8: molecular manipulation (ie. lower hardness of physical obs by level-7, not lfs) (innate)
|
||||
addflag(lastjob->flags, F_LEVFLAG, 8, F_TREMORSENSE, NA, NULL);
|
||||
// 9: resistance to charm, hypnosis, sleep (innate)
|
||||
|
@ -1029,6 +1029,7 @@ void initobjects(void) {
|
|||
addpoisontype(P_FOOD, "gastroenteritis", "Poisoned", "^bYOU vomit#S violently.", OT_VOMITPOOL, 1, 25, PS_POISON,20);
|
||||
addpoisontype(P_FOODBAD, "salmonella poisoning", "Poisoned", "^bYOU vomit#S violently.", OT_VOMITPOOL, 2, 33, PS_POISON, 30);
|
||||
addpoisontype(P_GAS, "gas inhalation", "Poisoned", "^bYOU cough#S.", OT_NONE, 1, 25, PS_POISON,0);
|
||||
addpoisontype(P_LYCANTHROPY, "lycanthropy", "Cursed", "", OT_NONE, 0, 0, PS_CURSE, -1);
|
||||
addpoisontype(P_ROT, "the mummy's curse", "Cursed", "", OT_NONE, 0, 0, PS_CURSE, 0);
|
||||
addpoisontype(P_TETANUS, "tetanus", "Sick", "^bYOUR muscles spasm violently!", OT_NONE, 0, 3, PS_DISEASE, 15);
|
||||
addpoisontype(P_VENOM, "venom poisoning", "Poisoned", "^bYOU cough#S up blood.", OT_BLOODSPLASH, 1, 25, PS_POISON, 0);
|
||||
|
@ -2788,6 +2789,8 @@ void initobjects(void) {
|
|||
addflag(lastot->flags, F_AIBOOSTITEM, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_AIFLEEITEM, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_VALUE, 150, NA, NA, NULL);
|
||||
addot(OT_POT_LYCANTHROPY, "potion of lycanthropy", "Infects the drinker with the curse of lycanthropy.", MT_GLASS, 1, OC_POTION, SZ_TINY);
|
||||
addflag(lastot->flags, F_VALUE, 300, NA, NA, NULL);
|
||||
addot(OT_POT_LEVITATION, "potion of levitation", "Causes the drinker to float up in the air.", MT_GLASS, 1, OC_POTION, SZ_TINY);
|
||||
addflag(lastot->flags, F_RARITY, H_ALL, 100, RR_RARE, NULL);
|
||||
addflag(lastot->flags, F_VALUE, 150, NA, NA, NULL);
|
||||
|
@ -4779,6 +4782,10 @@ void initobjects(void) {
|
|||
addflag(lastot->flags, F_STAMCOST, 4, NA, NA, NULL);
|
||||
addot(OT_A_INSPECT, "inspect item", "Try to identify an unknown scroll, book, wand or ring from your pack.", MT_NOTHING, 0, OC_ABILITY, SZ_TINY);
|
||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_ABILITY, NA, NA, NULL);
|
||||
addot(OT_A_IRONFIST, "iron fist", "Channel all your remaining stamina into one almighty blow.", MT_NOTHING, 0, OC_ABILITY, SZ_TINY);
|
||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_ABILITY, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_AICASTTOATTACK, ST_ADJVICTIM, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_STAMCOST, 1, NA, NA, NULL);
|
||||
addot(OT_A_JUMP, "jump", "You can leap large distances.", MT_NOTHING, 0, OC_ABILITY, SZ_TINY);
|
||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_ABILITY, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_AICASTTOATTACK, ST_SPECIAL, NA, NA, NULL);
|
||||
|
@ -4972,6 +4979,7 @@ void initobjects(void) {
|
|||
addflag(lastot->flags, F_THE, NA, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_INVULNERABLE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_OPERABLE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_OPERWITHOUTHANDS, B_TRUE, NA, NA, NULL);
|
||||
|
||||
addot(OT_KEYIRON, "ancient iron key", "An ancient key made from iron. It looks important.", MT_METAL, 2, OC_TOOLS, SZ_SMALL);
|
||||
addflag(lastot->flags, F_GLYPH, C_GREY, '[', NA, NULL);
|
||||
|
@ -5349,6 +5357,7 @@ void initobjects(void) {
|
|||
addflag(lastot->flags, F_TECHLEVEL, PR_NOVICE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_HASHIDDENNAME, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_HOLDCONFER, F_KNOWSTIME, B_FALSE, IFKNOWN, NULL);
|
||||
addflag(lastot->flags, F_OPERWITHOUTHANDS, B_TRUE, NA, NA, NULL);
|
||||
addot(OT_DIGITALWATCH, "digital watch", "An electronic timekeeping device which shows the time as a number.", MT_METAL, 0.1, OC_TECH, SZ_TINY);
|
||||
addflag(lastot->flags, F_RARITY, H_ALL, 85, NA, NULL);
|
||||
addflag(lastot->flags, F_VALUE, 50, NA, NA, NULL);
|
||||
|
@ -5356,6 +5365,7 @@ void initobjects(void) {
|
|||
addflag(lastot->flags, F_TECHLEVEL, PR_NOVICE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_HASHIDDENNAME, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastot->flags, F_HOLDCONFER, F_KNOWSTIME, B_TRUE, IFKNOWN, NULL);
|
||||
addflag(lastot->flags, F_OPERWITHOUTHANDS, B_TRUE, NA, NA, NULL);
|
||||
addot(OT_INSECTICIDE, "can of insecticide", "A spraycan containing poisonous chemicals.", MT_METAL, 0.5, OC_TECH, SZ_TINY);
|
||||
addflag(lastot->flags, F_RARITY, H_SWAMP, 85, RR_COMMON, NULL);
|
||||
addflag(lastot->flags, F_RARITY, H_ALL, 85, RR_UNCOMMON, NULL);
|
||||
|
@ -17222,7 +17232,7 @@ void initrace(void) {
|
|||
addflag(lastrace->flags, F_SPELLSPEED, SP_SLOW, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HITDICE, 6, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_TR, 6, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HASATTACK, OT_FISTS, 6, NA, NULL);
|
||||
addflag(lastrace->flags, F_HASATTACK, OT_CLAWS, 6, NA, NULL);
|
||||
addflag(lastrace->flags, F_REGENERATES, 1, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_CANWILL, OT_A_GRAB, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_CANWILL, OT_A_CRUSH, NA, NA, "dam:2d8;");
|
||||
|
@ -17239,10 +17249,13 @@ void initrace(void) {
|
|||
addflag(lastrace->flags, F_HATESRACE, R_WERERAT, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HATESRACE, R_WEREWOLF, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_NOCTURNAL, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_LYCANTHROPE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_LYCANTHROPE, -1, NA, NA, "grizzly bear");
|
||||
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_MORALE, 8, NA, NA, NULL);
|
||||
addflag(lastjob->flags, F_HIRABLE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HIRABLE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HITCONFER, F_POISONED, SC_POISON, 25, NULL);
|
||||
addflag(lastrace->flags, F_HITCONFERVALS, P_LYCANTHROPY, -1, PERMENANT, "10^grizzly bear");
|
||||
addflag(lastrace->flags, F_FILLPOT, OT_POT_LYCANTHROPY, NA, NA, NULL);
|
||||
|
||||
addrace(R_WERERAT, "wererat", 50, '@', C_BROWN, MT_FLESH, RC_HUMANOID, "Weedy humans with shifty eyes and whiskers, wererats are known for their extreme cunning.");
|
||||
setbodytype(lastrace, BT_HUMANOID);
|
||||
|
@ -17266,10 +17279,12 @@ void initrace(void) {
|
|||
addflag(lastrace->flags, F_HITDICE, 3, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_TR, 3, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HASATTACK, OT_CLAWS, 3, NA, NULL);
|
||||
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 2, NA, NULL);
|
||||
addflag(lastrace->flags, F_MAXATTACKS, 1, 1, NA, NULL);
|
||||
addflag(lastrace->flags, F_REGENERATES, 1, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_CANCAST, OT_S_SHAPESHIFT, 3, 3, "pw:1;race:plague rat;");
|
||||
addflag(lastrace->flags, F_CANCAST, OT_S_SUMMONANIMALSSM, 10, 10, "pw:5;race:giant rat;count:5;");
|
||||
addflag(lastrace->flags, F_STARTOBWEPSK, 100, SK_SHORTBLADES, NA, NULL);
|
||||
addflag(lastrace->flags, F_STARTOBWEPSK, 40, SK_SHORTBLADES, NA, NULL);
|
||||
addflag(lastrace->flags, F_STARTOB, 10, NA, NA, "potion of rum");
|
||||
addflag(lastrace->flags, F_AISPELLTARGETOVERRIDE, OT_S_SHAPESHIFT, F_AICASTTOFLEE, ST_SELF, "100");
|
||||
addflag(lastrace->flags, F_STARTSKILL, SK_PERCEPTION, PR_SKILLED, NA, NULL);
|
||||
|
@ -17279,8 +17294,11 @@ void initrace(void) {
|
|||
addflag(lastrace->flags, F_WANTS, OT_POT_RUM, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_SPELLCASTTEXT, OT_NONE, NA, NA, "twitches its nose");
|
||||
addflag(lastrace->flags, F_NOCTURNAL, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_LYCANTHROPE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_LYCANTHROPE, -1, NA, NA, "dire rat");
|
||||
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HITCONFER, F_POISONED, SC_POISON, 25, NULL);
|
||||
addflag(lastrace->flags, F_HITCONFERVALS, P_LYCANTHROPY, -1, PERMENANT, "10^dire rat");
|
||||
addflag(lastrace->flags, F_FILLPOT, OT_POT_LYCANTHROPY, NA, NA, NULL);
|
||||
|
||||
addrace(R_WEREWOLF, "werewolf", 100, '@', C_BROWN, MT_FLESH, RC_HUMANOID, "Shaggy humans with the uncanny ability to shapeshift into a ferocious wolf.");
|
||||
setbodytype(lastrace, BT_HUMANOID);
|
||||
|
@ -17302,7 +17320,9 @@ void initrace(void) {
|
|||
addflag(lastrace->flags, F_ACTIONSPEED, SP_NORMAL, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HITDICE, 4, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_TR, 4, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HASATTACK, OT_FISTS, 6, NA, NULL);
|
||||
addflag(lastrace->flags, F_HASATTACK, OT_CLAWS, 4, NA, NULL);
|
||||
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 6, NA, NULL);
|
||||
addflag(lastrace->flags, F_MAXATTACKS, 1, 1, NA, NULL);
|
||||
addflag(lastrace->flags, F_REGENERATES, 1, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_CANCAST, OT_S_SHAPESHIFT, 3, 3, "pw:1;race:dire wolf;");
|
||||
addflag(lastrace->flags, F_CANCAST, OT_S_SUMMONANIMALSMD, 10, 10, "pw:5;race:young wolf;");
|
||||
|
@ -17313,11 +17333,14 @@ void initrace(void) {
|
|||
addflag(lastrace->flags, F_CASTCHANCE, 40, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_SPELLCASTTEXT, OT_NONE, NA, NA, "howls");
|
||||
addflag(lastrace->flags, F_NOCTURNAL, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_LYCANTHROPE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_LYCANTHROPE, -1, NA, NA, "dire wolf");
|
||||
addflag(lastrace->flags, F_CARNIVORE, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_CANINE, B_TRUE, NA, NA, NULL); // ie. cats will know!
|
||||
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_MORALE, 6, NA, NA, NULL);
|
||||
addflag(lastrace->flags, F_HITCONFER, F_POISONED, SC_POISON, 25, NULL);
|
||||
addflag(lastrace->flags, F_HITCONFERVALS, P_LYCANTHROPY, -1, PERMENANT, "10^dire wolf");
|
||||
addflag(lastrace->flags, F_FILLPOT, OT_POT_LYCANTHROPY, NA, NA, NULL);
|
||||
|
||||
// special monsters
|
||||
addrace(R_GASCLOUD, "cloud of gas", 0.1, 'y', C_GREY, MT_GAS, RC_OTHER, "A large cloud of gas which seems to move with a life of its own...");
|
||||
|
|
BIN
data/hiscores.db
BIN
data/hiscores.db
Binary file not shown.
20
defs.h
20
defs.h
|
@ -23,6 +23,9 @@
|
|||
#define TEXT_WARN_MUTABLE "(you can now gain attributes by eating corpses)"
|
||||
#define TEXT_WARN_NOXP_GOODVSPEACEFUL "Warning: Only Evil players gain XP for peaceful kills."
|
||||
|
||||
// F_SCOREBONUS text args
|
||||
#define SCB_DONATIONS "charitable donations"
|
||||
|
||||
// Defaults
|
||||
#define DEF_AIFOLLOWTIME (20) // if target lf is out of view
|
||||
|
||||
|
@ -477,6 +480,7 @@ enum SHOPACTION {
|
|||
#define PERMENANT (-9873)
|
||||
#define FROMSPELL (-9863)
|
||||
#define FROMPOISON (-9862)
|
||||
#define FROMLYCANTHROPY (-9861)
|
||||
|
||||
// flag lifetimes - external sources (ie. don't kill them)
|
||||
#define FROMEXTERNAL_HIGH (-7000)
|
||||
|
@ -560,6 +564,7 @@ enum GODANGERREASON {
|
|||
GA_MERCY, // allowed something to flee
|
||||
GA_MONEY, // paid money to someone
|
||||
GA_MURDER, // killed someone peaceful
|
||||
GA_PEACEHOUR, // attacked during glorana's peace
|
||||
GA_POISON, // used poison
|
||||
GA_PRAY, // pestering through constant prayer
|
||||
GA_RACE, // prayed while a hated race.
|
||||
|
@ -1527,6 +1532,7 @@ enum OBTYPE {
|
|||
OT_POT_INVIS,
|
||||
OT_POT_INVULN,
|
||||
OT_POT_LEVITATION,
|
||||
OT_POT_LYCANTHROPY,
|
||||
OT_POT_MAGIC,
|
||||
OT_POT_OIL,
|
||||
OT_POT_POISON,
|
||||
|
@ -1865,6 +1871,7 @@ enum OBTYPE {
|
|||
OT_A_HEAVYBLOW,
|
||||
OT_A_HIDE,
|
||||
OT_A_INSPECT,
|
||||
OT_A_IRONFIST,
|
||||
OT_A_HURRICANESTRIKE,
|
||||
OT_A_PICKLOCK,
|
||||
OT_A_POLYREVERT,
|
||||
|
@ -2411,6 +2418,7 @@ enum POISONTYPE {
|
|||
P_FOOD,
|
||||
P_FOODBAD,
|
||||
P_GAS,
|
||||
P_LYCANTHROPY,
|
||||
P_MIGRAINE,
|
||||
P_ROT,
|
||||
P_TETANUS,
|
||||
|
@ -2705,6 +2713,8 @@ enum FLAG {
|
|||
// -1 means "nutrition is weight x abs(val1)"
|
||||
// if v2=DONTKILL, this object does NOT die when drunk.
|
||||
F_OPERABLE, // can operate?
|
||||
F_OPERWITHOUTHANDS, // can operate without having hands or being
|
||||
// humanoid
|
||||
F_OPERWITHOUTID, // can operate without knowing what it is?
|
||||
F_NOTRIED, // don't show '[tried]' or update knowledge
|
||||
// after you have tried this object.
|
||||
|
@ -2795,6 +2805,8 @@ enum FLAG {
|
|||
F_SHARP, // does damage when you step on it. v0/1 are min/max dam
|
||||
F_SCARY, // gives other lfs a penalty to morale checks against you,
|
||||
// v0 = penalty amt.
|
||||
F_SCOREBONUS, // player gains (v1*65535)+v0 points at end game.
|
||||
// text = reason (ie 'donated items' etc)
|
||||
F_SLIPPERY, // you might slip when stepping on it. v0 is amt
|
||||
F_SLIPMOVE, // if someone slips on this, it will move to an adj cell
|
||||
F_FLAMMABLE, // object will catch alight if burnt (ie fire damage)
|
||||
|
@ -2984,6 +2996,7 @@ enum FLAG {
|
|||
// OR
|
||||
// eating this object gives it.
|
||||
// player only flags
|
||||
F_AICONTROLLED, // player will be controlled by the computer
|
||||
F_DONEBURNMSG, // tells the game not to say 'the {celltype} burns!'
|
||||
F_DONEDARKMSG, // tells the game not to say 'it is very dark here'
|
||||
F_DONELISTEN, // supress further 'you hear xx' messages this turn.
|
||||
|
@ -3452,7 +3465,12 @@ enum FLAG {
|
|||
F_HUMANOID, // this race is a humanoid
|
||||
// (can wear armour / use weapons)
|
||||
F_INSECT, // this race is classed as an insect
|
||||
F_LYCANTHROPE, // this race is a lycanthrope. text = what to turn into.
|
||||
F_LYCANTHROPE, // this race is a lycanthrope.
|
||||
// text = what to turn into.
|
||||
// v0 = # of automatic full moon chnages left.
|
||||
// each auto change will decrement this, down
|
||||
// to zero.
|
||||
// -1 means always change on full moon.
|
||||
F_UNDEAD, // this race is classed as undead
|
||||
F_COLDBLOOD, // this race is coldblooded
|
||||
F_NOBODYPART, // this race doesn't have bodypart val0
|
||||
|
|
11
flag.c
11
flag.c
|
@ -1385,6 +1385,17 @@ void timeeffectsflag(flag_t *f, int howlong) {
|
|||
}
|
||||
}
|
||||
|
||||
int flagretainedduringpoly(enum FLAG fid) {
|
||||
switch (fid) {
|
||||
case F_FLEEFROM:
|
||||
case F_HOSTILE:
|
||||
case F_LYCANTHROPE:
|
||||
return B_TRUE;
|
||||
default: break;
|
||||
}
|
||||
return B_FALSE;
|
||||
}
|
||||
|
||||
int flagtomaxhp(flag_t *f) {
|
||||
int hp;
|
||||
int nsides = HITDIESIDES;
|
||||
|
|
1
flag.h
1
flag.h
|
@ -22,6 +22,7 @@ int flagcausesinterrupt(flag_t *f, enum GAINORLOSS gol);
|
|||
int flagcausesloscalc(enum FLAG fid);
|
||||
int flagcausesredraw(lifeform_t *lf, enum FLAG fid);
|
||||
int flagcausesstatredraw(lifeform_t *lf, enum FLAG fid);
|
||||
int flagretainedduringpoly(enum FLAG fid);
|
||||
int flagstacks(enum FLAG fid);
|
||||
int flagtomaxhp(flag_t *f);
|
||||
cell_t *getflagpilelocation(flagpile_t *fp);
|
||||
|
|
3
god.c
3
god.c
|
@ -113,6 +113,9 @@ void angergod(enum RACE rid, int amt, enum GODANGERREASON why) {
|
|||
godsay(rid, B_TRUE, "Where is your sense of greed?!"); break;
|
||||
case GA_MURDER:
|
||||
godsay(rid, B_TRUE, "You have taken a life!"); break;
|
||||
case GA_PEACEHOUR:
|
||||
godsay(rid, B_TRUE, "You dare violate the sanctity of Glorana's Peace?"); break;
|
||||
break;
|
||||
case GA_PRAY: dosay = B_TRUE; break;
|
||||
case GA_POISON:
|
||||
godsay(rid, B_TRUE, "I do not condone the use of poison!"); break;
|
||||
|
|
72
io.c
72
io.c
|
@ -1316,12 +1316,18 @@ int announceflaggain(lifeform_t *lf, flag_t *f) {
|
|||
}
|
||||
|
||||
switch (f->id) {
|
||||
case F_AICONTROLLED:
|
||||
if (isplayer(lf)) {
|
||||
msg("^%cYou lose control of your body!", getlfcol(lf, CC_VBAD));
|
||||
donesomething = B_TRUE;
|
||||
}
|
||||
break;
|
||||
case F_ANTICIPATE:
|
||||
if (isplayer(lf)) {
|
||||
lf2 = findlf(NULL, f->val[0]);
|
||||
if (lf2) {
|
||||
getlfname(lf2, buf);
|
||||
msg("^%d%s%s intentions enter your mind!", getlfcol(lf, CC_GOOD), buf, getpossessive(buf));
|
||||
msg("^%c%s%s intentions enter your mind!", getlfcol(lf, CC_GOOD), buf, getpossessive(buf));
|
||||
donesomething = B_TRUE;
|
||||
}
|
||||
}
|
||||
|
@ -1610,10 +1616,10 @@ int announceflaggain(lifeform_t *lf, flag_t *f) {
|
|||
break;
|
||||
case F_HEAVENARM:
|
||||
if (isplayer(lf)) { // don't know if monsters get it
|
||||
msg("^%dYou are surrounded by a %s!", getlfcol(lf, CC_GOOD), f->text);
|
||||
msg("^%cYou are surrounded by a %s!", getlfcol(lf, CC_GOOD), f->text);
|
||||
donesomething = B_TRUE;
|
||||
} else {
|
||||
msg("^%d%s is surrounded by a %s!", getlfcol(lf, CC_GOOD), lfname, f->text);
|
||||
msg("^%c%s is surrounded by a %s!", getlfcol(lf, CC_GOOD), lfname, f->text);
|
||||
donesomething = B_TRUE;
|
||||
}
|
||||
break;
|
||||
|
@ -1693,9 +1699,9 @@ int announceflaggain(lifeform_t *lf, flag_t *f) {
|
|||
pt = findpoisontype(f->val[0]);
|
||||
if (isplayer(lf)) {
|
||||
if (streq(pt->desc, "Sick") || (pt->id == P_FOOD) || (pt->id == P_FOODBAD)) {
|
||||
msg("^%cYou have contracted %s.", getlfcol(lf, CC_VBAD), pt->name);
|
||||
} else {
|
||||
msg("^%cYou are sick with %s.", getlfcol(lf, CC_VBAD), pt->name);
|
||||
} else {
|
||||
msg("^%cYou have contracted %s.", getlfcol(lf, CC_VBAD), pt->name);
|
||||
}
|
||||
more();
|
||||
} else {
|
||||
|
@ -2097,12 +2103,18 @@ int announceflagloss(lifeform_t *lf, flag_t *f) {
|
|||
return B_FALSE;
|
||||
}
|
||||
switch (f->id) {
|
||||
case F_AICONTROLLED:
|
||||
if (isplayer(lf)) {
|
||||
msg("You have regained control of your body.");
|
||||
donesomething = B_TRUE;
|
||||
}
|
||||
break;
|
||||
case F_ANTICIPATE:
|
||||
if (isplayer(lf)) {
|
||||
lf2 = findlf(NULL, f->val[0]);
|
||||
if (lf2) {
|
||||
getlfname(lf2, buf);
|
||||
msg("^%dYou no longer know %s%s intentions.", getlfcol(lf, CC_BAD), buf, getpossessive(buf));
|
||||
msg("^%cYou no longer know %s%s intentions.", getlfcol(lf, CC_BAD), buf, getpossessive(buf));
|
||||
donesomething = B_TRUE;
|
||||
}
|
||||
}
|
||||
|
@ -2387,13 +2399,13 @@ int announceflagloss(lifeform_t *lf, flag_t *f) {
|
|||
break;
|
||||
case F_HEAVENARM:
|
||||
if (isplayer(lf)) { // don't know if monsters get it
|
||||
msg("^%dYour %s vanishes!", getlfcol(lf, CC_BAD), f->text);
|
||||
msg("^%cYour %s vanishes!", getlfcol(lf, CC_BAD), f->text);
|
||||
donesomething = B_TRUE;
|
||||
} else {
|
||||
char text[BUFLEN];
|
||||
sprintf(text,"%s%s %s vanishes!", lfname, getpossessive(lfname), f->text);
|
||||
capitalise(text);
|
||||
msg("^%d%s", getlfcol(lf, CC_BAD), text);
|
||||
msg("^%c%s", getlfcol(lf, CC_BAD), text);
|
||||
donesomething = B_TRUE;
|
||||
}
|
||||
break;
|
||||
|
@ -4231,7 +4243,12 @@ void docomms(lifeform_t *lf) {
|
|||
|
||||
if (!isgod(lf) && ispeaceful(lf) && cantalk(lf)) {
|
||||
enum SKILLLEVEL slev;
|
||||
job_t *j;
|
||||
slev = getskill(player, SK_SPEECH);
|
||||
// same race or job?
|
||||
j = getjob(player);
|
||||
if ((slev != PR_MASTER) && j && (j == getjob(lf))) slev++;
|
||||
if ((slev != PR_MASTER) && (player->race->id == lf->race->id)) slev++;
|
||||
if (slev >= PR_NOVICE) {
|
||||
addchoice(&prompt, 'x', "Any dangers nearby that I should look out for?", NULL, NULL, NULL);
|
||||
}
|
||||
|
@ -4304,7 +4321,7 @@ void docomms(lifeform_t *lf) {
|
|||
getlfname(lf2, lfname2);
|
||||
msg("You say \"Attack %s!\" to %s.",isplayer(lf2) ? "me" : lfname2, lfname);
|
||||
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT)) {
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT, NULL)) {
|
||||
msg("%s doesn't respond.", lfname);
|
||||
break;
|
||||
}
|
||||
|
@ -4334,7 +4351,7 @@ void docomms(lifeform_t *lf) {
|
|||
break;
|
||||
case 'c':
|
||||
msg("You say \"Come here!\" to %s.",lfname);
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT)) {
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT, NULL)) {
|
||||
msg("%s doesn't respond.", lfname);
|
||||
break;
|
||||
}
|
||||
|
@ -4548,7 +4565,7 @@ void docomms(lifeform_t *lf) {
|
|||
// stop attacking all current targets first...
|
||||
killflagsofid(lf->flags, F_TARGETLF);
|
||||
msg("You say \"Go over there!\" to %s.", lfname);
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT)) {
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT, NULL)) {
|
||||
msg("%s doesn't respond.", lfname);
|
||||
break;
|
||||
}
|
||||
|
@ -4572,7 +4589,7 @@ void docomms(lifeform_t *lf) {
|
|||
case 'j':
|
||||
// charisma check to see if they'll join you.
|
||||
msg("You say \"Join me on my quest!\" to %s.", lfname);
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT)) {
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT, NULL)) {
|
||||
msg("%s doesn't respond.", lfname);
|
||||
break;
|
||||
}
|
||||
|
@ -4598,7 +4615,7 @@ void docomms(lifeform_t *lf) {
|
|||
}
|
||||
if (islowhp(player) &&
|
||||
cantalk(lf) &&
|
||||
canhear(lf, player->cell, SV_SHOUT) &&
|
||||
canhear(lf, player->cell, SV_SHOUT, NULL) &&
|
||||
(getattrbracket(getattr(lf, A_IQ), A_IQ, NULL) > IQ_ANIMAL) &&
|
||||
!isundead(lf)) {
|
||||
if (skillcheck(player, SC_SPEECH, 30, alignmod)) {
|
||||
|
@ -4663,7 +4680,7 @@ void docomms(lifeform_t *lf) {
|
|||
*/
|
||||
case 'r':
|
||||
msg("You say \"Get some rest.\" to %s.", lfname);
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT)) {
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT, NULL)) {
|
||||
msg("%s doesn't respond.", lfname);
|
||||
break;
|
||||
}
|
||||
|
@ -4736,7 +4753,7 @@ void docomms(lifeform_t *lf) {
|
|||
break;
|
||||
case '<':
|
||||
msg("You say \"Stay close!\" to %s.", lfname);
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT)) {
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT, NULL)) {
|
||||
msg("%s doesn't respond.", lfname);
|
||||
break;
|
||||
}
|
||||
|
@ -4748,7 +4765,7 @@ void docomms(lifeform_t *lf) {
|
|||
break;
|
||||
case '>':
|
||||
msg("You say \"Keep your distance!\" to %s.", lfname);
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT)) {
|
||||
if (lfhasflag(lf, F_RAGE) || !canhear(lf, player->cell, SV_SHOUT, NULL)) {
|
||||
msg("%s doesn't respond.", lfname);
|
||||
break;
|
||||
}
|
||||
|
@ -10998,7 +11015,11 @@ void drawstatus(void) {
|
|||
pt = findpoisontype(f->val[0]);
|
||||
// find highest amount of poison
|
||||
if (getskill(player, SK_FIRSTAID) >= PR_ADEPT) {
|
||||
if (poisonthreatenslife(player, f)) {
|
||||
if (pt->severity == PS_CURSE) {
|
||||
setcol(statwin, C_RED);
|
||||
wprintw(statwin, " %s", pt->desc);
|
||||
unsetcol(statwin, C_RED);
|
||||
} else if (poisonthreatenslife(player, f)) {
|
||||
setcol(statwin, C_RED);
|
||||
wprintw(statwin, " %s(bad)", pt->desc);
|
||||
unsetcol(statwin, C_RED);
|
||||
|
@ -11304,10 +11325,14 @@ void showlfarmour(lifeform_t *lf) {
|
|||
enum BODYPART bp;
|
||||
object_t *o;
|
||||
object_t *arm[MAXBODYPARTS];
|
||||
int y;
|
||||
int y,i;
|
||||
char buf[BUFLEN],ch;
|
||||
int keepgoing = B_TRUE;
|
||||
|
||||
for (i = 0; i < MAXBODYPARTS; i++) {
|
||||
arm[i] = NULL;
|
||||
}
|
||||
|
||||
while (keepgoing) {
|
||||
cls();
|
||||
if (isplayer(lf)) {
|
||||
|
@ -13427,14 +13452,21 @@ void showlfstats(lifeform_t *lf, int showall) {
|
|||
}
|
||||
}
|
||||
|
||||
if (pt->id == P_LYCANTHROPY) {
|
||||
snprintf(buf, BUFLEN, "%s %s afflicted with %s.", you(lf), is(lf),
|
||||
pt->name);
|
||||
} else {
|
||||
snprintf(buf, BUFLEN, "%s %s sick with %s%s.", you(lf), is(lf),
|
||||
pt->name, knownfatal ? ", potentially fatally" : "");
|
||||
}
|
||||
if (pt->severity != PS_CURSE) {
|
||||
if (lfhasflag(lf, F_EXTRAINFO) || lfhasflag(lf, F_OMNIPOTENT) ||
|
||||
(getskill(player, SK_FIRSTAID) >= PR_ADEPT) ) {
|
||||
char buf2[BUFLEN];
|
||||
snprintf(buf2, BUFLEN, " [max %d turns left]", f->lifetime);
|
||||
strcat(buf, buf2);
|
||||
}
|
||||
}
|
||||
mvwprintw(mainwin, y, 0, buf);
|
||||
y++;
|
||||
}
|
||||
|
@ -13442,7 +13474,11 @@ void showlfstats(lifeform_t *lf, int showall) {
|
|||
if (f->known && (f->id == F_INCUBATING)) {
|
||||
poisontype_t *pt;
|
||||
pt = findpoisontype(f->val[0]);
|
||||
if (pt->id == P_LYCANTHROPY) {
|
||||
snprintf(buf, BUFLEN, "%s %s afflicted with early onset %s.", you(lf), is(lf), pt->name);
|
||||
} else {
|
||||
snprintf(buf, BUFLEN, "%s %s incubating %s.", you(lf), is(lf), pt->name);
|
||||
}
|
||||
mvwprintw(mainwin, y, 0, buf);
|
||||
y++;
|
||||
}
|
||||
|
|
320
lf.c
320
lf.c
|
@ -316,13 +316,23 @@ long calcscore(lifeform_t *lf) {
|
|||
flag_t *f;
|
||||
long points = 0;
|
||||
object_t *o;
|
||||
flag_t *retflag[MAXCANDIDATES];
|
||||
int nretflags,i;
|
||||
if (lfhasflag(lf, F_NOSCORE)) {
|
||||
return 0;
|
||||
}
|
||||
// objects
|
||||
for (o = lf->pack->first ; o ; o = o->next) {
|
||||
// full points
|
||||
points += getobpoints(o);
|
||||
}
|
||||
// donated items etc
|
||||
getflags(lf->flags, retflag, &nretflags, F_SCOREBONUS, F_NONE);
|
||||
for (i = 0; i < nretflags; i++) {
|
||||
long thisamt;
|
||||
thisamt = (retflag[i]->val[1] * 65535) + retflag[i]->val[0];
|
||||
points += thisamt;
|
||||
}
|
||||
// points for xp
|
||||
points += (lf->xp / 10);
|
||||
|
||||
|
@ -869,7 +879,7 @@ int canhaverandombehaviour(lifeform_t *lf) {
|
|||
}
|
||||
|
||||
// ie. will sound from 'dest' reach the ears of 'lf'
|
||||
int canhear(lifeform_t *lf, cell_t *dest, int volume) {
|
||||
int canhear(lifeform_t *lf, cell_t *dest, int volume, int *numwalls) {
|
||||
int numpixels;
|
||||
int i;
|
||||
int x1,y1;
|
||||
|
@ -879,6 +889,8 @@ int canhear(lifeform_t *lf, cell_t *dest, int volume) {
|
|||
cell_t *retcell[MAXRETCELLS];
|
||||
int celldist;
|
||||
|
||||
if (numwalls) *numwalls = 0;
|
||||
|
||||
if (!lf) return B_FALSE;
|
||||
if (!dest) return B_FALSE;
|
||||
if (!lf->cell) return B_FALSE;
|
||||
|
@ -937,6 +949,7 @@ int canhear(lifeform_t *lf, cell_t *dest, int volume) {
|
|||
if (i != 0) {
|
||||
// solid cells decrease hearing range
|
||||
if (cell->type->solid) {
|
||||
if (numwalls) (*numwalls)++;
|
||||
sounddist--;
|
||||
}
|
||||
// magic barriers stop all sound
|
||||
|
@ -1913,7 +1926,7 @@ int castspell(lifeform_t *lf, enum OBTYPE sid, lifeform_t *targlf, object_t *tar
|
|||
|
||||
if (cansee(player, lf)) {
|
||||
doannounce = B_TRUE;
|
||||
} else if ((casttype == CT_SOUNDBASED) && canhear(player, lf->cell, SV_TALK)) {
|
||||
} else if ((casttype == CT_SOUNDBASED) && canhear(player, lf->cell, SV_TALK, NULL)) {
|
||||
doannounce = B_TRUE;
|
||||
}
|
||||
if (doannounce) {
|
||||
|
@ -2402,7 +2415,7 @@ int checkfordrowning(lifeform_t *lf, object_t *o) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%dThe running water burns %s!", getlfcol(lf, CC_BAD), lfname);
|
||||
msg("^%cThe running water burns %s!", getlfcol(lf, CC_BAD), lfname);
|
||||
}
|
||||
losehp(lf, roll("6d6"), DT_DIRECT, NULL, "running water");
|
||||
}
|
||||
|
@ -2424,7 +2437,7 @@ int checkfordrowning(lifeform_t *lf, object_t *o) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s drowns.",getlfcol(lf, CC_BAD) , lfname);
|
||||
msg("^%c%s drowns.",getlfcol(lf, CC_BAD) , lfname);
|
||||
didsomething = B_TRUE;
|
||||
}
|
||||
addflag(lf->flags, F_NODEATHANNOUNCE, B_TRUE, NA, NA, NULL);
|
||||
|
@ -2441,7 +2454,7 @@ int checkfordrowning(lifeform_t *lf, object_t *o) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s is drowning!", getlfcol(lf, CC_VBAD), lfname);
|
||||
msg("^%c%s is drowning!", getlfcol(lf, CC_VBAD), lfname);
|
||||
didsomething = B_TRUE;
|
||||
}
|
||||
getobnametruebase(o, obname, o->amt);
|
||||
|
@ -2523,6 +2536,22 @@ float comparelfs(lifeform_t *lf1, lifeform_t *lf2) {
|
|||
return ratio;
|
||||
}
|
||||
|
||||
// note: this will kill incubateflag!
|
||||
void completeincubation(lifeform_t *lf, flag_t *incubateflag) {
|
||||
// parse flag text to get power & whatfrom
|
||||
char *p;
|
||||
char buf[BUFLEN];
|
||||
int power;
|
||||
enum POISONTYPE ptype;
|
||||
ptype = incubateflag->val[0];
|
||||
p = readuntil(buf, incubateflag->text, '^');
|
||||
power = atoi(buf);
|
||||
readuntil(buf, p, '^');
|
||||
addtempflag(lf->flags, F_POISONED, ptype, power, incubateflag->obfrom, buf, incubateflag->val[2]);
|
||||
poisoneffects(lf, ptype, power);
|
||||
killflag(incubateflag);
|
||||
}
|
||||
|
||||
int confuse(lifeform_t *lf, int howlong) {
|
||||
flag_t *f;
|
||||
f = lfhasflag(lf, F_CONFUSED);
|
||||
|
@ -3182,7 +3211,7 @@ void die(lifeform_t *lf) {
|
|||
// intelligent monsters will say something
|
||||
if (!hasflag(lf->flags, F_NODEATHSPEECH) && !lfhasflag(lf, F_SUMMONEDBY)) {
|
||||
if (ispetof(lf, player)) {
|
||||
if (cantalk(lf) && canhear(player, lf->cell, 4)) {
|
||||
if (cantalk(lf) && canhear(player, lf->cell, 4, NULL)) {
|
||||
sayphrase(lf, SP_DIE, SV_SHOUT, NA, NULL);
|
||||
} else if (!cansee(player, lf)) {
|
||||
warn("You feel a profound sense of loss.");
|
||||
|
@ -3203,14 +3232,14 @@ void die(lifeform_t *lf) {
|
|||
if (cansee(player, lf)) {
|
||||
getlfname(lf, buf);
|
||||
if (lf->lastdamtype == DT_EXPLOSIVE) {
|
||||
msg("^%d%s is vaporised!",getlfcol(lf, CC_BAD), buf);
|
||||
msg("^%c%s is vaporised!",getlfcol(lf, CC_BAD), buf);
|
||||
vaporised = B_TRUE;
|
||||
} else if (lf->lastdamtype == DT_MELT) {
|
||||
msg("^%d%s completely melts.",getlfcol(lf, CC_BAD), buf);
|
||||
msg("^%c%s completely melts.",getlfcol(lf, CC_BAD), buf);
|
||||
} else if ((lf->lastdamtype == DT_BASH) && lfhasflag(lf, F_FROZEN)) {
|
||||
msg("^%d%s shatters!",getlfcol(lf, CC_BAD), buf);
|
||||
msg("^%c%s shatters!",getlfcol(lf, CC_BAD), buf);
|
||||
} else {
|
||||
msg("^%d%s dies.",getlfcol(lf, CC_BAD), buf);
|
||||
msg("^%c%s dies.",getlfcol(lf, CC_BAD), buf);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -3347,7 +3376,7 @@ void die(lifeform_t *lf) {
|
|||
if (isplayer(souleater)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%dYou consume %s%s soul!", getlfcol(souleater, CC_VGOOD), lfname, getpossessive(lfname));
|
||||
msg("^%cYou consume %s%s soul!", getlfcol(souleater, CC_VGOOD), lfname, getpossessive(lfname));
|
||||
soulflag->known = B_TRUE;
|
||||
|
||||
revealflagob(souleater, soulflag);
|
||||
|
@ -3355,7 +3384,7 @@ void die(lifeform_t *lf) {
|
|||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
getlfname(souleater, buf);
|
||||
msg("^%d%s consumes %s%s soul!", getlfcol(souleater, CC_VGOOD), buf, lfname, getpossessive(lfname));
|
||||
msg("^%c%s consumes %s%s soul!", getlfcol(souleater, CC_VGOOD), buf, lfname, getpossessive(lfname));
|
||||
soulflag->known = B_TRUE;
|
||||
}
|
||||
amt = pctof( rnd(1,soulflag->val[0]), lf->maxhp);
|
||||
|
@ -4875,7 +4904,7 @@ void endlfturn(lifeform_t *lf) {
|
|||
if (islowhp(lf) && onein(3) && !hasflag(lf->flags, F_ASLEEP)) {
|
||||
// TODO: replace 4
|
||||
if (ispetof(lf, player)) {
|
||||
if (!canhear(player, lf->cell, 4)) {
|
||||
if (!canhear(player, lf->cell, 4, NULL)) {
|
||||
char realname[BUFLEN];
|
||||
real_getlfname(lf, realname, NULL, B_NOSHOWALL, B_REALRACE);
|
||||
warn("You feel worried about %s%s.", lfhasflag(lf, F_NAME) ? "" : "your ", noprefix(realname));
|
||||
|
@ -5931,6 +5960,38 @@ subjob_t *findsubjob(enum SUBJOB sjid) {
|
|||
return NULL;
|
||||
}
|
||||
|
||||
// returns true if we did somethign
|
||||
int fixcurses(lifeform_t *lf) {
|
||||
int donesomething = B_FALSE;
|
||||
flag_t *f,*nextf;
|
||||
for (f = lf->flags->first ; f ; f = nextf) {
|
||||
nextf = f->next;
|
||||
if (f->id == F_LYCANTHROPE) {
|
||||
donesomething = B_TRUE;
|
||||
killflag(f);
|
||||
continue;
|
||||
} else if ((f->id == F_INCUBATING) || (f->id == F_POISONED)) {
|
||||
poisontype_t *pt;
|
||||
pt = findpoisontype(f->val[0]);
|
||||
if (pt->severity == PS_CURSE) {
|
||||
donesomething = B_TRUE;
|
||||
killflag(f);
|
||||
continue;
|
||||
}
|
||||
} else if (f->lifetime == FROMLYCANTHROPY) {
|
||||
donesomething = B_TRUE;
|
||||
killflag(f);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
if (donesomething) {
|
||||
if (isplayer(lf)) {
|
||||
msg("^%cYour curses are lifted!", getlfcol(lf, CC_VGOOD));
|
||||
}
|
||||
}
|
||||
return donesomething;
|
||||
}
|
||||
|
||||
// try to actually do the 'run away' action for
|
||||
// anyone we are fleeing from.
|
||||
// returns TRUE if we ran away from something
|
||||
|
@ -9023,8 +9084,8 @@ char *real_getlfname(lifeform_t *lf, char *buf, lifeform_t *usevis, int showall,
|
|||
}
|
||||
|
||||
if (!lfrace) {
|
||||
if (lfhasflag(lf, F_LYCANTHROPE)) {
|
||||
// lycanthropes appear as human unless you know better
|
||||
if (lfhasflag(lf, F_LYCANTHROPE) && !ispolymorphed(lf)) {
|
||||
// lycanthropes in human form appear as human unless you know better
|
||||
if ((getlorelevel(player, RC_HUMANOID) >= PR_ADEPT) ||
|
||||
(getlorelevel(player, RC_MAGIC) >= PR_BEGINNER)) {
|
||||
lfrace = lf->race;
|
||||
|
@ -9199,8 +9260,8 @@ char *real_getlfnamea(lifeform_t *lf, char *buf, lifeform_t * usevis, int showal
|
|||
}
|
||||
|
||||
if (!lfrace) {
|
||||
if (lfhasflag(lf, F_LYCANTHROPE)) {
|
||||
// lycanthropes appear as human unless you know better
|
||||
if (lfhasflag(lf, F_LYCANTHROPE) && !ispolymorphed(lf)) {
|
||||
// lycanthropes in human form appear as human unless you know better
|
||||
if (getlorelevel(player, RC_HUMANOID) >= PR_ADEPT) {
|
||||
lfrace = lf->race;
|
||||
} else {
|
||||
|
@ -9803,6 +9864,35 @@ race_t *getrandomrace(cell_t *c, int forcedepth) {
|
|||
return r;
|
||||
}
|
||||
|
||||
race_t *getrandomracewithflag(enum FLAG fid) {
|
||||
race_t **poss;
|
||||
race_t *r;
|
||||
int nposs = 0;
|
||||
int sel;
|
||||
int count = 0;
|
||||
|
||||
// count races
|
||||
for (r = firstrace ; r ; r = r->next) {
|
||||
if (hasflag(r->flags, fid)) {
|
||||
count++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
poss = malloc(count * sizeof(race_t *));
|
||||
|
||||
for (r = firstrace ; r ; r = r->next) {
|
||||
if (hasflag(r->flags, fid)) {
|
||||
poss[nposs] = r;
|
||||
nposs++;
|
||||
}
|
||||
}
|
||||
sel = rnd(0,nposs-1);
|
||||
r = poss[sel];
|
||||
free(poss);
|
||||
return r;
|
||||
}
|
||||
|
||||
race_t *getreallyrandomrace(enum RACECLASS wantrc) {
|
||||
race_t **poss;
|
||||
race_t *r;
|
||||
|
@ -11769,7 +11859,7 @@ void growhydrahead(lifeform_t *lf, int announce) {
|
|||
getlfname(lf, vname);
|
||||
// regrow
|
||||
if (cansee(player, lf)) {
|
||||
msg("^%d%s grow%s two more heads!", getlfcol(lf, CC_GOOD), vname, isplayer(lf) ? "" : "s");
|
||||
msg("^%c%s grow%s two more heads!", getlfcol(lf, CC_GOOD), vname, isplayer(lf) ? "" : "s");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -12147,7 +12237,7 @@ int injure(lifeform_t *lf, enum BODYPART where, enum DAMTYPE damtype, enum INJUR
|
|||
if (isplayer(lf)) {
|
||||
msg("^BYour brain is ruptured!");
|
||||
} else if (cansee(player, lf)) {
|
||||
msg("^%d%s%s brain ruptures!", getlfcol(lf, CC_VBAD), lfname, getpossessive(lfname));
|
||||
msg("^%c%s%s brain ruptures!", getlfcol(lf, CC_VBAD), lfname, getpossessive(lfname));
|
||||
}
|
||||
if (lf->hp > 0) {
|
||||
setlastdam(lf, "a ruptured brain");
|
||||
|
@ -12204,7 +12294,7 @@ int injure(lifeform_t *lf, enum BODYPART where, enum DAMTYPE damtype, enum INJUR
|
|||
if (isplayer(lf)) {
|
||||
msg("^BYour heart is pierced!");
|
||||
} else if (cansee(player, lf)) {
|
||||
msg("^%d%s%s heart is pierced!", getlfcol(lf, CC_VBAD), lfname, getpossessive(lfname));
|
||||
msg("^%c%s%s heart is pierced!", getlfcol(lf, CC_VBAD), lfname, getpossessive(lfname));
|
||||
}
|
||||
if (lf->hp > 0) {
|
||||
setlastdam(lf, "a pierced heart");
|
||||
|
@ -14458,7 +14548,7 @@ void applywalkdam(lifeform_t *lf, int dam, enum DAMTYPE damtype, object_t *o) {
|
|||
if (isplayer(lf) || cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s choke%s on %s!", getlfcol(lf, CC_BAD), lfname, isplayer(lf) ? "" : "s", buf);
|
||||
msg("^%c%s choke%s on %s!", getlfcol(lf, CC_BAD), lfname, isplayer(lf) ? "" : "s", buf);
|
||||
}
|
||||
} else {
|
||||
if (isplayer(lf)) {
|
||||
|
@ -14467,7 +14557,7 @@ void applywalkdam(lifeform_t *lf, int dam, enum DAMTYPE damtype, object_t *o) {
|
|||
char lfname[BUFLEN];
|
||||
char buf2[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
snprintf(buf2, BUFLEN, "^%d%s %ss %s!", getlfcol(lf, CC_BAD), buf, getattackverb(NULL, NULL, damtype, dam,lf->maxhp), lfname);
|
||||
snprintf(buf2, BUFLEN, "^%c%s %ss %s!", getlfcol(lf, CC_BAD), buf, getattackverb(NULL, NULL, damtype, dam,lf->maxhp), lfname);
|
||||
msg("%s", buf2);
|
||||
}
|
||||
}
|
||||
|
@ -16235,7 +16325,7 @@ int modattr(lifeform_t *lf, enum ATTRIB attr, int amt) {
|
|||
break;
|
||||
}
|
||||
}
|
||||
msg("^%d%s %s %s!", getlfcol(lf, (amt > 0) ? CC_GOOD : CC_BAD), lfname, verb, adverb);
|
||||
msg("^%c%s %s %s!", getlfcol(lf, (amt > 0) ? CC_GOOD : CC_BAD), lfname, verb, adverb);
|
||||
more();
|
||||
}
|
||||
return B_FALSE;
|
||||
|
@ -16323,7 +16413,7 @@ void modhunger(lifeform_t *lf, int amt) {
|
|||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
gethungername(lf, posthlev, buf);
|
||||
msg("^%d%s looks %s%c", getlfcol(lf, CC_BAD), lfname, buf, (needexclam) ? '!' : '.');
|
||||
msg("^%c%s looks %s%c", getlfcol(lf, CC_BAD), lfname, buf, (needexclam) ? '!' : '.');
|
||||
}
|
||||
|
||||
if ((posthlev >= H_VHUNGRY) && (amt > 0)) {
|
||||
|
@ -16490,6 +16580,7 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
|||
int dist;
|
||||
int difficulty;
|
||||
int lbonus;
|
||||
int nwalls = 0;
|
||||
flag_t *f;
|
||||
|
||||
if (l == noisemaker) continue;
|
||||
|
@ -16524,7 +16615,7 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
|||
|
||||
// skillcheck to hear this
|
||||
if ( (isplayer(l) && haslos(l, c)) || // only player can "hear by seeing"
|
||||
(canhear(l, c, volume) && (alwayshear || skillcheck(l, SC_LISTEN, difficulty, lbonus)) ) ) {
|
||||
(canhear(l, c, volume, &nwalls) && (alwayshear || skillcheck(l, SC_LISTEN, difficulty, lbonus)) ) ) {
|
||||
flag_t *f;
|
||||
// announce?
|
||||
if (isplayer(l) && !lfhasflag(l, F_ASLEEP)) {
|
||||
|
@ -16564,10 +16655,38 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
|||
char textnopunc[BUFLEN];
|
||||
char punc;
|
||||
int dist;
|
||||
int muffled = B_FALSE;
|
||||
char prefix[BUFLEN];
|
||||
enum SKILLLEVEL slev;
|
||||
char distbuf[BUFLEN],distbufbad[BUFLEN];
|
||||
char dirbuf[BUFLEN];
|
||||
char localtext[BUFLEN];
|
||||
|
||||
if (nwalls >= 1) muffled = B_TRUE;
|
||||
|
||||
if (muffled) {
|
||||
char *p;
|
||||
// "you hear [a xxx]"
|
||||
// becomes:
|
||||
// "you hear [a muffled xxx]"
|
||||
p = strstartswitha(text, prefix);
|
||||
if (p) {
|
||||
sprintf(localtext, "%smuffled %s", prefix, p);
|
||||
} else {
|
||||
// "you hear [xxx]"
|
||||
// becomes:
|
||||
// "you hear muffled [xxx]"
|
||||
//
|
||||
sprintf(localtext, "muffled %s", text);
|
||||
}
|
||||
|
||||
} else {
|
||||
strcpy(localtext, text);
|
||||
}
|
||||
|
||||
//punc = text[strlen(text)-1];
|
||||
//strncpy(textnopunc, text, strlen(text)-1);
|
||||
strcpy(textnopunc, text);
|
||||
strcpy(textnopunc, localtext);
|
||||
punc = textnopunc[strlen(textnopunc)-1];
|
||||
if (punc == '\"') {
|
||||
// ie. someone saying something
|
||||
|
@ -16580,18 +16699,16 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
|||
|
||||
// adjust text if you are deaf.
|
||||
|
||||
getdisttext(l->cell, c, distbuf, distbufbad, dirbuf);
|
||||
slev = getskill(l, SK_LISTEN);
|
||||
|
||||
// listen skill gives you more info about monsters
|
||||
if (noisemaker) {
|
||||
enum SKILLLEVEL slev;
|
||||
char lfname[BUFLEN];
|
||||
char distbuf[BUFLEN],distbufbad[BUFLEN];
|
||||
char dirbuf[BUFLEN];
|
||||
int detectdist = 0;
|
||||
char lfname[BUFLEN];
|
||||
|
||||
real_getlfnamea(noisemaker, lfname, NULL, B_NOSHOWALL, B_CURRACE);
|
||||
getdisttext(l->cell, c, distbuf, distbufbad, dirbuf);
|
||||
|
||||
slev = getskill(l, SK_LISTEN);
|
||||
detectdist = getlistendetectrange(l);
|
||||
//
|
||||
// high listen skill lets you know more info.
|
||||
|
@ -16611,7 +16728,11 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
|||
}
|
||||
// now announce it.
|
||||
if (slev >= PR_EXPERT) {
|
||||
if (muffled) {
|
||||
msg("You hear a muffled %s%s to the %s%c", noprefix(lfname), distbuf, dirbuf, punc);
|
||||
} else {
|
||||
msg("You hear %s%s to the %s%c", lfname, distbuf, dirbuf, punc);
|
||||
}
|
||||
rv = B_TRUE;
|
||||
} else if (slev >= PR_BEGINNER) {
|
||||
msg("You hear %s%s to the %s%c", textnopunc, distbuf, dirbuf, punc);
|
||||
|
@ -16620,13 +16741,18 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
|||
msg("You hear %s%s%c", textnopunc, distbufbad, punc);
|
||||
rv = B_TRUE;
|
||||
} else {
|
||||
assert(text);
|
||||
msg("You hear %s", text);
|
||||
msg("You hear %s", localtext);
|
||||
rv = B_TRUE;
|
||||
}
|
||||
} else {
|
||||
assert(text);
|
||||
msg("You hear %s", text);
|
||||
if (slev >= PR_BEGINNER) {
|
||||
msg("You hear %s%s to the %s%c", textnopunc, distbuf, dirbuf, punc);
|
||||
} else if (slev >= PR_NOVICE) {
|
||||
msg("You hear %s%s%c", textnopunc, distbufbad, punc);
|
||||
} else {
|
||||
msg("You hear %s", localtext);
|
||||
}
|
||||
rv = B_TRUE;
|
||||
}
|
||||
// can only hear one 'walk' sound per turn.
|
||||
|
@ -16666,7 +16792,6 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
|||
if (isplayer(l)) {
|
||||
char wakenoise[BUFLEN];
|
||||
char *punc;
|
||||
assert(text);
|
||||
strcpy(wakenoise, text);
|
||||
// omit punctuation
|
||||
punc = &(wakenoise[strlen(wakenoise)-1]);
|
||||
|
@ -16951,6 +17076,11 @@ void poison(lifeform_t *lf, int howlong, enum POISONTYPE ptype, int power, char
|
|||
pt = findpoisontype(ptype);
|
||||
srcrace = findrace(srcraceid);
|
||||
|
||||
// special case - lycanthropy only affects players
|
||||
if ((pt->id == P_LYCANTHROPY) && !isplayer(lf)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// are you immune to disease/poison?
|
||||
psev = pt->severity;
|
||||
switch (psev) {
|
||||
|
@ -16991,11 +17121,11 @@ void poison(lifeform_t *lf, int howlong, enum POISONTYPE ptype, int power, char
|
|||
// announce - announceflaggain won't be called
|
||||
// since this isn't a new flag.
|
||||
if (isplayer(lf)) {
|
||||
msg("^%dYou feel more sick.", getlfcol(lf, CC_VBAD));
|
||||
msg("^%cYou feel more sick.", getlfcol(lf, CC_VBAD));
|
||||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s looks even more sick.", getlfcol(lf, CC_VBAD), lfname);
|
||||
msg("^%c%s looks even more sick.", getlfcol(lf, CC_VBAD), lfname);
|
||||
}
|
||||
|
||||
found = B_TRUE;
|
||||
|
@ -17008,6 +17138,7 @@ void poison(lifeform_t *lf, int howlong, enum POISONTYPE ptype, int power, char
|
|||
flag_t *ii;
|
||||
int multiplier = 0;
|
||||
int tempmult;
|
||||
if (pt->incubationtime != -1) {
|
||||
// modify incubation time based on metabolism
|
||||
sumflags(lf->flags, F_FASTMETAB, &tempmult, NULL, NULL);
|
||||
multiplier += tempmult;
|
||||
|
@ -17019,8 +17150,10 @@ void poison(lifeform_t *lf, int howlong, enum POISONTYPE ptype, int power, char
|
|||
} else if (multiplier < 0) {
|
||||
howlong *= abs(multiplier);
|
||||
}
|
||||
}
|
||||
ii = lfhasflagval(lf, F_INCUBATING, ptype, NA, NA, NULL);
|
||||
if (ii) {
|
||||
if (ptype != P_LYCANTHROPY) {
|
||||
// will happen faster
|
||||
ii->val[2] /= 2;
|
||||
if (ii->val[2] < 1) ii->val[2] = 1;
|
||||
|
@ -17028,6 +17161,7 @@ void poison(lifeform_t *lf, int howlong, enum POISONTYPE ptype, int power, char
|
|||
ii->known = B_TRUE;
|
||||
msg("^BYou recognise the increased onset of %s.", pt->name);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
char ftext[BUFLEN];
|
||||
sprintf(ftext, "%d^%s", power, fromwhat);
|
||||
|
@ -18623,6 +18757,7 @@ void setrace(lifeform_t *lf, enum RACE rid, int frompolymorph) {
|
|||
race_t *origrace = NULL;
|
||||
int nretflags;
|
||||
int reverting = B_FALSE;
|
||||
int lycanthrope = B_FALSE;
|
||||
lifeform_t *l;
|
||||
|
||||
//if (gamemode == GM_GAMESTARTED) checkmapflags(player->cell->map); // debugging
|
||||
|
@ -18666,6 +18801,31 @@ void setrace(lifeform_t *lf, enum RACE rid, int frompolymorph) {
|
|||
}
|
||||
//}
|
||||
|
||||
// reverting from initial lycanthrope change?
|
||||
if (lfhasflagval(lf, F_POISONED, P_LYCANTHROPY, NA, NA, NULL) &&
|
||||
lfhasflag(lf, F_AICONTROLLED) && !lfhasflag(lf, F_LYCANTHROPE)) {
|
||||
// add lycanthropy flag
|
||||
addflag(lf->flags, F_LYCANTHROPE, 4, NA, NA, lf->race->name);
|
||||
killflagsofid(lf->flags, F_AICONTROLLED);
|
||||
killflagsofid(lf->flags, F_RAGE);
|
||||
if (isplayer(lf)) killflagsofid(lf->flags, F_HATESALL);
|
||||
} else {
|
||||
flag_t *lyflag;
|
||||
lyflag = lfhasflag(lf, F_LYCANTHROPE);
|
||||
if (lyflag && (lyflag->val[0] > 0)) {
|
||||
// reduce # of auto changes
|
||||
lyflag->val[0]--;
|
||||
if (lyflag->val[0] <= 0) {
|
||||
char cwtext[BUFLEN];
|
||||
if (isplayer(lf)) {
|
||||
msg("^%cYou have gained control of your lycanthropy.", getlfcol(lf, CC_GOOD));
|
||||
}
|
||||
sprintf(cwtext, "pw:1;race:%s;", lf->race->name);
|
||||
addtempflag(lf->flags, F_CANWILL, OT_S_SHAPESHIFT, NA, NA, cwtext, FROMLYCANTHROPY);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ((lf->race->id == R_GASCLOUD) && (origrace->id == R_VAMPIRE)) {
|
||||
if (!isplayer(lf)) {
|
||||
f = lfhasflagval(lf, F_WANTS, OT_COFFIN, NA, NA, NULL);
|
||||
|
@ -18703,19 +18863,39 @@ void setrace(lifeform_t *lf, enum RACE rid, int frompolymorph) {
|
|||
// stop stoning.
|
||||
killflagsofid(lf->flags, F_BEINGSTONED);
|
||||
|
||||
if (lfhasflag(lf, F_LYCANTHROPE)) {
|
||||
lycanthrope = B_TRUE;
|
||||
}
|
||||
|
||||
//if (gamemode == GM_GAMESTARTED) checkmapflags(player->cell->map); // debugging
|
||||
// first remove flags from existing race, or temporary ones
|
||||
lf->born = B_FALSE;
|
||||
for (f = lf->flags->first ; f ; f = nextf) {
|
||||
nextf = f->next;
|
||||
if (frompolymorph && flagretainedduringpoly(f->id)) continue;
|
||||
if (lycanthrope) {
|
||||
switch (f->id) {
|
||||
case F_DTVULN:
|
||||
case F_MATVULN:
|
||||
case F_HITCONFER:
|
||||
case F_HITCONFERVALS:
|
||||
case F_CANEATRAW:
|
||||
case F_CARNIVORE:
|
||||
case F_VEGETARIAN:
|
||||
case F_FILLPOT:
|
||||
continue;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (f->lifetime == FROMRACE) {
|
||||
killflag(f);
|
||||
nkilled++;
|
||||
} else if ((f->lifetime > 0) && (f->id != F_POLYMORPHED)) {
|
||||
// kill most temporary flags, with exceptions
|
||||
switch (f->id) {
|
||||
case F_FLEEFROM:
|
||||
break;
|
||||
default:
|
||||
killflag(f);
|
||||
nkilled++;
|
||||
|
@ -18746,7 +18926,8 @@ void setrace(lifeform_t *lf, enum RACE rid, int frompolymorph) {
|
|||
}
|
||||
// don't change hostility when polymorphing
|
||||
if (frompolymorph) {
|
||||
if (f->id == F_HOSTILE) ignorethis = B_TRUE;
|
||||
if (flagretainedduringpoly(f->id)) ignorethis = B_TRUE;
|
||||
//if (f->id == F_HOSTILE) ignorethis = B_TRUE;
|
||||
}
|
||||
if (!ignorethis) {
|
||||
//if (gamemode == GM_GAMESTARTED) checkmapflags(player->cell->map); // debugging
|
||||
|
@ -19764,7 +19945,7 @@ void startlfturn(lifeform_t *lf) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s is suffocating!", getlfcol(lf, CC_VBAD), lfname);
|
||||
msg("^%c%s is suffocating!", getlfcol(lf, CC_VBAD), lfname);
|
||||
}
|
||||
dam = lf->maxhp / 3;
|
||||
limit(&dam, 1, NA);
|
||||
|
@ -19779,7 +19960,7 @@ void startlfturn(lifeform_t *lf) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%dThe sunlight burns %s!", getlfcol(lf, CC_BAD), lfname);
|
||||
msg("^%cThe sunlight burns %s!", getlfcol(lf, CC_BAD), lfname);
|
||||
}
|
||||
losehp(lf, roll("6d6"), DT_DIRECT, NULL, "sunlight");
|
||||
if (isdead(lf)) return;
|
||||
|
@ -20569,7 +20750,7 @@ void startlfturn(lifeform_t *lf) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s%s spine snaps!", getlfcol(lf, CC_VBAD),
|
||||
msg("^%c%s%s spine snaps!", getlfcol(lf, CC_VBAD),
|
||||
lfname, getpossessive(lfname));
|
||||
}
|
||||
losehp_real(lf, lf->maxhp, DT_DIRECT, NULL, "tetanus", B_FALSE, NULL, B_FALSE, NULL, B_FALSE);
|
||||
|
@ -20604,7 +20785,7 @@ void startlfturn(lifeform_t *lf) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s shivers.", getlfcol(lf, CC_BAD), lfname);
|
||||
msg("^%c%s shivers.", getlfcol(lf, CC_BAD), lfname);
|
||||
}
|
||||
wep = getweapon(lf);
|
||||
if (wep) {
|
||||
|
@ -20652,7 +20833,7 @@ void startlfturn(lifeform_t *lf) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s %s.", getlfcol(lf, CC_BAD), lfname, rnd(0,1) ? "retches" : "gags");
|
||||
msg("^%c%s %s.", getlfcol(lf, CC_BAD), lfname, rnd(0,1) ? "retches" : "gags");
|
||||
}
|
||||
taketime(lf,getactspeed(lf));
|
||||
|
||||
|
@ -20670,7 +20851,7 @@ void startlfturn(lifeform_t *lf) {
|
|||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%d%s melts a little.",getlfcol(lf, CC_BAD), lfname);
|
||||
msg("^%c%s melts a little.",getlfcol(lf, CC_BAD), lfname);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -20719,7 +20900,7 @@ void startlfturn(lifeform_t *lf) {
|
|||
getlfname(lf, lfname);
|
||||
getobname(bloodamu, obname, 1);
|
||||
getobname(o, bname, 1);
|
||||
msg("^%d%s%s %s sucks up %s!", getlfcol(lf, CC_GOOD), lfname, getpossessive(lfname), noprefix(obname), bname);
|
||||
msg("^%c%s%s %s sucks up %s!", getlfcol(lf, CC_GOOD), lfname, getpossessive(lfname), noprefix(obname), bname);
|
||||
makeknown(bloodamu->type->id);
|
||||
}
|
||||
}
|
||||
|
@ -20728,6 +20909,21 @@ void startlfturn(lifeform_t *lf) {
|
|||
continue;
|
||||
}
|
||||
|
||||
if (o->type->id == OT_HOLYCIRCLE) {
|
||||
if (isundead(lf) || lfhasflag(lf, F_LYCANTHROPE)) {
|
||||
char obname[BUFLEN];
|
||||
getobname(o, obname, 1);
|
||||
if (isplayer(lf)) {
|
||||
msg("^%c%s burns you!^n", getlfcol(lf, CC_BAD), obname);
|
||||
} else if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%c%s burns %s!^n", getlfcol(lf, CC_BAD), obname, lfname);
|
||||
}
|
||||
losehp(lf, rnd(10,20), DT_HOLY, NULL, "a holy circle");
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
f = hasflag(o->flags, F_GODSTONE);
|
||||
if (f && (f->val[2] == B_TRUE)) {
|
||||
|
@ -20897,21 +21093,11 @@ void startlfturn(lifeform_t *lf) {
|
|||
}
|
||||
}
|
||||
|
||||
if (f->id == F_INCUBATING) {
|
||||
if ((f->id == F_INCUBATING) && (f->val[1] > 0)) {
|
||||
f->val[1]--;
|
||||
if (f->val[1] <= 0) {
|
||||
// parse text to get power & whatfrom
|
||||
char *p;
|
||||
char buf[BUFLEN];
|
||||
int power;
|
||||
enum POISONTYPE ptype;
|
||||
ptype = f->val[0];
|
||||
p = readuntil(buf, f->text, '^');
|
||||
power = atoi(buf);
|
||||
readuntil(buf, p, '^');
|
||||
addtempflag(lf->flags, F_POISONED, ptype, power, f->obfrom, buf, f->val[2]);
|
||||
poisoneffects(lf, ptype, power);
|
||||
killflag(f);
|
||||
// note: this functino will kill f
|
||||
completeincubation(lf, f);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
@ -21152,9 +21338,9 @@ int steal(lifeform_t *lf, obpile_t *op, enum FLAG wantflag) {
|
|||
if (op->owner) {
|
||||
getlfname(op->owner, targname);
|
||||
if (isplayer(lf)) {
|
||||
msg("^%dYou steal %s from %s!", getlfcol(op->owner, CC_BAD), obname, targname);
|
||||
msg("^%cYou steal %s from %s!", getlfcol(op->owner, CC_BAD), obname, targname);
|
||||
} else if (cansee(player, lf)) {
|
||||
msg("^%d%s steals %s from %s!", getlfcol(op->owner, CC_BAD), lfname, obname, targname);
|
||||
msg("^%c%s steals %s from %s!", getlfcol(op->owner, CC_BAD), lfname, obname, targname);
|
||||
}
|
||||
} else {
|
||||
if (isplayer(lf)) {
|
||||
|
@ -21204,7 +21390,7 @@ int stone(lifeform_t *lf) {
|
|||
addflag(lf->flags, F_CORPSETYPE, B_TRUE, NA, NA, statname);
|
||||
|
||||
if (cansee(player, lf)) {
|
||||
msg("^%d%s %s to stone!", getlfcol(lf, CC_VBAD), lfname, isplayer(lf) ? "turn" : "turns");
|
||||
msg("^%c%s %s to stone!", getlfcol(lf, CC_VBAD), lfname, isplayer(lf) ? "turn" : "turns");
|
||||
}
|
||||
setlastdam(lf, "petrification");
|
||||
lf->hp = 0;
|
||||
|
@ -22510,7 +22696,7 @@ int usestairs(lifeform_t *lf, object_t *o, int onpurpose, int climb) {
|
|||
if (isimmuneto(lf->flags, DT_FALL, B_FALSE)) {
|
||||
msg("%s lands gently on the ground.", lfname);
|
||||
} else {
|
||||
msg("^%d%s slams into the ground!", getlfcol(lf, CC_BAD), lfname);
|
||||
msg("^%c%s slams into the ground!", getlfcol(lf, CC_BAD), lfname);
|
||||
}
|
||||
}
|
||||
// how far did you fall?
|
||||
|
@ -22541,7 +22727,7 @@ int usestairs(lifeform_t *lf, object_t *o, int onpurpose, int climb) {
|
|||
if (isplayer(lf)) {
|
||||
msg("^bYou slam into the roof!");
|
||||
} else if (cansee(player, lf)){
|
||||
msg("^%d%s slams into the roof!",getlfcol(lf, CC_BAD), lfname);
|
||||
msg("^%c%s slams into the roof!",getlfcol(lf, CC_BAD), lfname);
|
||||
}
|
||||
// how far did you fall?
|
||||
sumflags(lf->flags, F_FALLDISTANCE, &howfar, NULL, NULL);
|
||||
|
@ -23657,7 +23843,7 @@ int wear(lifeform_t *lf, object_t *o) {
|
|||
}
|
||||
} else if (o->type->id == OT_AMU_CHOKING) {
|
||||
if (isplayer(lf)) {
|
||||
msg("^%d%s starts to constrict around your neck!", getlfcol(lf, CC_VBAD), obname);
|
||||
msg("^%c%s starts to constrict around your neck!", getlfcol(lf, CC_VBAD), obname);
|
||||
makeknown(o->type->id);
|
||||
if (!needstobreath(lf)) {
|
||||
msg("Luckily, you don't need to breath.");
|
||||
|
|
5
lf.h
5
lf.h
|
@ -47,7 +47,7 @@ int canclimb(lifeform_t *lf, enum ERROR *reason);
|
|||
int candrink(lifeform_t *lf, object_t *o);
|
||||
int caneat(lifeform_t *lf, object_t *o);
|
||||
int canhaverandombehaviour(lifeform_t *lf);
|
||||
int canhear(lifeform_t *lf, cell_t *c, int volume);
|
||||
int canhear(lifeform_t *lf, cell_t *c, int volume, int *numwalls);
|
||||
int canlearn(lifeform_t *lf, enum SKILL skid);
|
||||
int canmakerecipe(lifeform_t *lf, recipe_t *rec);
|
||||
int canopendoors(lifeform_t *lf);
|
||||
|
@ -75,6 +75,7 @@ int check_rest_ok(lifeform_t *lf);
|
|||
//void checkxp(enum RACE rid);
|
||||
lifeform_t *clonelf(lifeform_t *src, cell_t *where);
|
||||
float comparelfs(lifeform_t *lf1, lifeform_t *lf2);
|
||||
void completeincubation(lifeform_t *lf, flag_t *incubateflag);
|
||||
int confuse(lifeform_t *lf, int howlong);
|
||||
void copycorpseflags(flagpile_t *dst, flagpile_t *src);
|
||||
int continuedigging(lifeform_t *lf);
|
||||
|
@ -121,6 +122,7 @@ skill_t *findskill(enum SKILL id);
|
|||
skill_t *findskillbyname(char *name);
|
||||
enum SKILLLEVEL findskilllevbyname(char *name);
|
||||
subjob_t *findsubjob(enum SUBJOB sjid);
|
||||
int fixcurses(lifeform_t *lf);
|
||||
int flee(lifeform_t *lf);
|
||||
void fleefrom(lifeform_t *lf, lifeform_t *enemy, int howlong, int onpurpose);
|
||||
int fovlist_contains(int *endx, int *endy, int nendcells, int x, int y);
|
||||
|
@ -255,6 +257,7 @@ race_t *getrandomcorpserace(cell_t *c);
|
|||
job_t *getrandomjob(int onlyplayerjobs);
|
||||
int getrandommonlevel(race_t *r, map_t *m);
|
||||
race_t *getrandomrace(cell_t *c, int forcedepth);
|
||||
race_t *getrandomracewithflag(enum FLAG fid);
|
||||
race_t *getreallyrandomrace(enum RACECLASS wantrc);
|
||||
enum SKILL getrandomskill(void);
|
||||
object_t *getrestob(lifeform_t *lf);
|
||||
|
|
2
map.c
2
map.c
|
@ -7472,7 +7472,7 @@ int isinscanrange(cell_t *c, void **thing, char *desc, glyph_t *glyph) {
|
|||
int i;
|
||||
// handle scanner
|
||||
if (c->lf) {
|
||||
if (areallies(player, c->lf) && !isplayer(c->lf) && canhear(player, c, SV_SHOUT)) {
|
||||
if (areallies(player, c->lf) && !isplayer(c->lf) && canhear(player, c, SV_SHOUT, NULL)) {
|
||||
// assume that allies will keep in contact with the player, as long
|
||||
// as they're not asleep
|
||||
if (!lfhasflag(c->lf, F_ASLEEP)) {
|
||||
|
|
10
move.c
10
move.c
|
@ -215,6 +215,12 @@ int celldangerous(lifeform_t *lf, cell_t *cell, int onlyifknown, enum ERROR *err
|
|||
}
|
||||
}
|
||||
}
|
||||
} else if (o->type->id == OT_HOLYCIRCLE) {
|
||||
if (isundead(lf) || lfhasflag(lf, F_LYCANTHROPE)) {
|
||||
*error = E_AVOIDOB;
|
||||
rdata = o;
|
||||
return B_TRUE;
|
||||
}
|
||||
}
|
||||
f = hasflag(o->flags, F_PIT);
|
||||
if (f && (f->val[0] == D_DOWN)) {
|
||||
|
@ -955,7 +961,7 @@ int knockback(lifeform_t *lf, int dir, int howfar, lifeform_t *pusher, int fallc
|
|||
} else { // ie door or object
|
||||
getobname(rdata, thing, 1);
|
||||
}
|
||||
if (seen) msg("^%d%s slam%s into %s!^n",getlfcol(lf, CC_BAD), lfname,isplayer(lf) ? "" : "s", thing);
|
||||
if (seen) msg("^%c%s slam%s into %s!^n",getlfcol(lf, CC_BAD), lfname,isplayer(lf) ? "" : "s", thing);
|
||||
snprintf(buf, BUFLEN, "slamming into %s", thing);
|
||||
// 1d6 dam per cell pushed
|
||||
dam = rolldie(howfar, 6);
|
||||
|
@ -2859,7 +2865,7 @@ int trymove(lifeform_t *lf, int dir, int onpurpose, int strafe) {
|
|||
setfacing(lf, dir);
|
||||
drawscreen();
|
||||
|
||||
if (isplayer(lf)) {
|
||||
if (isplayer(lf) && !lfhasflag(lf, F_AICONTROLLED)) {
|
||||
addflagifneeded(lf->flags, F_TURNED, B_TRUE, NA, NA, NULL);
|
||||
lf->turncounter++;
|
||||
if (lf->turncounter >= 5) {
|
||||
|
|
99
nexus.c
99
nexus.c
|
@ -774,20 +774,72 @@ void donextturn(map_t *map) {
|
|||
// do we need to run away from something?
|
||||
if (!flee(who)) {
|
||||
int donormalmove = B_TRUE;
|
||||
flag_t *f;
|
||||
flag_t *f = NULL,*lyflag = NULL;
|
||||
|
||||
// lycanthrope in human form at midnight?
|
||||
if (gettimephase() == TP_MIDNIGHT) {
|
||||
flag_t *f;
|
||||
f = lfhasflag(who, F_LYCANTHROPE);
|
||||
if (f && !ispolymorphed(who)) {
|
||||
char changerace[BUFLEN];
|
||||
int willchange = B_FALSE;
|
||||
int willrage = B_FALSE;
|
||||
//int mintime=20,maxtime=30;
|
||||
strcpy(changerace, "");
|
||||
if (!ispolymorphed(who)) {
|
||||
lyflag = lfhasflag(who, F_LYCANTHROPE);
|
||||
if (lyflag && (lyflag->val[0] != 0)) {
|
||||
strcpy(changerace, lyflag->text);
|
||||
willchange = B_TRUE;
|
||||
} else {
|
||||
flag_t *incflag;
|
||||
incflag = lfhasflagval(who, F_INCUBATING, P_LYCANTHROPY, NA, NA, NULL);
|
||||
if (incflag) {
|
||||
char *p;
|
||||
char *localtext;
|
||||
char buf[BUFLEN];
|
||||
// figure out race name from f_incubating flag.
|
||||
localtext = strdup(incflag->text);
|
||||
p = readuntil(buf, localtext, '^');
|
||||
readuntil(buf, p, '^');
|
||||
strcpy(changerace, buf);
|
||||
// turn f_incubating into f_poisoned
|
||||
completeincubation(who, incflag);
|
||||
willchange = B_TRUE;
|
||||
free(localtext);
|
||||
addflag(who->flags, F_AICONTROLLED, B_TRUE, NA, NA, NULL);
|
||||
if (isplayer(who)) {
|
||||
addflag(who->flags, F_HATESALL, B_TRUE, NA, NA, NULL);
|
||||
}
|
||||
willrage = B_TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (willchange) {
|
||||
race_t *r;
|
||||
if (isplayer(who)) {
|
||||
msg("You feel a change coming over your body!");
|
||||
}
|
||||
r = findracebyname(f->text);
|
||||
polymorphto(who, r->id, rnd(50,100));
|
||||
r = findracebyname(changerace);
|
||||
//polymorphto(who, r->id, rnd(mintime,maxtime));
|
||||
polymorphto(who, r->id, PERMENANT);
|
||||
donormalmove = B_FALSE;
|
||||
if (willrage) {
|
||||
addflag(who->flags, F_RAGE, B_TRUE, NA, NA, NULL);
|
||||
}
|
||||
}
|
||||
} else if (ispolymorphed(who)) {
|
||||
int autorevert = B_FALSE;
|
||||
// not midnight. polymorphed uncontrollably?
|
||||
if (lfhasflagval(who, F_POISONED, P_LYCANTHROPY, NA, NA, NULL) &&
|
||||
lfhasflag(who, F_AICONTROLLED)) {
|
||||
autorevert = B_TRUE;
|
||||
} else if (isplayer(who)) {
|
||||
flag_t *lyflag;
|
||||
lyflag = lfhasflag(who, F_LYCANTHROPE);
|
||||
if (lyflag && (lyflag->val[0] > 0)) {
|
||||
autorevert = B_TRUE;
|
||||
}
|
||||
}
|
||||
if (autorevert) {
|
||||
abilityeffects(who, OT_A_POLYREVERT, who->cell, who, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -988,7 +1040,11 @@ void donextturn(map_t *map) {
|
|||
if (isplayer(who)) {
|
||||
drawcursor();
|
||||
// find out what player wants to do
|
||||
if (lfhasflag(who, F_AICONTROLLED)) {
|
||||
aiturn(who);
|
||||
} else {
|
||||
handleinput();
|
||||
}
|
||||
if (who->bartimer) {
|
||||
who->bartimer--;
|
||||
if (who->bartimer == 0) {
|
||||
|
@ -1231,6 +1287,14 @@ int init(void) {
|
|||
return B_FALSE;
|
||||
}
|
||||
|
||||
void inctime(long nunits) {
|
||||
curtime += (nunits*(TIMECONST));
|
||||
// don't let it get higher than 23:59
|
||||
while (curtime >= DAYSECS) {
|
||||
curtime -= DAYSECS;
|
||||
}
|
||||
}
|
||||
|
||||
// retcell[0] will be initial location
|
||||
void calcbresnham(map_t *m, int x1, int y1, int x2, int y2, cell_t **retcell, int *numpixels) {
|
||||
int xinc1,xinc2,yinc1,yinc2,dinc1,dinc2,d;
|
||||
|
@ -1719,6 +1783,21 @@ dblog("doing sort...");
|
|||
}
|
||||
*/
|
||||
|
||||
void setcurtime(int hours, int minutes) {
|
||||
int h = -1,m = -1,s = -1;
|
||||
|
||||
splittime(&h, &m, &s);
|
||||
while ((h != hours) || (m != minutes)) {
|
||||
curtime += TIMECONST;
|
||||
// don't let it get higher than 23:59
|
||||
while (curtime >= DAYSECS) {
|
||||
curtime -= DAYSECS;
|
||||
}
|
||||
|
||||
splittime(&h, &m, &s);
|
||||
}
|
||||
msg("DEBUG: time fastforwarded to %d:%d",hours, minutes);
|
||||
}
|
||||
|
||||
|
||||
void timeeffectsworld(map_t *map, int updategametime) {
|
||||
|
@ -1893,11 +1972,7 @@ void timeeffectsworld(map_t *map, int updategametime) {
|
|||
|
||||
if (updategametime) {
|
||||
// inc game time
|
||||
curtime += (firstlftime*(TIMECONST));
|
||||
// don't let it get higher than 23:59
|
||||
while (curtime >= DAYSECS) {
|
||||
curtime -= DAYSECS;
|
||||
}
|
||||
inctime(firstlftime);
|
||||
|
||||
// inc total gametime passed
|
||||
gamesecs += firstlftime;
|
||||
|
@ -1920,7 +1995,7 @@ void timeeffectsworld(map_t *map, int updategametime) {
|
|||
char text[BUFLEN];
|
||||
switch (rnd(1,4)) {
|
||||
case 1: sprintf(text, "The hour of Glorana's Peace is here."); break;
|
||||
case 2: sprintf(text, "Mortal, rejoice in Glorana's Peace!"); break;
|
||||
case 2: sprintf(text, "Mortal, rejoice in the hour of Glorana's Peace!"); break;
|
||||
case 3: sprintf(text, "Now is the time of Glorana's Peace."); break;
|
||||
case 4: sprintf(text, "Be healed my child - Glorana's Peace is upon you."); break;
|
||||
}
|
||||
|
|
2
nexus.h
2
nexus.h
|
@ -18,6 +18,7 @@ enum COLOUR getpctcol(float num, float max);
|
|||
char getpctletter(float num, float max);
|
||||
void getrarityrange(int depth, int *min, int *max, int range, int oodok);
|
||||
int init(void);
|
||||
void inctime(long nunits);
|
||||
void calcbresnham(map_t *m, int x1, int y1, int x2, int y2, cell_t **retcell, int *numpixels);
|
||||
void initbresnham(int x1, int y1, int x2, int y2, int *xinc1, int *yinc1, int *dinc1, int *xinc2, int *yinc2, int *dinc2, int *numpixels, int *d);
|
||||
int isplayerturn(void);
|
||||
|
@ -38,6 +39,7 @@ int roll(char *string);
|
|||
int rolldie(int ndice, int sides);
|
||||
int rollhitdice(lifeform_t *lf, int wantmax);
|
||||
int rollmpdice(lifeform_t *lf, int wantmax);
|
||||
void setcurtime(int hours, int minutes);
|
||||
//void sortlf(map_t *map);
|
||||
void timeeffectsworld(map_t *map, int updategametime);
|
||||
void usage(char *progname);
|
||||
|
|
30
objects.c
30
objects.c
|
@ -9121,12 +9121,14 @@ int operate(lifeform_t *lf, object_t *o, cell_t *where) {
|
|||
int wastech = B_FALSE;
|
||||
|
||||
if (!lfhasflag(lf, F_HUMANOID) || !hasbp(lf, BP_HANDS)) {
|
||||
if (!hasflag(o->flags, F_OPERWITHOUTHANDS)) {
|
||||
// only humanoids can zap things
|
||||
if (isplayer(lf)) {
|
||||
msg("You lack the manual dexterity to operate this.");
|
||||
}
|
||||
return B_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
if (lfhasflag(lf, F_RAGE)) {
|
||||
if (isplayer(lf)) {
|
||||
|
@ -10915,6 +10917,7 @@ void potioneffects(lifeform_t *lf, enum OBTYPE oid, object_t *o, enum BLESSTYPE
|
|||
int failed;
|
||||
int seenbyplayer;
|
||||
object_t *o2;
|
||||
race_t *r;
|
||||
flag_t *f;
|
||||
|
||||
if (isplayer(lf)) {
|
||||
|
@ -11167,6 +11170,12 @@ void potioneffects(lifeform_t *lf, enum OBTYPE oid, object_t *o, enum BLESSTYPE
|
|||
i = rnd(5,20);
|
||||
addtempflag(lf->flags, F_LEVITATING, B_TRUE, NA, NA, NULL, i);
|
||||
break;
|
||||
case OT_POT_LYCANTHROPY:
|
||||
if (isplayer(lf)) msg("Yuck, this tastes like blood!");
|
||||
// find random lycanthrope type
|
||||
r = getrandomracewithflag(F_LYCANTHROPE);
|
||||
poison(lf, PERMENANT, P_LYCANTHROPY, 1, r->name, R_NONE);
|
||||
break;
|
||||
case OT_POT_MAGIC:
|
||||
if (getmr(lf) && skillcheck(lf, SC_RESISTMAG, 30, -10)) {
|
||||
if (isplayer(lf)) {
|
||||
|
@ -11285,7 +11294,9 @@ void potioneffects(lifeform_t *lf, enum OBTYPE oid, object_t *o, enum BLESSTYPE
|
|||
}
|
||||
losehp(lf, rnd(5,15), DT_HOLY, NULL, "drinking holy water");
|
||||
} else {
|
||||
if (isplayer(lf)) msg("Mmm, holy water.");
|
||||
if (isplayer(lf)) msg("A feeling of holiness spreads through your body.");
|
||||
// cure any curses, and lycanthropy
|
||||
fixcurses(lf);
|
||||
}
|
||||
break;
|
||||
case B_UNCURSED:
|
||||
|
@ -11882,8 +11893,6 @@ int readsomething(lifeform_t *lf, object_t *o) {
|
|||
|
||||
} else if (o->type->id == OT_SCR_REMOVECURSE) {
|
||||
int seen = B_FALSE;
|
||||
flag_t *retflag[MAXCANDIDATES];
|
||||
int i,nretflags = 0;
|
||||
object_t *oo;
|
||||
// remove curses!
|
||||
for (oo = lf->pack->first ; oo ; oo = oo->next) {
|
||||
|
@ -11897,16 +11906,9 @@ int readsomething(lifeform_t *lf, object_t *o) {
|
|||
}
|
||||
}
|
||||
// fix player curses
|
||||
getflags(lf->flags, retflag, &nretflags, F_POISONED, F_NONE);
|
||||
for (i = 0; i < nretflags; i++) {
|
||||
poisontype_t *pt;
|
||||
pt = findpoisontype(retflag[i]->val[0]);
|
||||
if (pt->severity == PS_CURSE) {
|
||||
} else {
|
||||
killflag(retflag[i]);
|
||||
if (fixcurses(lf)) {
|
||||
if (isplayer(lf) || cansee(player, lf)) seen = B_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
if (seen) {
|
||||
// id the scroll now
|
||||
|
@ -13792,7 +13794,7 @@ int real_fireat(lifeform_t *thrower, object_t *o, int amt, cell_t *where, int sp
|
|||
applyarmourdamage(target, o, reduceamt, DT_PROJECTILE, NULL);
|
||||
}
|
||||
|
||||
wepeffects(o->flags, target->cell, hasflag(o->flags, F_DAM), dam);
|
||||
wepeffects(o->flags, target->cell, hasflag(o->flags, F_DAM), dam, B_FALSE);
|
||||
|
||||
missiledam += ((speed*2)+rnd(1,4));
|
||||
|
||||
|
@ -13852,7 +13854,7 @@ int real_fireat(lifeform_t *thrower, object_t *o, int amt, cell_t *where, int sp
|
|||
stuck = B_TRUE;
|
||||
if (cansee(player, target)) {
|
||||
if (thrower) {
|
||||
msg("^%d%s sticks to %s!", getlfcol(thrower, CC_BAD), obname, targetname);
|
||||
msg("^%c%s sticks to %s!", getlfcol(thrower, CC_BAD), obname, targetname);
|
||||
} else {
|
||||
msg("%s sticks to %s!", obname, targetname);
|
||||
}
|
||||
|
@ -14381,7 +14383,7 @@ void timeeffectsob(object_t *o) {
|
|||
if (cansee(player, lf)) {
|
||||
char lfname[BUFLEN];
|
||||
getlfname(lf, lfname);
|
||||
msg("^%dPowerful winds pummel %s!^n", getlfcol(lf, CC_BAD), lfname);
|
||||
msg("^%cPowerful winds pummel %s!^n", getlfcol(lf, CC_BAD), lfname);
|
||||
}
|
||||
// lfs here take damage
|
||||
if (creator) {
|
||||
|
|
36
shops.c
36
shops.c
|
@ -438,7 +438,8 @@ enum SHOPRETURN shopdonate(lifeform_t *lf, object_t *vm, int starty, char *topte
|
|||
|
||||
// validate it
|
||||
if (o) {
|
||||
int goldgiven = 0;
|
||||
long goldgiven = 0;
|
||||
long multi = 0;
|
||||
flag_t *f;
|
||||
// can we remove it?
|
||||
if (isequipped(o)) {
|
||||
|
@ -467,16 +468,27 @@ enum SHOPRETURN shopdonate(lifeform_t *lf, object_t *vm, int starty, char *topte
|
|||
} else {
|
||||
object_t *newob;
|
||||
char let;
|
||||
int thisval,pct = 100;
|
||||
if (vm->contents->first) {
|
||||
let = vm->contents->last->letter + 1;
|
||||
} else {
|
||||
let = 'a';
|
||||
}
|
||||
|
||||
thisval = getobvalue(o);
|
||||
if (!isknown(o)) {
|
||||
pct -= 50;
|
||||
}
|
||||
if (!isidentified(o)) {
|
||||
pct -= 25;
|
||||
}
|
||||
thisval = pctof(pct, thisval);
|
||||
|
||||
newob = moveob(o, vm->contents, count);
|
||||
newob->letter = let;
|
||||
(*ndonated)++;
|
||||
practice(player, SK_SPEECH, 1);
|
||||
goldgiven += getobvalue(o);
|
||||
goldgiven += thisval;
|
||||
}
|
||||
|
||||
if ((vm->type->id == OT_TEMPLE) && goldgiven) {
|
||||
|
@ -500,9 +512,29 @@ enum SHOPRETURN shopdonate(lifeform_t *lf, object_t *vm, int starty, char *topte
|
|||
} else {
|
||||
addflag(vm->flags, F_SHOPDONATED, goldgiven, NA, NA, NULL);
|
||||
}
|
||||
|
||||
|
||||
|
||||
// remember amount donated, for addition to final score
|
||||
f = lfhasflagval(lf, F_SCOREBONUS, NA, NA, NA, SCB_DONATIONS);
|
||||
if (f) {
|
||||
multi = f->val[1];
|
||||
goldgiven += f->val[0];
|
||||
} else {
|
||||
f = addflag(lf->flags, F_SCOREBONUS, 0, NA, NA, SCB_DONATIONS);
|
||||
multi = 0;
|
||||
}
|
||||
// cope with >= 65535
|
||||
while (goldgiven > 65535) {
|
||||
goldgiven -= 65535;
|
||||
multi++;
|
||||
}
|
||||
f->val[0] = goldgiven;
|
||||
f->val[1] = multi;
|
||||
} else {
|
||||
return SR_BACK;
|
||||
}
|
||||
angergodmaybe(R_GODTHIEVES, 10, GA_MONEY);
|
||||
|
||||
return SR_CONTINUE;
|
||||
}
|
||||
|
|
85
spell.c
85
spell.c
|
@ -288,6 +288,7 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
}
|
||||
|
||||
// find out where the other end goes...
|
||||
user->changinglev = B_TRUE;
|
||||
c = getstairdestination(stairs, &madenewmap);
|
||||
|
||||
// show --more-- after we have the destination
|
||||
|
@ -295,6 +296,7 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
|
||||
if (!c) {
|
||||
msg("These stairs don't seem to go anywhere!");
|
||||
user->changinglev = B_FALSE;
|
||||
return B_TRUE;
|
||||
}
|
||||
|
||||
|
@ -341,7 +343,8 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
nposs = 1;
|
||||
}
|
||||
} else {
|
||||
// get all lfs within hearing of the other end
|
||||
int nwalls;
|
||||
// get all lfs within direct hearing (not through walls) of the other end
|
||||
for (lf = c->map->lf ; lf ; lf = lf->next) {
|
||||
if (lf == user) continue;
|
||||
// get movement text
|
||||
|
@ -350,7 +353,7 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
// overwrite name
|
||||
real_getlfnamea(lf, thismovetext, NULL, B_NOSHOWALL, B_CURRACE);
|
||||
}
|
||||
if (canhear(user, lf->cell, vol)) {
|
||||
if (canhear(user, lf->cell, vol, &nwalls) && (nwalls == 0)) {
|
||||
// already have this text?
|
||||
found = B_FALSE;
|
||||
for (n = 0; n < nposs; n++) {
|
||||
|
@ -520,6 +523,7 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
}
|
||||
}
|
||||
}
|
||||
user->changinglev = B_FALSE;
|
||||
// announce
|
||||
if (nposs) {
|
||||
for (n = 0; n < nposs; n++) {
|
||||
|
@ -1732,8 +1736,11 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
}
|
||||
}
|
||||
|
||||
// shield gets damaged
|
||||
if (!touch(target, shield)) {
|
||||
// if the victim touching the shield didn't destroy it, the shield gets damaged
|
||||
takedamage(shield, roll("1d3"), DT_DIRECT);
|
||||
}
|
||||
|
||||
} else if (abilid == OT_A_SNATCH) {
|
||||
object_t *o = NULL;
|
||||
flag_t *f;
|
||||
|
@ -1795,7 +1802,7 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
f = lfhasflagval(user, F_NOTIME, OT_A_SNATCH, NA, NA, NULL);
|
||||
if (f) killflag(f);
|
||||
} else if (abilid == OT_A_SONICBOLT) {
|
||||
int volume;
|
||||
int volume,nwalls;
|
||||
|
||||
if (!validatespellcell(user, &targcell,TT_MONSTER, abilid, power, B_FALSE)) return B_TRUE;
|
||||
target = targcell->lf;
|
||||
|
@ -1808,12 +1815,14 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
} else {
|
||||
volume = power;
|
||||
}
|
||||
if (target && canhear(target, user->cell, volume)) {
|
||||
if (target && canhear(target, user->cell, volume, &nwalls)) {
|
||||
if (nwalls == 0) {
|
||||
if (isplayer(target)) {
|
||||
msg("Pain shoots through your eardrums!");
|
||||
}
|
||||
losehp(target, roll(damstr), DT_SONIC, user, "a bolt of sound");
|
||||
}
|
||||
}
|
||||
} else if (abilid == OT_A_SPRINT) {
|
||||
flag_t *f;
|
||||
f = lfhasflag(user, F_SPRINTING);
|
||||
|
@ -3277,7 +3286,7 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
default:
|
||||
break;
|
||||
}
|
||||
if (ok && canhear(target, user->cell, 4)) {
|
||||
if (ok && canhear(target, user->cell, 4, NULL)) {
|
||||
scare(target, user, rnd(5,10), 0);
|
||||
}
|
||||
}
|
||||
|
@ -3484,6 +3493,61 @@ int abilityeffects(lifeform_t *user, enum OBTYPE abilid, cell_t *targcell, lifef
|
|||
addflag(user->flags, F_FAILEDINSPECT, o->type->id, NA, NA, NULL);
|
||||
}
|
||||
taketime(user, getactspeed(user));
|
||||
} else if (abilid == OT_A_IRONFIST) {
|
||||
char dirch,tname[BUFLEN];
|
||||
int dam,dir = D_NONE;
|
||||
|
||||
if (isswimming(user) && !lfhasflag(user, F_AQUATIC)) {
|
||||
if (isplayer(user)) msg("You lack the stability to invoke the iron fist manouver while swimming.");
|
||||
return B_TRUE;
|
||||
}
|
||||
|
||||
if (getweapon(user)) {
|
||||
if (isplayer(user)) msg("You must be unarmed to invoke the iron fist.");
|
||||
return B_TRUE;
|
||||
}
|
||||
|
||||
// ask for direction
|
||||
if (!targcell) {
|
||||
dirch = askchar("Iron fist in which direction (- to cancel)", "yuhjklbn.-","-", B_FALSE, B_TRUE);
|
||||
if (dirch == '.') {
|
||||
// yourself!
|
||||
targcell = user->cell;
|
||||
} else {
|
||||
dir = chartodir(dirch);
|
||||
if (dir == D_NONE) {
|
||||
if (isplayer(user)) msg("Cancelled.");
|
||||
return B_TRUE ;
|
||||
} else {
|
||||
targcell = getcellindir(user->cell, dir);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
target = targcell->lf;
|
||||
if (!target) {
|
||||
if (isplayer(user)) msg("There is nobody there to attack!");
|
||||
return B_TRUE;
|
||||
}
|
||||
getlfname(target, tname);
|
||||
|
||||
if (isplayer(user)) {
|
||||
msg("^%cYou strike %s with THE IRON FIST!",getlfcol(user, CC_GOOD),tname);
|
||||
} else if (cansee(player, user)) {
|
||||
msg("^%c%s strikes %s with THE IRON FIST!",getlfcol(user, CC_GOOD),username, tname);
|
||||
}
|
||||
|
||||
// convert all remaining stamina into damage.
|
||||
dam = getstamina(user);
|
||||
|
||||
setstamina(user, 0);
|
||||
sprintf(damstr, "%s%s invocation of the iron fist",username,getpossessive(username));
|
||||
losehp(target, dam, DT_DIRECT, user, damstr);
|
||||
|
||||
if (dir != D_NONE) {
|
||||
// knockback too
|
||||
knockback(target, dir, dam, user, 0, B_TRUE);
|
||||
}
|
||||
}
|
||||
|
||||
// expire ability
|
||||
|
@ -5553,7 +5617,9 @@ int dospelleffects(lifeform_t *caster, enum OBTYPE spellid, int power, lifeform_
|
|||
// all in range must pass a magic resistance check or die
|
||||
for (target = caster->cell->map->lf ; target ; target = target->next) {
|
||||
if (target != caster) {
|
||||
if (canhear(target, caster->cell, SV_TALK)) {
|
||||
int nwalls;
|
||||
if (canhear(target, caster->cell, SV_TALK, &nwalls)) {
|
||||
if (nwalls == 0) {
|
||||
if (spellresisted(target, caster, spellid, power, seenbyplayer, B_TRUE)) {
|
||||
} else {
|
||||
losehp(target, target->hp, DT_SONIC, caster, "a banshee's wail");
|
||||
|
@ -5561,6 +5627,7 @@ int dospelleffects(lifeform_t *caster, enum OBTYPE spellid, int power, lifeform_
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (spellid == OT_S_DETECTAURA) {
|
||||
if (isplayer(caster)) {
|
||||
object_t *o;
|
||||
|
@ -11918,6 +11985,10 @@ int dospelleffects(lifeform_t *caster, enum OBTYPE spellid, int power, lifeform_
|
|||
summoner = caster;
|
||||
}
|
||||
|
||||
if (!isplayer(caster)) {
|
||||
friendly = B_TRUE;
|
||||
}
|
||||
|
||||
ngot = summonlfs(caster, caster->cell, wantrace, wantrc, wantsize, AL_NONE, nwant, lifetime, friendly);
|
||||
if (!ngot) {
|
||||
fizzle(caster);
|
||||
|
|
24
text.c
24
text.c
|
@ -1086,7 +1086,7 @@ char *getflagsourcetext(flag_t *f) {
|
|||
int gethitconferlifetime(char *text, int *min, int *max) {
|
||||
int howlong;
|
||||
int localmin = -1,localmax = -1;
|
||||
if (text) {
|
||||
if (text && strlen(text)) {
|
||||
char loctext[BUFLEN];
|
||||
char *word, *dummy;
|
||||
strcpy(loctext,text);
|
||||
|
@ -2318,6 +2318,28 @@ char *strstarts(char *a, char *prefix) {
|
|||
return NULL;
|
||||
}
|
||||
|
||||
// if string starts with 'a ', 'an ' or 'the ', then return the position after it,
|
||||
// and write the prefix into 'prefix'.
|
||||
// otherwise return null.
|
||||
//
|
||||
char *strstartswitha(char *text, char *retprefix) {
|
||||
char *prefix[] = {
|
||||
"the ",
|
||||
"an ",
|
||||
"a "
|
||||
};
|
||||
int nprefixes = 3,i;
|
||||
for (i = 0; i < nprefixes; i++) {
|
||||
if (strstarts(text, prefix[i])) {
|
||||
if (retprefix) {
|
||||
strcpy(retprefix, prefix[i]);
|
||||
}
|
||||
return text + strlen(prefix[i]);
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int strlen_without_colours(char *buf) {
|
||||
char *p;
|
||||
int len = 0;
|
||||
|
|
1
text.h
1
text.h
|
@ -70,6 +70,7 @@ char *strends(char *a, char *suffix);
|
|||
char *strcasestarts(char *a, char *prefix);
|
||||
material_t *strmatchesmaterial(char *p);
|
||||
char *strstarts(char *a, char *prefix);
|
||||
char *strstartswitha(char *text, char *retprefix);
|
||||
int strlen_without_colours(char *buf);
|
||||
int strpixmatch(char *haystack, char *needle);
|
||||
int texttodice(char *text, int *ndice, int *nsides, int *bonus);
|
||||
|
|
Loading…
Reference in New Issue