- [+] make ring of invisibility also drain your hp!
- [+] monster with tremorsense can 'hear' - [+] allow attacking of wall cells with normal melee attacks - [+] glass should shatter - [+] option: stop running on hearing a sound - [+] make describerace use downline(). - [+] make certain strengths and weaknesses not show up in player selection - [+] An uncursed manriki wraps around the hawk. The hawk falls to the ground. A black bear comes into view. You critically scratch #. The black bear roars. - [+] check construct_hit_string. - [+] i was hitting a hawk. - [+] still some entrances overlapping glyphs. - [+] genericise checking code in fix_Reachabilty - [+] Also: in fix_reachability, disallow linking to cells which: - [+] are adjacent to a door - [+] are part of a vault with maintain_edge, and are 't marked as exits. - [+] looking a bit better now... - [+] incorrect glyph colour for animated zombies - [+] grow/shrink potions? to change lf size to fit armour. - [+] resizelf() - [+] modification spell (l2) - [+] grow - [+] shrink - [+] potions - [+] cursed growth does shrink - [+] make rare monsters / objects only sometimes be known.
This commit is contained in:
parent
4cff04558c
commit
bbaca368e7
202
attack.c
202
attack.c
|
@ -157,6 +157,7 @@ int attackcell(lifeform_t *lf, cell_t *c, int force) {
|
||||||
AT_NONE = 0,
|
AT_NONE = 0,
|
||||||
AT_LF = 1,
|
AT_LF = 1,
|
||||||
AT_OB = 2,
|
AT_OB = 2,
|
||||||
|
AT_WALL = 3,
|
||||||
} attacktype = AT_NONE;
|
} attacktype = AT_NONE;
|
||||||
void *attacktarget;
|
void *attacktarget;
|
||||||
int attacklfid = -1;
|
int attacklfid = -1;
|
||||||
|
@ -279,31 +280,16 @@ int attackcell(lifeform_t *lf, cell_t *c, int force) {
|
||||||
attacktype = AT_OB;
|
attacktype = AT_OB;
|
||||||
attacktarget = o;
|
attacktarget = o;
|
||||||
} else {
|
} else {
|
||||||
// TODO: attack wall?
|
|
||||||
if (!lfhasflag(lf, F_HURRICANESTRIKE)) {
|
if (!lfhasflag(lf, F_HURRICANESTRIKE)) {
|
||||||
/*
|
if (c->type->solid) {
|
||||||
flag_t *sf;
|
attacktype = AT_WALL;
|
||||||
lifeform_t *stomachlf = NULL;
|
attacktarget = c;
|
||||||
sf = hasflag(lf->cell->map->flags, F_STOMACHOF);
|
|
||||||
if (sf) {
|
|
||||||
stomachlf = findlf(NULL, sf->val[0]);
|
|
||||||
}
|
|
||||||
// we ARE allowed to attack stomach walls.
|
|
||||||
if (sf && stomachlf && (c->type->id == CT_WALLFLESH)) {
|
|
||||||
attacktype = AT_LF;
|
|
||||||
attacktarget = stomachlf;
|
|
||||||
} else {
|
} else {
|
||||||
// not allowed to attack normal walls
|
|
||||||
if (isplayer(lf)) {
|
if (isplayer(lf)) {
|
||||||
msg("There is nothing there to attack!");
|
msg("There is nothing there to attack!");
|
||||||
}
|
}
|
||||||
return B_TRUE;
|
return B_TRUE;
|
||||||
}
|
}
|
||||||
*/
|
|
||||||
if (isplayer(lf)) {
|
|
||||||
msg("There is nothing there to attack!");
|
|
||||||
}
|
|
||||||
return B_TRUE;
|
|
||||||
} // end if !hurricanestrike
|
} // end if !hurricanestrike
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -450,6 +436,12 @@ int attackcell(lifeform_t *lf, cell_t *c, int force) {
|
||||||
attacksdone = maxattacks;
|
attacksdone = maxattacks;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
} else if (attacktype == AT_WALL) {
|
||||||
|
if (attackwall(lf, (cell_t *)attacktarget, wep[i], damflag[i])) {
|
||||||
|
// failed
|
||||||
|
attacksdone = maxattacks;
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
attacksdone++;
|
attacksdone++;
|
||||||
|
|
||||||
|
@ -680,7 +672,9 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
||||||
object_t *armour;
|
object_t *armour;
|
||||||
char noun[BUFLEN];
|
char noun[BUFLEN];
|
||||||
critpos = getrandomcorebp(victim, lf);
|
critpos = getrandomcorebp(victim, lf);
|
||||||
if (critpos != BP_NONE) {
|
if (critpos == BP_NONE) {
|
||||||
|
strcpy(victimbpname, victimname);
|
||||||
|
} else {
|
||||||
armour = getequippedob(victim->pack, critpos);
|
armour = getequippedob(victim->pack, critpos);
|
||||||
if (armour) {
|
if (armour) {
|
||||||
char armname[BUFLEN];
|
char armname[BUFLEN];
|
||||||
|
@ -711,7 +705,6 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
||||||
getlfname(victim, victimname);
|
getlfname(victim, victimname);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// weapon passing through ghosts etc?
|
// weapon passing through ghosts etc?
|
||||||
if (hit) {
|
if (hit) {
|
||||||
if (lfhasflag(victim, F_NONCORPOREAL) &&
|
if (lfhasflag(victim, F_NONCORPOREAL) &&
|
||||||
|
@ -1402,13 +1395,17 @@ int attackob(lifeform_t *lf, object_t *o, object_t *wep, flag_t *damflag) {
|
||||||
if (isplayer(lf) && hasflag(o->flags, F_LOCKED)) {
|
if (isplayer(lf) && hasflag(o->flags, F_LOCKED)) {
|
||||||
angergodmaybe(R_GODTHIEVES, 25, GA_MONEY);
|
angergodmaybe(R_GODTHIEVES, 25, GA_MONEY);
|
||||||
}
|
}
|
||||||
|
if (isdeadob(o)) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
} // end foreach damtype
|
} // end foreach damtype
|
||||||
|
|
||||||
|
if (!isdeadob(o)) {
|
||||||
// special weapon effects, as long as you're not doing a heavy blow
|
// special weapon effects, as long as you're not doing a heavy blow
|
||||||
if (!lfhasflag(lf, F_HEAVYBLOW) && dam[0]) {
|
if (!lfhasflag(lf, F_HEAVYBLOW) && dam[0]) {
|
||||||
wepeffects(wep->flags, obloc, damflag, dam[0]);
|
wepeffects(wep->flags, obloc, damflag, dam[0]);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (isunarmed) {
|
if (isunarmed) {
|
||||||
// touch effects
|
// touch effects
|
||||||
|
@ -1426,6 +1423,169 @@ int attackob(lifeform_t *lf, object_t *o, object_t *wep, flag_t *damflag) {
|
||||||
return B_FALSE;
|
return B_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int attackwall(lifeform_t *lf, cell_t *c, object_t *wep, flag_t *damflag) {
|
||||||
|
int dam[100];
|
||||||
|
enum DAMTYPE damtype[100];
|
||||||
|
int ndam = 0;
|
||||||
|
char attackername[BUFLEN];
|
||||||
|
char obname[BUFLEN];
|
||||||
|
int isunarmed = B_FALSE;
|
||||||
|
char buf[BUFLEN];
|
||||||
|
int i;
|
||||||
|
int maxhp;
|
||||||
|
|
||||||
|
moveeffects(lf);
|
||||||
|
if (isdead(lf)) return B_TRUE;
|
||||||
|
|
||||||
|
maxhp = c->type->hp;
|
||||||
|
|
||||||
|
// get names
|
||||||
|
getlfname(lf, attackername);
|
||||||
|
|
||||||
|
// don't need to figure out accuracy - we always hit.
|
||||||
|
|
||||||
|
// determine damage
|
||||||
|
ndam = 0;
|
||||||
|
//if (unarmedflag && (unarmedflag->val[0] != NA)) {
|
||||||
|
dam[ndam] = getdamroll(wep, NULL, damflag);
|
||||||
|
|
||||||
|
// modify for strength
|
||||||
|
if (!hasflag(wep->flags, F_NOSTRDAMMOD) && !lfhasflag(lf, F_NOSTRDAMMOD)) {
|
||||||
|
dam[ndam] = (int)((float)dam[ndam] * getstrdammod(lf));
|
||||||
|
}
|
||||||
|
|
||||||
|
// damtype?
|
||||||
|
damtype[ndam] = getdamtype(wep);
|
||||||
|
ndam++;
|
||||||
|
|
||||||
|
// don't need to check for blessed vs mosnters
|
||||||
|
|
||||||
|
// determine extra damage
|
||||||
|
getextradamwep(wep, &dam[0], &damtype[0], &ndam);
|
||||||
|
getextradamlf(lf, &dam[0], &damtype[0], &ndam);
|
||||||
|
|
||||||
|
|
||||||
|
for (i = 0; i < ndam; i++) {
|
||||||
|
// announce the hit
|
||||||
|
construct_hit_string(lf, NULL, attackername, c->type->name, NULL, wep, damtype[i], dam[i], maxhp, i, B_FALSE, B_FALSE, B_FALSE, isunarmed, buf);
|
||||||
|
|
||||||
|
if (strlen(buf)) {
|
||||||
|
msg("%s", buf);
|
||||||
|
}
|
||||||
|
if (!isplayer(lf) && !cansee(player, lf)) {
|
||||||
|
char noisebuf[BUFLEN];
|
||||||
|
int vol;
|
||||||
|
switch (c->type->material->id) {
|
||||||
|
case MT_METAL:
|
||||||
|
strcpy(noisebuf, "a metallic clanging.");
|
||||||
|
vol = 4;
|
||||||
|
break;
|
||||||
|
case MT_GLASS:
|
||||||
|
strcpy(noisebuf, "cracking glass.");
|
||||||
|
vol = 4;
|
||||||
|
break;
|
||||||
|
case MT_WOOD:
|
||||||
|
case MT_DRAGONWOOD:
|
||||||
|
strcpy(noisebuf, "splintering wood.");
|
||||||
|
vol = 4;
|
||||||
|
break;
|
||||||
|
case MT_BONE:
|
||||||
|
case MT_STONE:
|
||||||
|
strcpy(noisebuf, "a dull thumping.");
|
||||||
|
vol = 3;
|
||||||
|
break;
|
||||||
|
case MT_GOLD:
|
||||||
|
case MT_SILVER:
|
||||||
|
case MT_LEATHER:
|
||||||
|
strcpy(noisebuf, "a dull thumping.");
|
||||||
|
vol = 2;
|
||||||
|
break;
|
||||||
|
case MT_PAPER:
|
||||||
|
case MT_WETPAPER:
|
||||||
|
case MT_RUBBER:
|
||||||
|
strcpy(noisebuf, "a dull thumping.");
|
||||||
|
vol = 1;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
strcpy(noisebuf, "something being hit.");
|
||||||
|
vol = 3;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
noise(c, NULL, NC_OTHER, vol, noisebuf, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((i == 0) && (wep->type->id == OT_FISTS) && hasflag(c->type->material->flags, F_HARDNESS)) {
|
||||||
|
object_t *gloves;
|
||||||
|
gloves = getequippedob(lf->pack, BP_HANDS);
|
||||||
|
if (gloves && hasflag(gloves->flags, F_HARDNESS)) {
|
||||||
|
// ok
|
||||||
|
} else if ((c->type->material->id == MT_WOOD) && (getskill(lf, SK_UNARMED) >= PR_ADEPT)) {
|
||||||
|
// ok
|
||||||
|
} else {
|
||||||
|
char buf[BUFLEN];
|
||||||
|
snprintf(buf, BUFLEN, "punching %s", obname);
|
||||||
|
if ( losehp(lf, 1, DT_BASH, lf, buf)) {
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
msg("^bOw!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// smash wood bonus
|
||||||
|
if ((wep->type->id == OT_FISTS) &&
|
||||||
|
(c->type->material->id == MT_WOOD) &&
|
||||||
|
(getskill(lf, SK_UNARMED) >= PR_ADEPT)) {
|
||||||
|
dam[i] += rnd(1,6);
|
||||||
|
}
|
||||||
|
|
||||||
|
// adjust dam
|
||||||
|
adjustdammaterial(&dam[i], damtype[i], c->type->material->id);
|
||||||
|
|
||||||
|
if (dam[i] > 0) {
|
||||||
|
// wall loses hp
|
||||||
|
c->hp -= dam[i];
|
||||||
|
if (c->hp <= 0) {
|
||||||
|
char cellname[BUFLEN];
|
||||||
|
int shattered = B_FALSE;
|
||||||
|
enum MATERIAL cellmat;
|
||||||
|
// remember cell properties
|
||||||
|
sprintf(cellname, "%s %s", needan(c->type->name) ? "An" : "A", c->type->name);
|
||||||
|
cellmat = c->type->material->id;
|
||||||
|
// cell dies (have to do this before calling fragments())
|
||||||
|
setcelltype(c, c->map->habitat->emptycelltype);
|
||||||
|
// announce
|
||||||
|
if (haslos(player, c)) {
|
||||||
|
msg("%s %s!", cellname, shattered ? "shatters" : "is destroyed");
|
||||||
|
}
|
||||||
|
// shatter?
|
||||||
|
if (willshatter(cellmat)) {
|
||||||
|
char what[BUFLEN];
|
||||||
|
shattered = B_TRUE;
|
||||||
|
noise(c, NULL, NC_OTHER, SV_CAR, "something shattering.", NULL);
|
||||||
|
if (getshardobname(cellmat, what)) {
|
||||||
|
fragments(c, what, 0, 3); // TODO: use speed so shards will hit lfs
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} // end foreach damtype
|
||||||
|
|
||||||
|
// no special weapon effects on cells.
|
||||||
|
|
||||||
|
// weapon gets damaged ?
|
||||||
|
if (wep && (ndam > 0)) {
|
||||||
|
if (wepdullable(wep)) {
|
||||||
|
// weapon gets duller
|
||||||
|
if (rnd(1,2)) makeduller(wep, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return B_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
enum DAMTYPE basedamagetype(enum DAMTYPE dt) {
|
enum DAMTYPE basedamagetype(enum DAMTYPE dt) {
|
||||||
switch (dt) {
|
switch (dt) {
|
||||||
case DT_HEAT:
|
case DT_HEAT:
|
||||||
|
|
1
attack.h
1
attack.h
|
@ -5,6 +5,7 @@ void applyarmourdamreduction(lifeform_t *lf, object_t *wep, int reduceamt, int *
|
||||||
int attackcell(lifeform_t *lf, cell_t *c, int force);
|
int attackcell(lifeform_t *lf, cell_t *c, int force);
|
||||||
int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag);
|
int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag);
|
||||||
int attackob(lifeform_t *lf, object_t *o, object_t *wep, flag_t *damflag);
|
int attackob(lifeform_t *lf, object_t *o, object_t *wep, flag_t *damflag);
|
||||||
|
int attackwall(lifeform_t *lf, cell_t *c, object_t *wep, flag_t *damflag);
|
||||||
enum DAMTYPE basedamagetype(enum DAMTYPE dt);
|
enum DAMTYPE basedamagetype(enum DAMTYPE dt);
|
||||||
int check_for_block(lifeform_t *lf, lifeform_t *victim, int dam, enum DAMTYPE damtype, int difficulty, char *attackname);
|
int check_for_block(lifeform_t *lf, lifeform_t *victim, int dam, enum DAMTYPE damtype, int difficulty, char *attackname);
|
||||||
//void confereffects(flagpile_t *fp, lifeform_t *victim);
|
//void confereffects(flagpile_t *fp, lifeform_t *victim);
|
||||||
|
|
26
data.c
26
data.c
|
@ -2189,6 +2189,9 @@ void initobjects(void) {
|
||||||
addflag(lastot->flags, F_VALUE, 10, NA, NA, NULL);
|
addflag(lastot->flags, F_VALUE, 10, NA, NA, NULL);
|
||||||
addot(OT_POT_CANINETRACKING, "potion of canine tracking", "Mimics the effects of a 'canine tracking' spell.", MT_GLASS, 1, OC_POTION, SZ_TINY);
|
addot(OT_POT_CANINETRACKING, "potion of canine tracking", "Mimics the effects of a 'canine tracking' spell.", MT_GLASS, 1, OC_POTION, SZ_TINY);
|
||||||
addflag(lastot->flags, F_RARITY, H_ALL, 100, RR_COMMON, NULL);
|
addflag(lastot->flags, F_RARITY, H_ALL, 100, RR_COMMON, NULL);
|
||||||
|
addot(OT_POT_GROWTH, "potion of growth", "A magical liquid which causes the imbiber's body to instantly undergo rapid growth.", MT_GLASS, 1, OC_POTION, SZ_TINY);
|
||||||
|
addflag(lastot->flags, F_RARITY, H_ALL, 100, RR_COMMON, NULL);
|
||||||
|
addflag(lastot->flags, F_VALUE, 50, NA, NA, NULL);
|
||||||
|
|
||||||
addot(OT_POT_HEALINGMIN, "potion of minor healing", "Restores 1-10 health to whoever drinks it.", MT_GLASS, 1, OC_POTION, SZ_TINY);
|
addot(OT_POT_HEALINGMIN, "potion of minor healing", "Restores 1-10 health to whoever drinks it.", MT_GLASS, 1, OC_POTION, SZ_TINY);
|
||||||
addflag(lastot->flags, F_RARITY, H_ALL, 100, NA, NULL);
|
addflag(lastot->flags, F_RARITY, H_ALL, 100, NA, NULL);
|
||||||
|
@ -2830,7 +2833,7 @@ void initobjects(void) {
|
||||||
addflag(lastot->flags, F_SPELLLEVEL, 1, NA, NA, NULL);
|
addflag(lastot->flags, F_SPELLLEVEL, 1, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_MAXPOWER, 1, NA, NA, NULL);
|
addflag(lastot->flags, F_MAXPOWER, 1, NA, NA, NULL);
|
||||||
// l2
|
// l2
|
||||||
addot(OT_S_BLADEBURN, "bladeburn", "Ignites the target's bladed weapon, causing it to temporarily deal fire damage. The spell's power determines how long it will last.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
addot(OT_S_BLADEBURN, "bladeburn", "Ignites the caster's weapon, causing it to temporarily deal fire damage. The spell's power determines how long it will last.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "The spell's power determines its duration.");
|
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "The spell's power determines its duration.");
|
||||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, NA, NA, NULL);
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_ENCHANTMENT, NA, NA, NULL);
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_ENCHANTMENT, NA, NA, NULL);
|
||||||
|
@ -3467,6 +3470,14 @@ void initobjects(void) {
|
||||||
addflag(lastot->flags, F_AICASTTOATTACK, ST_ANYWHERE, NA, NA, NULL);
|
addflag(lastot->flags, F_AICASTTOATTACK, ST_ANYWHERE, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_LOSLOF, B_FALSE, LOF_DONTNEED, NA, NULL);
|
addflag(lastot->flags, F_LOSLOF, B_FALSE, LOF_DONTNEED, NA, NULL);
|
||||||
// l2
|
// l2
|
||||||
|
addot(OT_S_SIZEUP, "unnatural growth", "Causes the caster's body to grow in size.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_MODIFICATION, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_SPELLLEVEL, 2, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_MAXPOWER, 1, NA, NA, NULL);
|
||||||
|
addot(OT_S_SIZEDOWN, "unnatural shrinkage", "Causes the caster's body to shrink in size.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_MODIFICATION, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_SPELLLEVEL, 2, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_MAXPOWER, 1, NA, NA, NULL);
|
||||||
addot(OT_S_DARKNESS, "darkness", "Permenantly darkens the area around the caster.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
addot(OT_S_DARKNESS, "darkness", "Permenantly darkens the area around the caster.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "At Power III, you can control where the darkness appears.");
|
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "At Power III, you can control where the darkness appears.");
|
||||||
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "At Power VIII, the darkness becomes permenant.");
|
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "At Power VIII, the darkness becomes permenant.");
|
||||||
|
@ -3485,6 +3496,7 @@ void initobjects(void) {
|
||||||
addflag(lastot->flags, F_TARGETTEDSPELL, TT_MONSTER, NA, NA, NULL);
|
addflag(lastot->flags, F_TARGETTEDSPELL, TT_MONSTER, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_AICASTTOATTACK, ST_VICTIM, NA, NA, NULL);
|
addflag(lastot->flags, F_AICASTTOATTACK, ST_VICTIM, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_AICASTTOFLEE, ST_VICTIM, NA, NA, NULL);
|
addflag(lastot->flags, F_AICASTTOFLEE, ST_VICTIM, NA, NA, NULL);
|
||||||
|
|
||||||
// l3
|
// l3
|
||||||
addot(OT_S_INVISIBILITY, "invisibility", "Temporarily renders the target invisible.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
addot(OT_S_INVISIBILITY, "invisibility", "Temporarily renders the target invisible.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "The spell's power determines how long the invisibility will last.");
|
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "The spell's power determines how long the invisibility will last.");
|
||||||
|
@ -5290,7 +5302,6 @@ void initobjects(void) {
|
||||||
addflag(lastot->flags, F_RARITY, H_ALL, 100, RR_COMMON, NULL);
|
addflag(lastot->flags, F_RARITY, H_ALL, 100, RR_COMMON, NULL);
|
||||||
addflag(lastot->flags, F_GOESON, BP_BODY, NA, NA, NULL);
|
addflag(lastot->flags, F_GOESON, BP_BODY, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_ARMOURRATING, 5, NA, NA, NULL);
|
addflag(lastot->flags, F_ARMOURRATING, 5, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_EQUIPCONFER, F_ARMOURPENALTY, 10, 10, NULL);
|
|
||||||
addflag(lastot->flags, F_EQUIPCONFER, F_DTIMMUNE, DT_FIRE, NA, NULL);
|
addflag(lastot->flags, F_EQUIPCONFER, F_DTIMMUNE, DT_FIRE, NA, NULL);
|
||||||
addflag(lastot->flags, F_DTIMMUNE, DT_FIRE, NA, NA, NULL);
|
addflag(lastot->flags, F_DTIMMUNE, DT_FIRE, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_OBHP, 20, 20, NA, NULL);
|
addflag(lastot->flags, F_OBHP, 20, 20, NA, NULL);
|
||||||
|
@ -5781,9 +5792,10 @@ void initobjects(void) {
|
||||||
addflag(lastot->flags, F_ENCHANTABLE, B_TRUE, NA, NA, NULL);
|
addflag(lastot->flags, F_ENCHANTABLE, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_IDWHENUSED, B_TRUE, NA, NA, NULL);
|
addflag(lastot->flags, F_IDWHENUSED, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_VALUE, 350, NA, NA, NULL);
|
addflag(lastot->flags, F_VALUE, 350, NA, NA, NULL);
|
||||||
addot(OT_RING_INVIS, "ring of invisibility", "Renders the wearer invisible.", MT_METAL, 0.1, OC_RING, SZ_MINI);
|
addot(OT_RING_INVIS, "ring of invisibility", "Renders the wearer invisible - but drains the wearer's health at the same time.", MT_METAL, 0.1, OC_RING, SZ_MINI);
|
||||||
addflag(lastot->flags, F_RARITY, H_ALL, 75, RR_UNCOMMON, "");
|
addflag(lastot->flags, F_RARITY, H_ALL, 75, RR_UNCOMMON, "");
|
||||||
addflag(lastot->flags, F_EQUIPCONFER, F_INVISIBLE, NA, NA, NULL);
|
addflag(lastot->flags, F_EQUIPCONFER, F_INVISIBLE, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_EQUIPCONFER, F_HPDRAIN, 1, DT_DIRECT, "life force draining");
|
||||||
addflag(lastot->flags, F_VALUE, 400, NA, NA, NULL);
|
addflag(lastot->flags, F_VALUE, 400, NA, NA, NULL);
|
||||||
addot(OT_RING_INVULN, "ring of invulnerability", "Grants the caster complete immunity to physical harm.", MT_METAL, 0.1, OC_RING, SZ_MINI);
|
addot(OT_RING_INVULN, "ring of invulnerability", "Grants the caster complete immunity to physical harm.", MT_METAL, 0.1, OC_RING, SZ_MINI);
|
||||||
addflag(lastot->flags, F_EQUIPCONFER, F_INVULNERABLE, NA, NA, NULL);
|
addflag(lastot->flags, F_EQUIPCONFER, F_INVULNERABLE, NA, NA, NULL);
|
||||||
|
@ -6984,6 +6996,7 @@ void initobjects(void) {
|
||||||
|
|
||||||
void initoptions(void) {
|
void initoptions(void) {
|
||||||
addoption(OPT_ALWAYSSHOWTRAILS, "always show trail objects", B_FALSE);
|
addoption(OPT_ALWAYSSHOWTRAILS, "always show trail objects", B_FALSE);
|
||||||
|
addoption(OPT_STOPRUNONNOISE, "stop running if sound heard", B_TRUE);
|
||||||
}
|
}
|
||||||
|
|
||||||
void initrace(void) {
|
void initrace(void) {
|
||||||
|
@ -8871,7 +8884,7 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_NOISETEXT, N_WALK, 1, NA, "^slurping");
|
addflag(lastrace->flags, F_NOISETEXT, N_WALK, 1, NA, "^slurping");
|
||||||
addflag(lastrace->flags, F_DTIMMUNE, DT_ACID, B_TRUE, NA, NULL);
|
addflag(lastrace->flags, F_DTIMMUNE, DT_ACID, B_TRUE, NA, NULL);
|
||||||
addflag(lastrace->flags, F_AUTOCREATEOB, 0, NA, NA, "puddle of acid");
|
addflag(lastrace->flags, F_AUTOCREATEOB, 0, NA, NA, "puddle of acid");
|
||||||
addflag(lastrace->flags, F_DIESPLATTER, 3, NA, NA, "splash of acid");
|
addflag(lastrace->flags, F_DIESPLATTER, 3, 0, NA, "splash of acid");
|
||||||
addflag(lastrace->flags, F_MORALE, 30, NA, NA, NULL);
|
addflag(lastrace->flags, F_MORALE, 30, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_DEAF, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_DEAF, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_NOFLEE, 5, NA, NA, NULL);
|
addflag(lastrace->flags, F_NOFLEE, 5, NA, NA, NULL);
|
||||||
|
@ -9008,6 +9021,7 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_STARTSKILL, SK_PERCEPTION, PR_BEGINNER, NA, NULL);
|
addflag(lastrace->flags, F_STARTSKILL, SK_PERCEPTION, PR_BEGINNER, NA, NULL);
|
||||||
addflag(lastrace->flags, F_NOCTURNAL, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_NOCTURNAL, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_REVIVETIMER, 0, 25, R_TROLL, NULL);
|
||||||
|
|
||||||
addrace(R_XAT, "xat", 2, 'x', C_BROWN, MT_FLESH, RC_ANIMAL, "Xats are wild pigs with the claws of a dog.");
|
addrace(R_XAT, "xat", 2, 'x', C_BROWN, MT_FLESH, RC_ANIMAL, "Xats are wild pigs with the claws of a dog.");
|
||||||
setbodytype(lastrace, BT_QUADRAPED);
|
setbodytype(lastrace, BT_QUADRAPED);
|
||||||
|
@ -9875,7 +9889,7 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_NOISETEXT, N_WALK, 1, NA, "^slurping");
|
addflag(lastrace->flags, F_NOISETEXT, N_WALK, 1, NA, "^slurping");
|
||||||
addflag(lastrace->flags, F_DTIMMUNE, DT_ACID, B_TRUE, NA, NULL);
|
addflag(lastrace->flags, F_DTIMMUNE, DT_ACID, B_TRUE, NA, NULL);
|
||||||
addflag(lastrace->flags, F_AUTOCREATEOB, 0, NA, NA, "puddle of acid");
|
addflag(lastrace->flags, F_AUTOCREATEOB, 0, NA, NA, "puddle of acid");
|
||||||
addflag(lastrace->flags, F_DIESPLATTER, 3, NA, NA, "splash of acid");
|
addflag(lastrace->flags, F_DIESPLATTER, 3, 0, NA, "splash of acid");
|
||||||
addflag(lastrace->flags, F_MAXATTACKS, 1, 1, NA, NULL);
|
addflag(lastrace->flags, F_MAXATTACKS, 1, 1, NA, NULL);
|
||||||
addflag(lastrace->flags, F_NOSPELLS, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_NOSPELLS, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_SEEINDARK, 3, NA, NA, NULL);
|
addflag(lastrace->flags, F_SEEINDARK, 3, NA, NA, NULL);
|
||||||
|
@ -9908,7 +9922,7 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_BREATHWATER, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_BREATHWATER, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_AUTOCREATEOB, 0, NA, NA, "puddle of slime");
|
addflag(lastrace->flags, F_AUTOCREATEOB, 0, NA, NA, "puddle of slime");
|
||||||
addflag(lastrace->flags, F_DIESPLATTER, 3, NA, NA, "puddle of slime");
|
addflag(lastrace->flags, F_DIESPLATTER, 3, 0, NA, "puddle of slime");
|
||||||
addrace(R_SNAKE, "brown snake", 3, 's', C_BROWN, MT_FLESH, RC_ANIMAL, "Common venomous snakes.");
|
addrace(R_SNAKE, "brown snake", 3, 's', C_BROWN, MT_FLESH, RC_ANIMAL, "Common venomous snakes.");
|
||||||
setbodytype(lastrace, BT_SNAKE);
|
setbodytype(lastrace, BT_SNAKE);
|
||||||
addflag(lastrace->flags, F_RARITY, H_DUNGEON, NA, RR_COMMON, NULL);
|
addflag(lastrace->flags, F_RARITY, H_DUNGEON, NA, RR_COMMON, NULL);
|
||||||
|
|
BIN
data/hiscores.db
BIN
data/hiscores.db
Binary file not shown.
22
defs.h
22
defs.h
|
@ -65,6 +65,8 @@
|
||||||
// Booleans
|
// Booleans
|
||||||
#define B_FALSE (0)
|
#define B_FALSE (0)
|
||||||
#define B_TRUE (-1)
|
#define B_TRUE (-1)
|
||||||
|
#define B_MAYBE (-2)
|
||||||
|
|
||||||
#define B_FORCE (-2)
|
#define B_FORCE (-2)
|
||||||
#define B_ONPURPOSE (-1)
|
#define B_ONPURPOSE (-1)
|
||||||
#define B_CHANGEDIR (-1)
|
#define B_CHANGEDIR (-1)
|
||||||
|
@ -1213,6 +1215,7 @@ enum OBTYPE {
|
||||||
OT_POT_EXPERIENCE,
|
OT_POT_EXPERIENCE,
|
||||||
OT_POT_FURY,
|
OT_POT_FURY,
|
||||||
OT_POT_GASEOUSFORM,
|
OT_POT_GASEOUSFORM,
|
||||||
|
OT_POT_GROWTH,
|
||||||
OT_POT_HEALING,
|
OT_POT_HEALING,
|
||||||
OT_POT_HEALINGMIN,
|
OT_POT_HEALINGMIN,
|
||||||
OT_POT_HEALINGMAJ,
|
OT_POT_HEALINGMAJ,
|
||||||
|
@ -1394,6 +1397,8 @@ enum OBTYPE {
|
||||||
OT_S_POLYMORPH,
|
OT_S_POLYMORPH,
|
||||||
OT_S_POLYMORPHRND,
|
OT_S_POLYMORPHRND,
|
||||||
OT_S_QUICKENSTONE,
|
OT_S_QUICKENSTONE,
|
||||||
|
OT_S_SIZEUP,
|
||||||
|
OT_S_SIZEDOWN,
|
||||||
// nature / enviromancy
|
// nature / enviromancy
|
||||||
OT_S_BARKSKIN,
|
OT_S_BARKSKIN,
|
||||||
OT_S_CALLLIGHTNING,
|
OT_S_CALLLIGHTNING,
|
||||||
|
@ -2083,6 +2088,9 @@ enum FLAG {
|
||||||
F_NOQUALITY, // can't be masterwork / shoddy
|
F_NOQUALITY, // can't be masterwork / shoddy
|
||||||
F_CORPSEOF, // this is a corpse of montype val0.
|
F_CORPSEOF, // this is a corpse of montype val0.
|
||||||
// text is how it died.
|
// text is how it died.
|
||||||
|
F_REVIVETIMER, // v0 = cur, v1 = max. v0 incremenets each tick.
|
||||||
|
// when v0 == v1, this object changes into lf of race
|
||||||
|
// v2.
|
||||||
F_DTCONVERT, // damtype val0 converts this to f->text
|
F_DTCONVERT, // damtype val0 converts this to f->text
|
||||||
F_DTCREATEOB, // damtype val0 creates object f->text here
|
F_DTCREATEOB, // damtype val0 creates object f->text here
|
||||||
// v1 = radius to burst in
|
// v1 = radius to burst in
|
||||||
|
@ -2392,8 +2400,12 @@ enum FLAG {
|
||||||
// v0 is the order in which these are displayed (0-5)
|
// v0 is the order in which these are displayed (0-5)
|
||||||
F_BONDESC, // text=extra description for playable races.
|
F_BONDESC, // text=extra description for playable races.
|
||||||
// v0 is the display order.
|
// v0 is the display order.
|
||||||
|
// v1=true means 'don't display this one during
|
||||||
|
// player race selection)
|
||||||
F_PENDESC, // text=extra description for playable races.
|
F_PENDESC, // text=extra description for playable races.
|
||||||
// v0 is the display order.
|
// v0 is the display order.
|
||||||
|
// v1=true means 'don't display this one during
|
||||||
|
// player race selection)
|
||||||
//F_SPELLLETTER, // text[0] = letter to cast this spell
|
//F_SPELLLETTER, // text[0] = letter to cast this spell
|
||||||
F_AICASTTOFLEE, // AI can cast this spell to help flee/heal
|
F_AICASTTOFLEE, // AI can cast this spell to help flee/heal
|
||||||
// v0 is who to target
|
// v0 is who to target
|
||||||
|
@ -2435,6 +2447,9 @@ enum FLAG {
|
||||||
// unconscious. announce it when you wake up.
|
// unconscious. announce it when you wake up.
|
||||||
F_TURNED, // lf turned this turn.
|
F_TURNED, // lf turned this turn.
|
||||||
F_PRAYEDTO, // player has prayed to this god before.
|
F_PRAYEDTO, // player has prayed to this god before.
|
||||||
|
F_HPDRAIN, // lf loses v0 hit points eath turn.
|
||||||
|
// v1 = damtype
|
||||||
|
// text = killer damage string
|
||||||
F_GAVEMONEY, // v0 tracks how much money we gave away this turn
|
F_GAVEMONEY, // v0 tracks how much money we gave away this turn
|
||||||
// used for r_godgreed anger effects.
|
// used for r_godgreed anger effects.
|
||||||
F_CLIMBING, // lf is currently climbing a wall
|
F_CLIMBING, // lf is currently climbing a wall
|
||||||
|
@ -2600,6 +2615,8 @@ enum FLAG {
|
||||||
// e = exits
|
// e = exits
|
||||||
// s = shops
|
// s = shops
|
||||||
// t = traps
|
// t = traps
|
||||||
|
// o = rare Objects
|
||||||
|
// m = rare Monsters
|
||||||
// eg: text=="st" means they know of shops+traps
|
// eg: text=="st" means they know of shops+traps
|
||||||
F_NOJOBTEXT, // this lf's name is 'a xxx', not 'a xxx wizard' etc
|
F_NOJOBTEXT, // this lf's name is 'a xxx', not 'a xxx wizard' etc
|
||||||
F_LASTDIR, // this is the last direction we moved.
|
F_LASTDIR, // this is the last direction we moved.
|
||||||
|
@ -2707,6 +2724,7 @@ enum FLAG {
|
||||||
F_DIESPLATTER, // this lf will splatter objcets of type 'text'
|
F_DIESPLATTER, // this lf will splatter objcets of type 'text'
|
||||||
// when it dies.
|
// when it dies.
|
||||||
// v0 = max distance to splatter (or UNLIMITED)
|
// v0 = max distance to splatter (or UNLIMITED)
|
||||||
|
// v1 = how fast to shoot objects (0 = just place them)
|
||||||
// text = type of object to splatter
|
// text = type of object to splatter
|
||||||
F_OBESE, // double base weight for race!
|
F_OBESE, // double base weight for race!
|
||||||
F_ORIGRACE, // original player race (if you polymorphed)
|
F_ORIGRACE, // original player race (if you polymorphed)
|
||||||
|
@ -2967,6 +2985,9 @@ enum FLAG {
|
||||||
// v0 is pct chance of door (as opposed to empty
|
// v0 is pct chance of door (as opposed to empty
|
||||||
// doorway with no door).
|
// doorway with no door).
|
||||||
F_AUTOPOPULATE, // fill this vault with obs/mons/pillars like normal rooms
|
F_AUTOPOPULATE, // fill this vault with obs/mons/pillars like normal rooms
|
||||||
|
F_MAINTAINEDGE, // when calling fixreachability(), only allow
|
||||||
|
// corridors to enter this vault through cells
|
||||||
|
// marked as exits.
|
||||||
F_NORANDOM, // this vault does not randomly appear
|
F_NORANDOM, // this vault does not randomly appear
|
||||||
// OR this spell doesn't apear in books
|
// OR this spell doesn't apear in books
|
||||||
F_VAULTATOB, // v0/1=x/y, v2=pctchance, text=obname
|
F_VAULTATOB, // v0/1=x/y, v2=pctchance, text=obname
|
||||||
|
@ -3262,6 +3283,7 @@ typedef struct warning_s {
|
||||||
|
|
||||||
enum OPTION {
|
enum OPTION {
|
||||||
OPT_ALWAYSSHOWTRAILS,
|
OPT_ALWAYSSHOWTRAILS,
|
||||||
|
OPT_STOPRUNONNOISE,
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef struct option_s {
|
typedef struct option_s {
|
||||||
|
|
6
flag.c
6
flag.c
|
@ -469,8 +469,10 @@ int fpisbad(flagpile_t *fp) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void copyflag(flagpile_t *dst, flagpile_t *src, enum FLAG id) {
|
// returns # of flags copied
|
||||||
|
int copyflag(flagpile_t *dst, flagpile_t *src, enum FLAG id) {
|
||||||
flag_t *f;
|
flag_t *f;
|
||||||
|
int ndone = 0;
|
||||||
for (f = src->first ; f ; f = f->next) {
|
for (f = src->first ; f ; f = f->next) {
|
||||||
// gone past the requrested id's number - ie. it's not there.
|
// gone past the requrested id's number - ie. it's not there.
|
||||||
if (f->id > id) break;
|
if (f->id > id) break;
|
||||||
|
@ -487,8 +489,10 @@ void copyflag(flagpile_t *dst, flagpile_t *src, enum FLAG id) {
|
||||||
f->altval->val[2],
|
f->altval->val[2],
|
||||||
f->altval->text);
|
f->altval->text);
|
||||||
}
|
}
|
||||||
|
ndone++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return ndone;
|
||||||
}
|
}
|
||||||
|
|
||||||
void copyflags(flagpile_t *dst, flagpile_t *src, int lifetime) {
|
void copyflags(flagpile_t *dst, flagpile_t *src, int lifetime) {
|
||||||
|
|
2
flag.h
2
flag.h
|
@ -14,7 +14,7 @@ void changeflagtext(flag_t *f, char *newtext);
|
||||||
void checkmapflags(map_t *m);
|
void checkmapflags(map_t *m);
|
||||||
int fpisbad(flagpile_t *fp);
|
int fpisbad(flagpile_t *fp);
|
||||||
void checkflagpile(flagpile_t *fp);
|
void checkflagpile(flagpile_t *fp);
|
||||||
void copyflag(flagpile_t *dst, flagpile_t *src, enum FLAG id);
|
int copyflag(flagpile_t *dst, flagpile_t *src, enum FLAG id);
|
||||||
void copyflags(flagpile_t *dst, flagpile_t *src, int lifetime);
|
void copyflags(flagpile_t *dst, flagpile_t *src, int lifetime);
|
||||||
int countflags(flagpile_t *fp);
|
int countflags(flagpile_t *fp);
|
||||||
int flagcausesloscalc(enum FLAG fid);
|
int flagcausesloscalc(enum FLAG fid);
|
||||||
|
|
60
io.c
60
io.c
|
@ -3472,6 +3472,7 @@ void describeob(object_t *o) {
|
||||||
void describerace(enum RACE rid) {
|
void describerace(enum RACE rid) {
|
||||||
char buf[BUFLEN];
|
char buf[BUFLEN];
|
||||||
char *buf2;
|
char *buf2;
|
||||||
|
char ch;
|
||||||
int x,y;
|
int x,y;
|
||||||
race_t *r;
|
race_t *r;
|
||||||
cls();
|
cls();
|
||||||
|
@ -3487,16 +3488,18 @@ void describerace(enum RACE rid) {
|
||||||
wmove(mainwin, 2, 0);
|
wmove(mainwin, 2, 0);
|
||||||
|
|
||||||
buf2 = malloc(HUGEBUFLEN * sizeof(char));
|
buf2 = malloc(HUGEBUFLEN * sizeof(char));
|
||||||
makedesc_race(rid, buf2, B_TRUE);
|
makedesc_race(rid, buf2, B_TRUE, B_FALSE);
|
||||||
//textwithcol(mainwin, buf2);
|
//textwithcol(mainwin, buf2);
|
||||||
getyx(mainwin,y,x);
|
getyx(mainwin,y,x);
|
||||||
wrapprint(mainwin, &y, &x, "%s", buf2);
|
ch = wrapprint(mainwin, &y, &x, "%s", buf2);
|
||||||
free(buf2);
|
free(buf2);
|
||||||
|
|
||||||
wrefresh(mainwin);
|
wrefresh(mainwin);
|
||||||
|
|
||||||
// wait for key
|
// wait for key, unless we quit from the 'more' prompt
|
||||||
|
if (ch != 27) {
|
||||||
getch();
|
getch();
|
||||||
|
}
|
||||||
real_clearmsg(B_TRUE);
|
real_clearmsg(B_TRUE);
|
||||||
restoregamewindows();
|
restoregamewindows();
|
||||||
}
|
}
|
||||||
|
@ -4163,6 +4166,7 @@ void docomms_areainfo(char *who, flagpile_t *fp, lifeform_t *lf) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// veryrare objects
|
// veryrare objects
|
||||||
|
if (strchr(knowflag->text, 'o')) {
|
||||||
ndone = 0;
|
ndone = 0;
|
||||||
for (y = 0; y < player->cell->map->h ; y++) {
|
for (y = 0; y < player->cell->map->h ; y++) {
|
||||||
for (x = 0; x < player->cell->map->w; x++) {
|
for (x = 0; x < player->cell->map->w; x++) {
|
||||||
|
@ -4179,6 +4183,7 @@ void docomms_areainfo(char *who, flagpile_t *fp, lifeform_t *lf) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (ndone) needredraw = B_TRUE;
|
if (ndone) needredraw = B_TRUE;
|
||||||
|
}
|
||||||
// staircases
|
// staircases
|
||||||
if (strchr(knowflag->text, 'e')) {
|
if (strchr(knowflag->text, 'e')) {
|
||||||
ndone = 0;
|
ndone = 0;
|
||||||
|
@ -4252,6 +4257,7 @@ void docomms_areadangers(char *who, flagpile_t *fp, lifeform_t *lf) {
|
||||||
totdone += ndone;
|
totdone += ndone;
|
||||||
}
|
}
|
||||||
// veryrare monsters
|
// veryrare monsters
|
||||||
|
if (strchr(knowflag->text, 'm')) {
|
||||||
gethitdicerange(getmapdifficulty(player->cell->map), &min,&max, RARITYVARIANCELF, B_FALSE);
|
gethitdicerange(getmapdifficulty(player->cell->map), &min,&max, RARITYVARIANCELF, B_FALSE);
|
||||||
|
|
||||||
ndone = 0;
|
ndone = 0;
|
||||||
|
@ -4283,6 +4289,7 @@ void docomms_areadangers(char *who, flagpile_t *fp, lifeform_t *lf) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
totdone += ndone;
|
totdone += ndone;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
msg("\"I know of no %sdangers in this area.\"", (totdone) ? "other " : "");
|
msg("\"I know of no %sdangers in this area.\"", (totdone) ? "other " : "");
|
||||||
|
@ -6110,7 +6117,7 @@ char *makedesc_ob(object_t *o, char *retbuf) {
|
||||||
return retbuf;
|
return retbuf;
|
||||||
}
|
}
|
||||||
|
|
||||||
char *makedesc_race(enum RACE rid, char *retbuf, int showextra) {
|
char *makedesc_race(enum RACE rid, char *retbuf, int showextra, int forplayersel) {
|
||||||
race_t *r;
|
race_t *r;
|
||||||
char buf[HUGEBUFLEN];
|
char buf[HUGEBUFLEN];
|
||||||
flag_t *retflag[MAXCANDIDATES],*f;
|
flag_t *retflag[MAXCANDIDATES],*f;
|
||||||
|
@ -6176,8 +6183,11 @@ char *makedesc_race(enum RACE rid, char *retbuf, int showextra) {
|
||||||
for (i = 0; i < nretflags; i++) {
|
for (i = 0; i < nretflags; i++) {
|
||||||
f = retflag[i];
|
f = retflag[i];
|
||||||
if (f->val[0] == curidx) {
|
if (f->val[0] == curidx) {
|
||||||
|
if ((f->val[1] == B_TRUE) && forplayersel) {
|
||||||
|
} else {
|
||||||
snprintf(buf, HUGEBUFLEN, "@- %s\n", f->text);
|
snprintf(buf, HUGEBUFLEN, "@- %s\n", f->text);
|
||||||
strncat(retbuf, buf, HUGEBUFLEN);
|
strncat(retbuf, buf, HUGEBUFLEN);
|
||||||
|
}
|
||||||
donesomething = B_TRUE;
|
donesomething = B_TRUE;
|
||||||
curidx++;
|
curidx++;
|
||||||
break;
|
break;
|
||||||
|
@ -6264,7 +6274,7 @@ char *makedesc_race(enum RACE rid, char *retbuf, int showextra) {
|
||||||
case F_ENHANCESMELL: sprintf(buf, "Enhanced sense of smell (range %d)", f->val[0]); break;
|
case F_ENHANCESMELL: sprintf(buf, "Enhanced sense of smell (range %d)", f->val[0]); break;
|
||||||
case F_FLYING: sprintf(buf, "Can fly at will"); break;
|
case F_FLYING: sprintf(buf, "Can fly at will"); break;
|
||||||
case F_HEAVYBLOW: sprintf(buf, "Attacks will knock enemies backwards"); break;
|
case F_HEAVYBLOW: sprintf(buf, "Attacks will knock enemies backwards"); break;
|
||||||
case F_HUMANOID: sprintf(buf, "Can use weapons and armour."); break;
|
case F_HUMANOID: if (!forplayersel) sprintf(buf, "Can use weapons and armour."); break;
|
||||||
case F_LEVITATING: sprintf(buf, "Can levitate at will"); break;
|
case F_LEVITATING: sprintf(buf, "Can levitate at will"); break;
|
||||||
case F_MEDITATES: sprintf(buf, "Meditates to retain awareness while sleeping."); break;
|
case F_MEDITATES: sprintf(buf, "Meditates to retain awareness while sleeping."); break;
|
||||||
case F_MPMOD: if (f->val[0] > 0) sprintf(buf, "+%d Mana", f->val[0]); break;
|
case F_MPMOD: if (f->val[0] > 0) sprintf(buf, "+%d Mana", f->val[0]); break;
|
||||||
|
@ -6313,8 +6323,11 @@ char *makedesc_race(enum RACE rid, char *retbuf, int showextra) {
|
||||||
for (i = 0; i < nretflags; i++) {
|
for (i = 0; i < nretflags; i++) {
|
||||||
f = retflag[i];
|
f = retflag[i];
|
||||||
if (f->val[0] == curidx) {
|
if (f->val[0] == curidx) {
|
||||||
|
if ((f->val[1] == B_TRUE) && forplayersel) {
|
||||||
|
} else {
|
||||||
snprintf(buf, HUGEBUFLEN, "@- %s\n", f->text);
|
snprintf(buf, HUGEBUFLEN, "@- %s\n", f->text);
|
||||||
strncat(retbuf, buf, HUGEBUFLEN);
|
strncat(retbuf, buf, HUGEBUFLEN);
|
||||||
|
}
|
||||||
donesomething = B_TRUE;
|
donesomething = B_TRUE;
|
||||||
curidx++;
|
curidx++;
|
||||||
break;
|
break;
|
||||||
|
@ -6330,7 +6343,7 @@ char *makedesc_race(enum RACE rid, char *retbuf, int showextra) {
|
||||||
switch (f->id) {
|
switch (f->id) {
|
||||||
case F_CARNIVORE: sprintf(buf, "Will only eat meat."); break;
|
case F_CARNIVORE: sprintf(buf, "Will only eat meat."); break;
|
||||||
case F_DEAF: sprintf(buf, "Deaf"); break;
|
case F_DEAF: sprintf(buf, "Deaf"); break;
|
||||||
case F_DIURNAL: sprintf(buf, "Sleeps at night."); break;
|
case F_DIURNAL: if (!forplayersel) sprintf(buf, "Sleeps at night."); break;
|
||||||
case F_DTVULN:
|
case F_DTVULN:
|
||||||
if (!hasflag(doneflags, F_DTVULN)) {
|
if (!hasflag(doneflags, F_DTVULN)) {
|
||||||
if (f->val[0] == DT_ALL) {
|
if (f->val[0] == DT_ALL) {
|
||||||
|
@ -6362,7 +6375,7 @@ char *makedesc_race(enum RACE rid, char *retbuf, int showextra) {
|
||||||
break;
|
break;
|
||||||
case F_MPMOD: if (f->val[0] < 0) sprintf(buf, "%d Mana", f->val[0]); break;
|
case F_MPMOD: if (f->val[0] < 0) sprintf(buf, "%d Mana", f->val[0]); break;
|
||||||
case F_NEEDSWATER: sprintf(buf, "Will suffocate without water"); break;
|
case F_NEEDSWATER: sprintf(buf, "Will suffocate without water"); break;
|
||||||
case F_NOCTURNAL: sprintf(buf, "Sleeps during the day."); break;
|
case F_NOCTURNAL: if (!forplayersel) sprintf(buf, "Sleeps during the day."); break;
|
||||||
case F_NOPACK: sprintf(buf, "Cannot carry objects."); break;
|
case F_NOPACK: sprintf(buf, "Cannot carry objects."); break;
|
||||||
case F_SIZE:
|
case F_SIZE:
|
||||||
if (hasflag(r->flags, F_HUMANOID) && (f->val[0] != SZ_HUMAN)) {
|
if (hasflag(r->flags, F_HUMANOID) && (f->val[0] != SZ_HUMAN)) {
|
||||||
|
@ -6373,7 +6386,9 @@ char *makedesc_race(enum RACE rid, char *retbuf, int showextra) {
|
||||||
sprintf(buf, "Will not leave its home territory."); break;
|
sprintf(buf, "Will not leave its home territory."); break;
|
||||||
break;
|
break;
|
||||||
case F_TAMABLE:
|
case F_TAMABLE:
|
||||||
sprintf(buf, "Susceptible to bribery."); break;
|
if (!forplayersel) {
|
||||||
|
sprintf(buf, "Susceptible to bribery.");
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case F_VEGETARIAN: sprintf(buf, "Will not eat meat."); break;
|
case F_VEGETARIAN: sprintf(buf, "Will not eat meat."); break;
|
||||||
case F_VISRANGEMOD: if (f->val[0] < 0) sprintf(buf, "Reduced vision range (%d)", f->val[0]); break;
|
case F_VISRANGEMOD: if (f->val[0] < 0) sprintf(buf, "Reduced vision range (%d)", f->val[0]); break;
|
||||||
|
@ -8331,7 +8346,9 @@ char getchoicestr(prompt_t *prompt, int useshortcuts, int showallatstart) {
|
||||||
// only print if on the page
|
// only print if on the page
|
||||||
if ((i >= first) && !atbottom) {
|
if ((i >= first) && !atbottom) {
|
||||||
// show heading first
|
// show heading first
|
||||||
|
wattron(mainwin, A_REVERSE);
|
||||||
mvwprintw(mainwin, y, 0, "%s", curheading);
|
mvwprintw(mainwin, y, 0, "%s", curheading);
|
||||||
|
wattroff(mainwin, A_REVERSE);
|
||||||
y++;
|
y++;
|
||||||
}
|
}
|
||||||
doneheading = B_TRUE;
|
doneheading = B_TRUE;
|
||||||
|
@ -12064,20 +12081,21 @@ int warnabout(char *what) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// @ = tab
|
// @ = tab
|
||||||
void wrapprint(WINDOW *win, int *y, int *x, char *format, ... ) {
|
char wrapprint(WINDOW *win, int *y, int *x, char *format, ... ) {
|
||||||
char word[HUGEBUFLEN],buf[HUGEBUFLEN];
|
char word[HUGEBUFLEN],buf[HUGEBUFLEN];
|
||||||
char *p;
|
char *p;
|
||||||
va_list args;
|
va_list args;
|
||||||
int w,nspaces = 0;
|
int w,nspaces = 0,h;
|
||||||
int first = B_TRUE;
|
int first = B_TRUE;
|
||||||
|
|
||||||
va_start(args, format);
|
va_start(args, format);
|
||||||
vsnprintf( buf, HUGEBUFLEN, format, args );
|
vsnprintf( buf, HUGEBUFLEN, format, args );
|
||||||
va_end(args);
|
va_end(args);
|
||||||
|
|
||||||
if (!strlen(buf)) return;
|
if (!strlen(buf)) return '\0';
|
||||||
|
|
||||||
w = getmaxx(win);
|
w = getmaxx(win);
|
||||||
|
h = getmaxy(win);
|
||||||
|
|
||||||
// remember the amount of spaces at the end
|
// remember the amount of spaces at the end
|
||||||
p = buf + strlen(buf) - 1;
|
p = buf + strlen(buf) - 1;
|
||||||
|
@ -12105,7 +12123,25 @@ void wrapprint(WINDOW *win, int *y, int *x, char *format, ... ) {
|
||||||
*x = 0;
|
*x = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (gamemode == GM_GAMESTARTED) {
|
||||||
|
if (*y >= h-2) {
|
||||||
|
char ch;
|
||||||
|
centre(win,C_WHITE, h-1, "--More--");
|
||||||
|
ch = getch();
|
||||||
|
if (ch == 27) { // esc
|
||||||
|
return ch;
|
||||||
|
} else {
|
||||||
|
// clear window
|
||||||
|
wclear(win);
|
||||||
|
*y = 0;
|
||||||
|
*x = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
wmove(win, *y, *x);
|
wmove(win, *y, *x);
|
||||||
|
|
||||||
if (first) {
|
if (first) {
|
||||||
first = B_FALSE;
|
first = B_FALSE;
|
||||||
} else if (*x != 0) {
|
} else if (*x != 0) {
|
||||||
|
@ -12137,6 +12173,8 @@ void wrapprint(WINDOW *win, int *y, int *x, char *format, ... ) {
|
||||||
//wattroff(win, A_BOLD);
|
//wattroff(win, A_BOLD);
|
||||||
setcol(win, C_GREY);
|
setcol(win, C_GREY);
|
||||||
getyx(win, *y, *x);
|
getyx(win, *y, *x);
|
||||||
|
|
||||||
|
return '\0';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
4
io.h
4
io.h
|
@ -106,7 +106,7 @@ int keycodetokey(int keycode, int escseqok);
|
||||||
void listobs(WINDOW *win, object_t **mylist, int *sellist, int *selcount, int firstob, int *counter, int lastline, int *y, char *myletters, int forpickup, int showpoints);
|
void listobs(WINDOW *win, object_t **mylist, int *sellist, int *selcount, int firstob, int *counter, int lastline, int *y, char *myletters, int forpickup, int showpoints);
|
||||||
char *makedesc_god(lifeform_t *god, char *retbuf);
|
char *makedesc_god(lifeform_t *god, char *retbuf);
|
||||||
char *makedesc_ob(object_t *o, char *retbuf);
|
char *makedesc_ob(object_t *o, char *retbuf);
|
||||||
char *makedesc_race(enum RACE rid, char *retbuf, int showextra);
|
char *makedesc_race(enum RACE rid, char *retbuf, int showextra, int forplayersel);
|
||||||
char *makedesc_skill(enum SKILL skid, char *retbuf, enum SKILLLEVEL levhilite);
|
char *makedesc_skill(enum SKILL skid, char *retbuf, enum SKILLLEVEL levhilite);
|
||||||
char *makedesc_spell(objecttype_t *ot, char *retbuf);
|
char *makedesc_spell(objecttype_t *ot, char *retbuf);
|
||||||
void makespellchoicelist(prompt_t *pr, lifeform_t *lf, char *ques, char *ques2, enum SPELLSCHOOL wantschool, int wantunknown, int wantlowmp, int wanttoohard,int mpcutoff);
|
void makespellchoicelist(prompt_t *pr, lifeform_t *lf, char *ques, char *ques2, enum SPELLSCHOOL wantschool, int wantunknown, int wantlowmp, int wanttoohard,int mpcutoff);
|
||||||
|
@ -136,4 +136,4 @@ void tombstone(lifeform_t *lf);
|
||||||
void updatestatus(void);
|
void updatestatus(void);
|
||||||
int updateviewfor(cell_t *cell);
|
int updateviewfor(cell_t *cell);
|
||||||
int warnabout(char *what);
|
int warnabout(char *what);
|
||||||
void wrapprint(WINDOW *win, int *y, int *x, char *format, ... );
|
char wrapprint(WINDOW *win, int *y, int *x, char *format, ... );
|
||||||
|
|
198
lf.c
198
lf.c
|
@ -1,6 +1,7 @@
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <math.h>
|
#include <math.h>
|
||||||
|
#include <signal.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
@ -2546,10 +2547,10 @@ void die(lifeform_t *lf) {
|
||||||
if (vaporised) {
|
if (vaporised) {
|
||||||
switch (rnd(1,2)) {
|
switch (rnd(1,2)) {
|
||||||
case 1:
|
case 1:
|
||||||
fragments(corpsecell, "chunk of flesh", 2, UNLIMITED);
|
fragments(corpsecell, "chunk of flesh", 0, UNLIMITED);
|
||||||
break;
|
break;
|
||||||
case 2:
|
case 2:
|
||||||
fragments(corpsecell, "pool of blood", 2, UNLIMITED);
|
fragments(corpsecell, "pool of blood", 0, UNLIMITED);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
} else if ((lf->lastdamtype == DT_BASH) && lfhasflag(lf, F_FROZEN)) {
|
} else if ((lf->lastdamtype == DT_BASH) && lfhasflag(lf, F_FROZEN)) {
|
||||||
|
@ -2620,6 +2621,11 @@ void die(lifeform_t *lf) {
|
||||||
copyflag(corpse->flags, lf->flags, F_KNOWSABOUT);
|
copyflag(corpse->flags, lf->flags, F_KNOWSABOUT);
|
||||||
copyflag(corpse->flags, lf->flags, F_HOMEMAP);
|
copyflag(corpse->flags, lf->flags, F_HOMEMAP);
|
||||||
|
|
||||||
|
// some corpses will regenerate...
|
||||||
|
if (copyflag(corpse->flags, lf->flags, F_REVIVETIMER)) {
|
||||||
|
killflagsofid(corpse->flags, F_OBHPDRAIN);
|
||||||
|
}
|
||||||
|
|
||||||
// corpse of a player pet?
|
// corpse of a player pet?
|
||||||
if (ispetof(lf, player)) {
|
if (ispetof(lf, player)) {
|
||||||
addflag(corpse->flags, F_PETOF, player->id, NA, NA, NULL);
|
addflag(corpse->flags, F_PETOF, player->id, NA, NA, NULL);
|
||||||
|
@ -2634,6 +2640,14 @@ void die(lifeform_t *lf) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// inherit size from lf
|
||||||
|
f = hasflag(corpse->flags, F_SIZE);
|
||||||
|
if (f) {
|
||||||
|
f->val[0] = getlfsize(lf);
|
||||||
|
} else {
|
||||||
|
addflag(corpse->flags, F_SIZE, getlfsize(lf), NA, NA, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
// remember what killed us.
|
// remember what killed us.
|
||||||
f = hasflag(corpse->flags, F_CORPSEOF);
|
f = hasflag(corpse->flags, F_CORPSEOF);
|
||||||
if (f) {
|
if (f) {
|
||||||
|
@ -2659,7 +2673,7 @@ void die(lifeform_t *lf) {
|
||||||
flag_t *f;
|
flag_t *f;
|
||||||
f = lfhasflag(lf, F_DIESPLATTER);
|
f = lfhasflag(lf, F_DIESPLATTER);
|
||||||
if (f) {
|
if (f) {
|
||||||
fragments(corpsecell, f->text, 1, f->val[0]);
|
fragments(corpsecell, f->text, f->val[1], f->val[0]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} // end if corpsecell
|
} // end if corpsecell
|
||||||
|
@ -2754,6 +2768,13 @@ void genareaknowledge(flagpile_t *fp, int chancemod) {
|
||||||
if (pctchance(75 + chancemod)) {
|
if (pctchance(75 + chancemod)) {
|
||||||
strcat(knownstuff, "e");
|
strcat(knownstuff, "e");
|
||||||
}
|
}
|
||||||
|
// rare monsters/objects? (highish chance)
|
||||||
|
if (pctchance(60 + chancemod)) {
|
||||||
|
strcat(knownstuff, "o");
|
||||||
|
}
|
||||||
|
if (pctchance(60 + chancemod)) {
|
||||||
|
strcat(knownstuff, "m");
|
||||||
|
}
|
||||||
// shops? (med chance)
|
// shops? (med chance)
|
||||||
if (pctchance(50 + chancemod)) {
|
if (pctchance(50 + chancemod)) {
|
||||||
strcat(knownstuff, "s");
|
strcat(knownstuff, "s");
|
||||||
|
@ -4664,13 +4685,13 @@ void gainxp(lifeform_t *lf, long amt) {
|
||||||
lf->xp += amt;
|
lf->xp += amt;
|
||||||
if (isplayer(lf)) statdirty = B_TRUE;
|
if (isplayer(lf)) statdirty = B_TRUE;
|
||||||
assert(lf->xp >= 0);
|
assert(lf->xp >= 0);
|
||||||
}
|
|
||||||
|
|
||||||
// skill xp
|
// skill xp
|
||||||
if (isplayer(lf)) {
|
if (isplayer(lf)) {
|
||||||
int amtneeded;
|
long amtneeded;
|
||||||
|
|
||||||
amtneeded = getspforpoint(lf);
|
amtneeded = getspforpoint(lf);
|
||||||
|
assert(amtneeded > 0);
|
||||||
|
|
||||||
lf->skillxp += amt;
|
lf->skillxp += amt;
|
||||||
|
|
||||||
|
@ -4680,20 +4701,23 @@ void gainxp(lifeform_t *lf, long amt) {
|
||||||
lf->skillxp -= amtneeded;
|
lf->skillxp -= amtneeded;
|
||||||
if (isplayer(lf)) statdirty = B_TRUE;
|
if (isplayer(lf)) statdirty = B_TRUE;
|
||||||
}
|
}
|
||||||
|
// debug!
|
||||||
|
if (newskillpoints >= 3) {
|
||||||
|
raise(SIGINT);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (doxp) {
|
|
||||||
// ready for next level? can only go up ONE level.
|
// ready for next level? can only go up ONE level.
|
||||||
if (lf->xp >= getxpforlev(lf->level + 1)) {
|
if (lf->xp >= getxpforlev(lf->level + 1)) {
|
||||||
gainlevel(lf, B_FALSE); // this will increment 'newlevel'
|
gainlevel(lf, B_FALSE); // this will increment 'newlevel'
|
||||||
}
|
}
|
||||||
}
|
|
||||||
if (newskillpoints) {
|
if (newskillpoints) {
|
||||||
lf->skillpoints += newskillpoints;
|
lf->skillpoints += newskillpoints;
|
||||||
msg("^GYou feel ready to learn a new skill!");
|
msg("^GYou feel ready to learn a new skill!");
|
||||||
lf->totskillpoints += newskillpoints;
|
lf->totskillpoints += newskillpoints;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int fovlist_contains(int *endx, int *endy, int nendcells, int x, int y) {
|
int fovlist_contains(int *endx, int *endy, int nendcells, int x, int y) {
|
||||||
int i;
|
int i;
|
||||||
|
@ -6610,6 +6634,7 @@ glyph_t *getlfglyph(lifeform_t *lf) {
|
||||||
tempglyph.colour = lf->race->glyph.colour;
|
tempglyph.colour = lf->race->glyph.colour;
|
||||||
} else if ((f = lfhasflag(lf, F_GLYPH)) != NULL) {
|
} else if ((f = lfhasflag(lf, F_GLYPH)) != NULL) {
|
||||||
tempglyph.ch = f->val[1];
|
tempglyph.ch = f->val[1];
|
||||||
|
tempglyph.colour = f->val[0];
|
||||||
} else {
|
} else {
|
||||||
tempglyph = lf->race->glyph;
|
tempglyph = lf->race->glyph;
|
||||||
}
|
}
|
||||||
|
@ -7030,6 +7055,7 @@ char *real_getlfname(lifeform_t *lf, char *buf, int usevis, int showall) {
|
||||||
char lname[BUFLEN];
|
char lname[BUFLEN];
|
||||||
job_t *j;
|
job_t *j;
|
||||||
flag_t *f;
|
flag_t *f;
|
||||||
|
enum LFSIZE size,racesize;
|
||||||
|
|
||||||
|
|
||||||
// 'the' or 'your' ?
|
// 'the' or 'your' ?
|
||||||
|
@ -7051,6 +7077,24 @@ char *real_getlfname(lifeform_t *lf, char *buf, int usevis, int showall) {
|
||||||
|
|
||||||
// construct description string
|
// construct description string
|
||||||
strcpy(descstring, "");
|
strcpy(descstring, "");
|
||||||
|
|
||||||
|
// has their size changed?
|
||||||
|
f = hasflag(lf->race->flags, F_SIZE);
|
||||||
|
if (f) {
|
||||||
|
racesize = f->val[0];
|
||||||
|
} else {
|
||||||
|
racesize = SZ_HUMAN; // default
|
||||||
|
}
|
||||||
|
size = getlfsize(lf);
|
||||||
|
if (size != racesize) {
|
||||||
|
if (size == SZ_HUMAN) {
|
||||||
|
strcat(descstring, "human-sized ");
|
||||||
|
} else {
|
||||||
|
strcat(descstring, getsizetext(size));
|
||||||
|
strcat(descstring, " ");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (lfhasflag(lf, F_FROZEN)) {
|
if (lfhasflag(lf, F_FROZEN)) {
|
||||||
strcat(descstring, "frozen ");
|
strcat(descstring, "frozen ");
|
||||||
}
|
}
|
||||||
|
@ -10557,6 +10601,8 @@ void killlf(lifeform_t *lf) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int isdeaf(lifeform_t *lf) {
|
int isdeaf(lifeform_t *lf) {
|
||||||
|
if (lfhasflag(lf, F_TREMORSENSE)) return B_FALSE;
|
||||||
|
|
||||||
if (lfhasflag(lf, F_DEAF)) return B_TRUE;
|
if (lfhasflag(lf, F_DEAF)) return B_TRUE;
|
||||||
if (isresting(lf) && lfhasflag(lf, F_RESTINGINMOTEL)) return B_TRUE;
|
if (isresting(lf) && lfhasflag(lf, F_RESTINGINMOTEL)) return B_TRUE;
|
||||||
if (lfhasflagval(lf, F_INJURY, IJ_EARSRINGING, NA, NA, NULL)) return B_TRUE;
|
if (lfhasflagval(lf, F_INJURY, IJ_EARSRINGING, NA, NA, NULL)) return B_TRUE;
|
||||||
|
@ -13257,6 +13303,7 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
||||||
// you can see the cell which made the noise
|
// you can see the cell which made the noise
|
||||||
if (seetext) {
|
if (seetext) {
|
||||||
msg("%s", seetext);
|
msg("%s", seetext);
|
||||||
|
rv = B_TRUE;
|
||||||
}
|
}
|
||||||
} else if (text && !isdeaf(l) && ((nclass != NC_MOVEMENT) || !lfhasflag(l, F_DONELISTEN))) {
|
} else if (text && !isdeaf(l) && ((nclass != NC_MOVEMENT) || !lfhasflag(l, F_DONELISTEN))) {
|
||||||
// this means you can only hear one 'walk' sound per turn
|
// this means you can only hear one 'walk' sound per turn
|
||||||
|
@ -13328,7 +13375,7 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
||||||
rv = B_TRUE;
|
rv = B_TRUE;
|
||||||
}
|
}
|
||||||
// can only hear one 'walk' sound per turn.
|
// can only hear one 'walk' sound per turn.
|
||||||
if (isplayer(l) && (nclass == NC_MOVEMENT)) {
|
if (nclass == NC_MOVEMENT) {
|
||||||
addflag(l->flags, F_DONELISTEN, B_TRUE, NA, NA, NULL);
|
addflag(l->flags, F_DONELISTEN, B_TRUE, NA, NA, NULL);
|
||||||
practice(l, SK_LISTEN, 1);
|
practice(l, SK_LISTEN, 1);
|
||||||
}
|
}
|
||||||
|
@ -13415,6 +13462,12 @@ int noise(cell_t *c, lifeform_t *noisemaker, enum NOISECLASS nclass, int volume,
|
||||||
} else { // can't hear the sound.
|
} else { // can't hear the sound.
|
||||||
}
|
}
|
||||||
} // end for each lf on map
|
} // end for each lf on map
|
||||||
|
|
||||||
|
if (rv == B_TRUE) {
|
||||||
|
if (getoption(OPT_STOPRUNONNOISE)) {
|
||||||
|
stoprunning(player);
|
||||||
|
}
|
||||||
|
}
|
||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -16009,7 +16062,6 @@ void startlfturn(lifeform_t *lf) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// sixth sense spell warnings
|
// sixth sense spell warnings
|
||||||
|
|
||||||
f = hasactivespell(lf, OT_S_SIXTHSENSE);
|
f = hasactivespell(lf, OT_S_SIXTHSENSE);
|
||||||
if (f) {
|
if (f) {
|
||||||
cell_t *retcell[MAXCANDIDATES];
|
cell_t *retcell[MAXCANDIDATES];
|
||||||
|
@ -16559,7 +16611,7 @@ void startlfturn(lifeform_t *lf) {
|
||||||
|
|
||||||
// effects for/on your own flags
|
// effects for/on your own flags
|
||||||
getflags(lf->flags, retflag, &nretflags, F_ATTACHEDTO, F_CANWILL, F_CHARMEDBY, F_CLIMBING, F_FEIGNFOOLEDBY,F_FLEEFROM,
|
getflags(lf->flags, retflag, &nretflags, F_ATTACHEDTO, F_CANWILL, F_CHARMEDBY, F_CLIMBING, F_FEIGNFOOLEDBY,F_FLEEFROM,
|
||||||
F_GRABBEDBY, F_GRABBING, F_GUNTARGET, F_BOOSTSPELL, F_FEIGNINGDEATH, F_INJURY,
|
F_GRABBEDBY, F_GRABBING, F_GUNTARGET, F_BOOSTSPELL, F_FEIGNINGDEATH, F_HPDRAIN, F_INJURY,
|
||||||
F_NOFLEEFROM, F_PETOF, F_SPOTTED, F_STABBEDBY, F_TARGETCELL, F_TARGETLF, F_NONE);
|
F_NOFLEEFROM, F_PETOF, F_SPOTTED, F_STABBEDBY, F_TARGETCELL, F_TARGETLF, F_NONE);
|
||||||
for (i = 0; i < nretflags; i++) {
|
for (i = 0; i < nretflags; i++) {
|
||||||
f = retflag[i];
|
f = retflag[i];
|
||||||
|
@ -16696,6 +16748,14 @@ void startlfturn(lifeform_t *lf) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} // end if f_target or f_targetcell
|
} // end if f_target or f_targetcell
|
||||||
|
|
||||||
|
// hp drain
|
||||||
|
if (f->id == F_HPDRAIN) {
|
||||||
|
losehp(lf, f->val[0], DT_DIRECT, NULL, f->text);
|
||||||
|
if (isdead(lf)) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
} // end loop through lf flags
|
} // end loop through lf flags
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -17004,7 +17064,6 @@ lifeform_t *summonmonster(lifeform_t *caster, cell_t *c, enum RACE rid, char *ra
|
||||||
|
|
||||||
|
|
||||||
int takeoff(lifeform_t *lf, object_t *o) {
|
int takeoff(lifeform_t *lf, object_t *o) {
|
||||||
flag_t *f;
|
|
||||||
char obname[BUFLEN];
|
char obname[BUFLEN];
|
||||||
char buf[BUFLEN];
|
char buf[BUFLEN];
|
||||||
|
|
||||||
|
@ -17066,19 +17125,7 @@ int takeoff(lifeform_t *lf, object_t *o) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// lose flags
|
unequipeffects(lf, o);
|
||||||
loseobflags(lf, o, F_EQUIPCONFER);
|
|
||||||
|
|
||||||
f = hasflag(o->flags, F_CREATEDBYSPELL);
|
|
||||||
if (f) stopspell(lf, f->val[0]);
|
|
||||||
|
|
||||||
if (obproduceslight(o)) {
|
|
||||||
calclight((getoblocation(o))->map);
|
|
||||||
setlosdirty(lf);
|
|
||||||
//precalclos(lf);
|
|
||||||
drawscreen();
|
|
||||||
}
|
|
||||||
|
|
||||||
return B_FALSE;
|
return B_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -17432,6 +17479,29 @@ void turntoface(lifeform_t *lf, cell_t *dstcell) {
|
||||||
setfacing(lf, getdirtowards(lf->cell, dstcell, NULL, B_FALSE, DT_ORTH) );
|
setfacing(lf, getdirtowards(lf->cell, dstcell, NULL, B_FALSE, DT_ORTH) );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void unequipeffects(lifeform_t *lf, object_t *o) {
|
||||||
|
flag_t *f;
|
||||||
|
// lose flags
|
||||||
|
loseobflags(lf, o, F_EQUIPCONFER);
|
||||||
|
|
||||||
|
if (obproduceslight(o)) {
|
||||||
|
calclight((getoblocation(o))->map);
|
||||||
|
setlosdirty(lf);
|
||||||
|
//precalclos(lf);
|
||||||
|
drawscreen();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (o->type->id == OT_ENERGYBLADE) {
|
||||||
|
stopspell(lf, OT_S_SUMMONWEAPON);
|
||||||
|
// object might be dead now, so stop.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
f = hasflag(o->flags, F_CREATEDBYSPELL);
|
||||||
|
if (f) {
|
||||||
|
stopspell(lf, f->val[0]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void unsummon(lifeform_t *lf, int vanishobs) {
|
void unsummon(lifeform_t *lf, int vanishobs) {
|
||||||
lifeform_t *creator = NULL;
|
lifeform_t *creator = NULL;
|
||||||
|
@ -17530,19 +17600,7 @@ int unweild(lifeform_t *lf, object_t *o) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// lose flags
|
unequipeffects(lf, o);
|
||||||
loseobflags(lf, o, F_EQUIPCONFER);
|
|
||||||
|
|
||||||
if (obproduceslight(o)) {
|
|
||||||
calclight((getoblocation(o))->map);
|
|
||||||
setlosdirty(lf);
|
|
||||||
//precalclos(lf);
|
|
||||||
drawscreen();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (o->type->id == OT_ENERGYBLADE) {
|
|
||||||
stopspell(lf, OT_S_SUMMONWEAPON);
|
|
||||||
}
|
|
||||||
|
|
||||||
return B_FALSE;
|
return B_FALSE;
|
||||||
}
|
}
|
||||||
|
@ -18109,6 +18167,72 @@ int validateraces(void) {
|
||||||
return goterror;
|
return goterror;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// returns TRUE on error
|
||||||
|
int resizelf(lifeform_t *lf, enum LFSIZE newsize) {
|
||||||
|
flag_t *f;
|
||||||
|
enum LFSIZE origsize;
|
||||||
|
int changedir;
|
||||||
|
char lfname[BUFLEN];
|
||||||
|
object_t *o,*nexto;
|
||||||
|
getlfname(lf, lfname);
|
||||||
|
f = hasflag(lf->flags, F_SIZE);
|
||||||
|
if (f) {
|
||||||
|
origsize = f->val[0];
|
||||||
|
} else {
|
||||||
|
origsize = SZ_HUMAN; // default
|
||||||
|
}
|
||||||
|
|
||||||
|
if (origsize == newsize) {
|
||||||
|
return B_TRUE;
|
||||||
|
} else if (newsize > origsize) {
|
||||||
|
changedir = 1;
|
||||||
|
} else {
|
||||||
|
changedir = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (f) {
|
||||||
|
f->val[0] = newsize;
|
||||||
|
} else {
|
||||||
|
addflag(lf->flags, F_SIZE, newsize, NA, NA, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
// announce
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
msg("Your body %s unnaturally!", (changedir == 1) ? "grows" : "shrinks");
|
||||||
|
} else if (cansee(player, lf)) {
|
||||||
|
msg("%s %s unnaturally!", lfname, (changedir == 1) ? "grows" : "shrinks");
|
||||||
|
}
|
||||||
|
|
||||||
|
// effects on objects, armour etc
|
||||||
|
for (o = lf->pack->first ; o ; o = nexto) {
|
||||||
|
nexto = o->next;
|
||||||
|
|
||||||
|
// object is now the wrong size?
|
||||||
|
if (isequipped(o) && isarmour(o)) {
|
||||||
|
if (!armourfits(lf, o, NULL)) {
|
||||||
|
char obname[BUFLEN];
|
||||||
|
getobname(o, obname, o->amt);
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
msg("Your %s no longer fits!", noprefix(obname));
|
||||||
|
} else if (cansee(player, lf)) {
|
||||||
|
msg("%s%s %s no longer fits!", lfname, getpossessive(lfname), noprefix(obname));
|
||||||
|
}
|
||||||
|
killflagsofid(o->flags, F_EQUIPPED);
|
||||||
|
unequipeffects(lf, o);
|
||||||
|
if (isplayer(lf)) statdirty = B_TRUE; // might have impacted AR
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// object is now too big to hold?
|
||||||
|
if (canpickup(lf, o, o->amt) == E_TOOBIG) {
|
||||||
|
drop(o, o->amt);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return B_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
int rest(lifeform_t *lf, int onpurpose) {
|
int rest(lifeform_t *lf, int onpurpose) {
|
||||||
flag_t *f;
|
flag_t *f;
|
||||||
flag_t *ff;
|
flag_t *ff;
|
||||||
|
|
2
lf.h
2
lf.h
|
@ -368,6 +368,7 @@ int readytotrain(lifeform_t *lf);
|
||||||
int recruit(lifeform_t *lf);
|
int recruit(lifeform_t *lf);
|
||||||
void refreshlevelabilities(lifeform_t *lf);
|
void refreshlevelabilities(lifeform_t *lf);
|
||||||
void relinklf(lifeform_t *src, map_t *dst);
|
void relinklf(lifeform_t *src, map_t *dst);
|
||||||
|
int resizelf(lifeform_t *lf, enum LFSIZE newsize);
|
||||||
int rest(lifeform_t *lf, int onpurpose);
|
int rest(lifeform_t *lf, int onpurpose);
|
||||||
void setskillused(lifeform_t *lf, enum SKILL skid);
|
void setskillused(lifeform_t *lf, enum SKILL skid);
|
||||||
int startclimbing(lifeform_t *lf);
|
int startclimbing(lifeform_t *lf);
|
||||||
|
@ -416,6 +417,7 @@ void timeeffectslf(lifeform_t *lf);
|
||||||
int tryclimb(lifeform_t *lf, cell_t *where, char *towhat);
|
int tryclimb(lifeform_t *lf, cell_t *where, char *towhat);
|
||||||
int touch(lifeform_t *lf, object_t *o);
|
int touch(lifeform_t *lf, object_t *o);
|
||||||
void turntoface(lifeform_t *lf, cell_t *dstcell);
|
void turntoface(lifeform_t *lf, cell_t *dstcell);
|
||||||
|
void unequipeffects(lifeform_t *lf, object_t *o);
|
||||||
void unpoison(lifeform_t *lf);
|
void unpoison(lifeform_t *lf);
|
||||||
void unsummon(lifeform_t *lf, int vanishobs);
|
void unsummon(lifeform_t *lf, int vanishobs);
|
||||||
int unweild(lifeform_t *lf, object_t *o);
|
int unweild(lifeform_t *lf, object_t *o);
|
||||||
|
|
208
map.c
208
map.c
|
@ -805,6 +805,7 @@ void adjustcellglyphforlight(cell_t *c, glyph_t *g) {
|
||||||
int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, int doorpct, int dooropenchance) {
|
int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, int doorpct, int dooropenchance) {
|
||||||
int i,d;
|
int i,d;
|
||||||
cell_t *poss[MAXCANDIDATES], *cell[MAXCANDIDATES]; // TODO: should this be maxroomw * maxroomh ?
|
cell_t *poss[MAXCANDIDATES], *cell[MAXCANDIDATES]; // TODO: should this be maxroomw * maxroomh ?
|
||||||
|
int possdir[MAXCANDIDATES];
|
||||||
int ncells = 0, npossible = 0;
|
int ncells = 0, npossible = 0;
|
||||||
int doorsadded = 0;
|
int doorsadded = 0;
|
||||||
int db = B_TRUE;
|
int db = B_TRUE;
|
||||||
|
@ -835,11 +836,13 @@ int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, in
|
||||||
makedoor(cell[i], dooropenchance);
|
makedoor(cell[i], dooropenchance);
|
||||||
} else {
|
} else {
|
||||||
setcelltype(cell[i], cell[i]->habitat->emptycelltype);
|
setcelltype(cell[i], cell[i]->habitat->emptycelltype);
|
||||||
|
cell[i]->isroomwall = compassdir(d);
|
||||||
addflag(map->flags, F_ROOMEXIT, roomid, cell[i]->x, cell[i]->y, "from autodoors, only way out");
|
addflag(map->flags, F_ROOMEXIT, roomid, cell[i]->x, cell[i]->y, "from autodoors, only way out");
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// otherwise mark this as a _potential_ door location.
|
// otherwise mark this as a _potential_ door location.
|
||||||
poss[npossible] = cell[i];
|
poss[npossible] = cell[i];
|
||||||
|
possdir[npossible] = d;
|
||||||
npossible++;
|
npossible++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -857,6 +860,7 @@ int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, in
|
||||||
setcelltype(poss[sel], poss[sel]->habitat->emptycelltype);
|
setcelltype(poss[sel], poss[sel]->habitat->emptycelltype);
|
||||||
addflag(map->flags, F_ROOMEXIT, roomid, poss[sel]->x, poss[sel]->y, "from autodoors, potential location");
|
addflag(map->flags, F_ROOMEXIT, roomid, poss[sel]->x, poss[sel]->y, "from autodoors, potential location");
|
||||||
}
|
}
|
||||||
|
poss[sel]->isroomwall = compassdir(possdir[sel]);
|
||||||
|
|
||||||
doorsadded++;
|
doorsadded++;
|
||||||
}
|
}
|
||||||
|
@ -888,7 +892,7 @@ int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, in
|
||||||
}
|
}
|
||||||
sel = rnd(0,nposs-1);
|
sel = rnd(0,nposs-1);
|
||||||
used[poss[sel]] = B_TRUE;
|
used[poss[sel]] = B_TRUE;
|
||||||
dodoor[ndodoors++] = poss[sel];
|
dodoor[ndodoors] = poss[sel];
|
||||||
}
|
}
|
||||||
|
|
||||||
// actually make the doors
|
// actually make the doors
|
||||||
|
@ -906,6 +910,7 @@ int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, in
|
||||||
addflag(map->flags, F_ROOMEXIT, roomid, cell[sel]->x, cell[sel]->y, "from autodoors, forced at end");
|
addflag(map->flags, F_ROOMEXIT, roomid, cell[sel]->x, cell[sel]->y, "from autodoors, forced at end");
|
||||||
doorsadded++;
|
doorsadded++;
|
||||||
}
|
}
|
||||||
|
cell[sel]->isroomwall = d;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1041,6 +1046,63 @@ int cellhaslos(cell_t *c1, cell_t *dest) {
|
||||||
return B_TRUE;
|
return B_TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// is the given cell a wall of a vault with maintain_edge, and not marked as an exit?
|
||||||
|
int cellisfixedvaultwall(cell_t *c) {
|
||||||
|
if ( getcellvault(c) &&
|
||||||
|
c->type->solid &&
|
||||||
|
hasflag(c->room->vault->flags, F_MAINTAINEDGE) &&
|
||||||
|
!hasflagval(c->map->flags, F_ROOMEXIT, c->room->id, c->x, c->y, NULL) ) {
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
return B_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
// returns B_TRUE, B_FALSE or B_MAYBE
|
||||||
|
int cellokforreachability(cell_t *startcell, cell_t *c, int srcroomid, int dir, int wantfilled, int *insameroom) {
|
||||||
|
int db = B_TRUE;
|
||||||
|
if ((srcroomid >= 0) && (getroomid(c) == srcroomid) && c->type->solid && startcell->type->solid) {
|
||||||
|
// hits a wall of the same room,
|
||||||
|
// and start cell NOT one inside the room.
|
||||||
|
|
||||||
|
// invalid
|
||||||
|
if (insameroom) *insameroom = B_TRUE;
|
||||||
|
if (db) dblog(" going %s hits wall of same room. invalid.", getdirname(dir));
|
||||||
|
return B_FALSE;
|
||||||
|
} else if (isroom(c) && (getroomid(c) != srcroomid) && (c->isroomwall != diropposite(dir))) {
|
||||||
|
// cell is in a different room, but not the correct edge
|
||||||
|
// invalid
|
||||||
|
if (insameroom) *insameroom = B_FALSE;
|
||||||
|
if (db) dblog(" going %s hits wrong wall of different room. invalid.", getdirname(dir));
|
||||||
|
return B_FALSE;
|
||||||
|
} else if (cellisfixedvaultwall(c)) {
|
||||||
|
// cell is a wall of a maintain_edge vault, and not an exit cell
|
||||||
|
// invalid
|
||||||
|
if (insameroom) *insameroom = B_FALSE;
|
||||||
|
if (db) dblog(" going %s hits non-exit wall maintain_edge vault. invalid.", getdirname(dir));
|
||||||
|
return B_FALSE;
|
||||||
|
} else if (isroom(c) && (getroomid(c) != srcroomid) && c->type->solid && countadjdoors(c) ) {
|
||||||
|
// cell is the wall of a different room, and adjacent to a door.
|
||||||
|
// invalid
|
||||||
|
if (insameroom) *insameroom = B_FALSE;
|
||||||
|
if (db) dblog(" going %s hits wall adjacent to door. invalid.", getdirname(dir));
|
||||||
|
return B_FALSE;
|
||||||
|
} else if (cellwalkable(NULL, c, NULL)) {
|
||||||
|
if (getroomid(c) == srcroomid) {
|
||||||
|
// invalid
|
||||||
|
if (insameroom) *insameroom = B_TRUE;
|
||||||
|
if (db) dblog(" going %s hits empty cell of same room. invalid.", getdirname(dir));
|
||||||
|
return B_FALSE;
|
||||||
|
} else {
|
||||||
|
if (!wantfilled || c->filled) {
|
||||||
|
// walkable and not in this vault. finished.
|
||||||
|
// valid.
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return B_MAYBE;
|
||||||
|
}
|
||||||
|
|
||||||
void clearcell(cell_t *c) {
|
void clearcell(cell_t *c) {
|
||||||
// kill everything there - (lifeforms && objects)
|
// kill everything there - (lifeforms && objects)
|
||||||
if (c->lf && !isplayer(c->lf)) {
|
if (c->lf && !isplayer(c->lf)) {
|
||||||
|
@ -1820,6 +1882,20 @@ int countadjrooms(cell_t *cell) {
|
||||||
return count;
|
return count;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int countadjdoors(cell_t *cell) {
|
||||||
|
int d;
|
||||||
|
int doors = 0;
|
||||||
|
|
||||||
|
for (d = DC_N; d <= DC_NW; d++) {
|
||||||
|
cell_t *newcell;
|
||||||
|
newcell = getcellindir(cell, d);
|
||||||
|
if (newcell || hasobwithflag(newcell->obpile, F_DOOR)) {
|
||||||
|
doors++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return doors;
|
||||||
|
}
|
||||||
|
|
||||||
int countadjwalls(cell_t *cell) {
|
int countadjwalls(cell_t *cell) {
|
||||||
int d;
|
int d;
|
||||||
int walls = 0;
|
int walls = 0;
|
||||||
|
@ -3742,64 +3818,57 @@ void killmap(map_t *m) {
|
||||||
// if 'wantfilled' is set, only link to "filled" cells.
|
// if 'wantfilled' is set, only link to "filled" cells.
|
||||||
// return TRUE on failure.
|
// return TRUE on failure.
|
||||||
int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
int db = B_FALSE;
|
int db = B_TRUE;
|
||||||
int d, roomid;
|
int d, roomid,startd,endd;
|
||||||
int poss2[MAXCANDIDATES],nposs2;
|
int poss2[MAXCANDIDATES],nposs2;
|
||||||
int dist[MAXDIR_ORTH],hitsedge[MAXDIR_ORTH], sameroom[MAXDIR_ORTH];
|
int dist[MAXDIR_ORTH],hitsedge[MAXDIR_ORTH], sameroom[MAXDIR_ORTH];
|
||||||
cell_t *directendcell[MAXDIR_ORTH];
|
cell_t *directendcell[MAXDIR_ORTH];
|
||||||
int mindist = 999,maxdist = -1;
|
int mindist = 999,maxdist = -1;
|
||||||
cell_t *c;
|
cell_t *c;
|
||||||
|
int forcedir = D_NONE;
|
||||||
|
|
||||||
if (ncellsadded) *ncellsadded = 0;
|
if (ncellsadded) *ncellsadded = 0;
|
||||||
|
|
||||||
if (db) dblog(" calling linkexit() for cell at %d,%d", startcell->x, startcell->y);
|
|
||||||
|
|
||||||
roomid = getroomid(startcell);
|
roomid = getroomid(startcell);
|
||||||
|
if (db) dblog(" calling linkexit() for cell at %d,%d in roomid %d", startcell->x, startcell->y, roomid);
|
||||||
|
|
||||||
for (d = D_N; d <= D_W; d++) {
|
for (d = D_N; d <= D_W; d++) {
|
||||||
hitsedge[d] = B_TRUE;
|
hitsedge[d] = B_TRUE;
|
||||||
directendcell[d] = NULL;
|
directendcell[d] = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
// link it. starting from the door, count the number of cells in
|
// link it.
|
||||||
|
// if our cell is marked specifically as a room exit, our first direction MUST be out the
|
||||||
|
// door.
|
||||||
|
if (startcell->isroomwall != D_NONE) {
|
||||||
|
forcedir = startcell->isroomwall;
|
||||||
|
startd = forcedir;
|
||||||
|
endd = forcedir;
|
||||||
|
} else {
|
||||||
|
startd = D_N; endd = D_W;
|
||||||
|
}
|
||||||
|
|
||||||
|
// otherwise, starting from the door, count the number of cells in
|
||||||
// each direction until we hit an empty (walkable) cell which isn't a room.
|
// each direction until we hit an empty (walkable) cell which isn't a room.
|
||||||
|
|
||||||
// if we hit a cell of this roomid, mark this dir as invalid.
|
// if we hit a cell of this roomid, mark this dir as invalid.
|
||||||
for (d = D_N; d <= D_W; d++) {
|
for (d = startd; d <= endd; d++) {
|
||||||
dist[d] = 0;
|
dist[d] = 0;
|
||||||
hitsedge[d] = B_FALSE;
|
hitsedge[d] = B_FALSE;
|
||||||
sameroom[d] = B_FALSE;
|
sameroom[d] = B_FALSE;
|
||||||
c = getcellindir(startcell, d);
|
c = getcellindir(startcell, d);
|
||||||
while (c) {
|
while (c) {
|
||||||
|
int rv;
|
||||||
dist[d]++;
|
dist[d]++;
|
||||||
if ((roomid >= 0) && getroomid(c) == roomid) { // same room
|
|
||||||
//if (wantfilled && c->type->solid) {
|
rv = cellokforreachability(startcell, c, roomid, d, wantfilled, &(sameroom[d]));
|
||||||
if (c->type->solid) {
|
if (rv == B_FALSE) {
|
||||||
// This is an exception:
|
|
||||||
// if startcell is a cell _inside_ the room as opposed to
|
|
||||||
// a cell inside the room's walls.
|
|
||||||
// in this case, we ARE allowed to travel through the room's walls.
|
|
||||||
} else {
|
|
||||||
// mark dir as invalid
|
|
||||||
dist[d] = 999;
|
dist[d] = 999;
|
||||||
sameroom[d] = B_TRUE;
|
|
||||||
if (db) dblog(" going %s hits same room. invalid.", getdirname(d));
|
|
||||||
break;
|
break;
|
||||||
}
|
} else if (rv == B_TRUE) {
|
||||||
} else if (isroom(c) && (getroomid(c) != roomid) && (c->isroomwall != diropposite(d))) {
|
|
||||||
// cell is in a different room, but not the correct edge
|
|
||||||
// mark dir as invalid
|
|
||||||
dist[d] = 999;
|
|
||||||
sameroom[d] = B_FALSE;
|
|
||||||
if (db) dblog(" going %s hits wrong wall of different room. invalid.", getdirname(d));
|
|
||||||
break;
|
|
||||||
} else if (cellwalkable(NULL, c, NULL)) {
|
|
||||||
if (!wantfilled || c->filled) {
|
|
||||||
// walkable and not in this vault. finished.
|
|
||||||
directendcell[d] = c;
|
directendcell[d] = c;
|
||||||
if (db) dblog(" can make %s path (hits empty cell at dist %d)", getdirname(d), dist[d]);
|
if (db) dblog(" can make %s path (hits empty cell at dist %d)", getdirname(d), dist[d]);
|
||||||
break;
|
} else { // ie. rv == B_MAYBE
|
||||||
}
|
|
||||||
} else {
|
|
||||||
int perpdir[2],n;
|
int perpdir[2],n;
|
||||||
cell_t *pcell = NULL;
|
cell_t *pcell = NULL;
|
||||||
perpdir[0] = d - 1; if (perpdir[0] < D_N) perpdir[0] = D_W;
|
perpdir[0] = d - 1; if (perpdir[0] < D_N) perpdir[0] = D_W;
|
||||||
|
@ -3813,6 +3882,7 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
proomid = getroomid(pcell);
|
proomid = getroomid(pcell);
|
||||||
if (((roomid == -1 ) || (proomid != roomid)) && cellwalkable(NULL, pcell, NULL)) {
|
if (((roomid == -1 ) || (proomid != roomid)) && cellwalkable(NULL, pcell, NULL)) {
|
||||||
if ((proomid >= 0) && (pcell->isroomwall != diropposite(perpdir[n]))) {
|
if ((proomid >= 0) && (pcell->isroomwall != diropposite(perpdir[n]))) {
|
||||||
|
} else if (cellisfixedvaultwall(pcell)) {
|
||||||
} else {
|
} else {
|
||||||
if (!wantfilled || c->filled) {
|
if (!wantfilled || c->filled) {
|
||||||
// finished.
|
// finished.
|
||||||
|
@ -3855,6 +3925,11 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
int nstartposs = 0;
|
int nstartposs = 0;
|
||||||
// no good directions.
|
// no good directions.
|
||||||
if (db) dblog(" No directions lead to valid cells. Trying turns.");
|
if (db) dblog(" No directions lead to valid cells. Trying turns.");
|
||||||
|
|
||||||
|
|
||||||
|
if (forcedir != D_NONE) {
|
||||||
|
startdir = forcedir;
|
||||||
|
} else {
|
||||||
// starting at the LONGEST distance, traverse up each dir,
|
// starting at the LONGEST distance, traverse up each dir,
|
||||||
// branching off looking for rooms.
|
// branching off looking for rooms.
|
||||||
|
|
||||||
|
@ -3873,6 +3948,7 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
if (nstartposs) {
|
if (nstartposs) {
|
||||||
startdir = startposs[rnd(0,nstartposs-1)];
|
startdir = startposs[rnd(0,nstartposs-1)];
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (wantfilled) {
|
if (wantfilled) {
|
||||||
// if startdir is D_NONE here, it means that we've called
|
// if startdir is D_NONE here, it means that we've called
|
||||||
|
@ -3902,6 +3978,7 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
|
|
||||||
while (c2) {
|
while (c2) {
|
||||||
int gotsolution = B_FALSE;
|
int gotsolution = B_FALSE;
|
||||||
|
int rv;
|
||||||
turndist++;
|
turndist++;
|
||||||
|
|
||||||
perpcell[nperpcells] = c2; // this will be used if we need to make 2 turns
|
perpcell[nperpcells] = c2; // this will be used if we need to make 2 turns
|
||||||
|
@ -3909,25 +3986,12 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
perpturndir1[nperpcells] = perpdir[n];
|
perpturndir1[nperpcells] = perpdir[n];
|
||||||
nperpcells++;
|
nperpcells++;
|
||||||
|
|
||||||
if ((roomid >= 0) && (getroomid(c2) == roomid)) {
|
rv = cellokforreachability(startcell, c2, roomid, perpdir[n], wantfilled, NULL);
|
||||||
if (wantfilled && c2->type->solid) {
|
|
||||||
// see EXCEPTION above.
|
if (rv == B_FALSE) {
|
||||||
} else {
|
|
||||||
// hits same room, not ok.
|
|
||||||
break;
|
break;
|
||||||
}
|
} else if (rv == B_TRUE) {
|
||||||
} else if (cellwalkable(NULL, c2, NULL)) {
|
|
||||||
if (!wantfilled || c2->filled) {
|
|
||||||
if (db) dblog(" Got to an empty cell here.");
|
|
||||||
gotsolution = B_TRUE;
|
gotsolution = B_TRUE;
|
||||||
}
|
|
||||||
} else if (isroom(c2) && (c2->isroomwall != diropposite(perpdir[n]))) {
|
|
||||||
// wrong wall of room
|
|
||||||
// mark dir as invalid
|
|
||||||
dist[d] = 999;
|
|
||||||
sameroom[d] = B_FALSE;
|
|
||||||
if (db) dblog(" going %s hits wrong wall of different room. invalid.", getdirname(d));
|
|
||||||
break;
|
|
||||||
} else if (turndist > 1) {
|
} else if (turndist > 1) {
|
||||||
// check l/r too
|
// check l/r too
|
||||||
int perpdir2[2],nn;
|
int perpdir2[2],nn;
|
||||||
|
@ -3942,6 +4006,7 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
if ( ((roomid == -1) || (proomid != roomid)) &&
|
if ( ((roomid == -1) || (proomid != roomid)) &&
|
||||||
cellwalkable(NULL, pcell, NULL)) {
|
cellwalkable(NULL, pcell, NULL)) {
|
||||||
if ((proomid >= 0) && (pcell->isroomwall != diropposite(perpdir2[n]))) {
|
if ((proomid >= 0) && (pcell->isroomwall != diropposite(perpdir2[n]))) {
|
||||||
|
} else if (cellisfixedvaultwall(pcell)) {
|
||||||
} else {
|
} else {
|
||||||
if (!wantfilled || pcell->filled) {
|
if (!wantfilled || pcell->filled) {
|
||||||
// finished.
|
// finished.
|
||||||
|
@ -4013,27 +4078,16 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
c2 = getcellindir(perpcell[i], dir3[n]);
|
c2 = getcellindir(perpcell[i], dir3[n]);
|
||||||
while (c2) {
|
while (c2) {
|
||||||
int gotsolution = B_FALSE;
|
int gotsolution = B_FALSE;
|
||||||
|
int rv;
|
||||||
turndist++;
|
turndist++;
|
||||||
if (db) dblog_nocr("(%d,%d)",c2->x,c2->y);
|
if (db) dblog_nocr("(%d,%d)",c2->x,c2->y);
|
||||||
if ((roomid >= 0) && (getroomid(c2) == roomid)) {
|
|
||||||
if (wantfilled && c2->type->solid) {
|
rv = cellokforreachability(startcell, c2, roomid, perpdir[n], wantfilled, NULL);
|
||||||
// see EXCEPTION above.
|
|
||||||
} else {
|
if (rv == B_FALSE) {
|
||||||
// hits same room, not ok.
|
|
||||||
break;
|
break;
|
||||||
}
|
} else if (rv == B_TRUE) {
|
||||||
} else if (cellwalkable(NULL, c2, NULL)) {
|
|
||||||
if (!wantfilled || c2->filled) {
|
|
||||||
if (db) dblog(" Got to an empty cell here.");
|
|
||||||
gotsolution = B_TRUE;
|
gotsolution = B_TRUE;
|
||||||
}
|
|
||||||
} else if (isroom(c2) && (c2->isroomwall != diropposite(dir3[n]))) {
|
|
||||||
// wrong wall of room
|
|
||||||
// mark dir as invalid
|
|
||||||
dist[d] = 999;
|
|
||||||
sameroom[d] = B_FALSE;
|
|
||||||
if (db) dblog(" going %s hits wrong wall of different room. invalid.", getdirname(d));
|
|
||||||
break;
|
|
||||||
} else if (turndist > 1) {
|
} else if (turndist > 1) {
|
||||||
// check l/r too
|
// check l/r too
|
||||||
int perpdir2[2],nn;
|
int perpdir2[2],nn;
|
||||||
|
@ -4049,6 +4103,7 @@ int linkexit(cell_t *startcell, int wantfilled, int *ncellsadded) {
|
||||||
cellwalkable(NULL, pcell, NULL)) {
|
cellwalkable(NULL, pcell, NULL)) {
|
||||||
if ((proomid >= 0) && (pcell->isroomwall != diropposite(perpdir2[nn]))) {
|
if ((proomid >= 0) && (pcell->isroomwall != diropposite(perpdir2[nn]))) {
|
||||||
// different room and hits wrong wall.
|
// different room and hits wrong wall.
|
||||||
|
} else if (cellisfixedvaultwall(pcell)) {
|
||||||
} else {
|
} else {
|
||||||
if (!wantfilled || pcell->filled) {
|
if (!wantfilled || pcell->filled) {
|
||||||
// finished.
|
// finished.
|
||||||
|
@ -4167,7 +4222,7 @@ int linkexits(map_t *m, int roomid) {
|
||||||
int x,y,i;
|
int x,y,i;
|
||||||
cell_t *poss[MAXCANDIDATES],*c;
|
cell_t *poss[MAXCANDIDATES],*c;
|
||||||
int nposs = 0;
|
int nposs = 0;
|
||||||
int db = B_FALSE;
|
int db = B_TRUE;
|
||||||
int nadded = 0;
|
int nadded = 0;
|
||||||
int minx = -1, miny = -1, maxx = -1, maxy = -1;
|
int minx = -1, miny = -1, maxx = -1, maxy = -1;
|
||||||
int roomidx = -1;
|
int roomidx = -1;
|
||||||
|
@ -4225,15 +4280,14 @@ int linkexits(map_t *m, int roomid) {
|
||||||
for (i = 0; i < nposs; i++) {
|
for (i = 0; i < nposs; i++) {
|
||||||
int ncorridors = 0,d;
|
int ncorridors = 0,d;
|
||||||
|
|
||||||
if (db) dblog("exit at %d,%d:",poss[i]->x, poss[i]->y);
|
if (db) dblog("exit #%d at %d,%d: (%s)",i, poss[i]->x, poss[i]->y,
|
||||||
|
(poss[i]->isroomwall != D_NONE) ? getdirname(poss[i]->isroomwall) : "nodir");
|
||||||
// if exit is solid and COMPLETELY surrounded by solid, ignore it.
|
// if exit is solid and COMPLETELY surrounded by solid, ignore it.
|
||||||
if (poss[i]->type->solid && (countcellexits(poss[i], DT_ORTH) == 0)){
|
if (poss[i]->type->solid && (countcellexits(poss[i], DT_ORTH) == 0)){
|
||||||
if (db) dblog("cell is solid and surrounded by solids. ignoring.");
|
if (db) dblog("cell is solid and surrounded by solids. ignoring.");
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (db) dblog("linking exit #%d",i);
|
|
||||||
|
|
||||||
for (d = D_N; d <= D_W; d++) {
|
for (d = D_N; d <= D_W; d++) {
|
||||||
c = getcellindir(poss[i], d);
|
c = getcellindir(poss[i], d);
|
||||||
if (c && cellwalkable(NULL, c, NULL) && (getroomid(c) != roomid)) {
|
if (c && cellwalkable(NULL, c, NULL) && (getroomid(c) != roomid)) {
|
||||||
|
@ -5595,6 +5649,20 @@ cell_t *getrandomcelloftype(map_t *map, enum CELLTYPE id) {
|
||||||
return cell;
|
return cell;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int compassdir(int orthdir) {
|
||||||
|
switch (orthdir) {
|
||||||
|
case D_N:
|
||||||
|
return DC_N;
|
||||||
|
case D_S:
|
||||||
|
return DC_S;
|
||||||
|
case D_E:
|
||||||
|
return DC_E;
|
||||||
|
case D_W:
|
||||||
|
return DC_W;
|
||||||
|
}
|
||||||
|
return D_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
int getrandomdir(int dirtype) {
|
int getrandomdir(int dirtype) {
|
||||||
if (dirtype == DT_ORTH) {
|
if (dirtype == DT_ORTH) {
|
||||||
|
|
4
map.h
4
map.h
|
@ -14,6 +14,8 @@ regiontype_t *addregiontype(enum REGIONTYPE id, char *name, int pluralname, enum
|
||||||
void adjustcellglyphforlight(cell_t *c, glyph_t *col);
|
void adjustcellglyphforlight(cell_t *c, glyph_t *col);
|
||||||
int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, int doorpct, int dooropenchance);
|
int autodoors(map_t *map, int roomid, int minx, int miny, int maxx, int maxy, int doorpct, int dooropenchance);
|
||||||
int cellhaslos(cell_t *c1, cell_t *dest);
|
int cellhaslos(cell_t *c1, cell_t *dest);
|
||||||
|
int cellisfixedvaultwall(cell_t *c);
|
||||||
|
int cellokforreachability(cell_t *startcell, cell_t *c, int srcroomid, int dir, int wantfilled, int *insameroom);
|
||||||
void clearcell(cell_t *c);
|
void clearcell(cell_t *c);
|
||||||
void clearcell_exceptflags(cell_t *c, ...);
|
void clearcell_exceptflags(cell_t *c, ...);
|
||||||
int doelementspread(cell_t *c);
|
int doelementspread(cell_t *c);
|
||||||
|
@ -39,9 +41,11 @@ void getroomedge(map_t *m, int roomid, int minx, int miny, int maxx, int maxy, i
|
||||||
object_t *gettopobject(cell_t *where, int forglyph);
|
object_t *gettopobject(cell_t *where, int forglyph);
|
||||||
void calclight(map_t *map);
|
void calclight(map_t *map);
|
||||||
int calcroompos(map_t *map, int w, int h, int xmargin, int ymargin, int *bx, int *by, int force);
|
int calcroompos(map_t *map, int w, int h, int xmargin, int ymargin, int *bx, int *by, int force);
|
||||||
|
int compassdir(int orthdir);
|
||||||
int countadjcellsoftype(cell_t *cell, int id);
|
int countadjcellsoftype(cell_t *cell, int id);
|
||||||
int countadjrooms(cell_t *cell);
|
int countadjrooms(cell_t *cell);
|
||||||
int countadjcellswithflag(cell_t *cell, enum FLAG fid, int dirtype);
|
int countadjcellswithflag(cell_t *cell, enum FLAG fid, int dirtype);
|
||||||
|
int countadjdoors(cell_t *cell);
|
||||||
int countadjwalls(cell_t *cell);
|
int countadjwalls(cell_t *cell);
|
||||||
int countcellexits(cell_t *cell, int dirtype);
|
int countcellexits(cell_t *cell, int dirtype);
|
||||||
int countcellexitsfor(lifeform_t *lf);
|
int countcellexitsfor(lifeform_t *lf);
|
||||||
|
|
4
nexus.c
4
nexus.c
|
@ -215,7 +215,7 @@ int main(int argc, char **argv) {
|
||||||
if (hasflag(r->flags, F_PLAYABLE)) {
|
if (hasflag(r->flags, F_PLAYABLE)) {
|
||||||
char *longdesc;
|
char *longdesc;
|
||||||
longdesc = malloc(HUGEBUFLEN * sizeof(char));
|
longdesc = malloc(HUGEBUFLEN * sizeof(char));
|
||||||
makedesc_race(r->id, longdesc, B_TRUE );
|
makedesc_race(r->id, longdesc, B_TRUE, B_TRUE );
|
||||||
addchoice(&prompt, ch++, r->name, NULL, r, longdesc);
|
addchoice(&prompt, ch++, r->name, NULL, r, longdesc);
|
||||||
free(longdesc);
|
free(longdesc);
|
||||||
}
|
}
|
||||||
|
@ -355,6 +355,7 @@ int main(int argc, char **argv) {
|
||||||
}
|
}
|
||||||
if (sb1) {
|
if (sb1) {
|
||||||
addflag(player->flags, F_CANCAST, sb1->contents->first->type->id, NA, NA, NULL);
|
addflag(player->flags, F_CANCAST, sb1->contents->first->type->id, NA, NA, NULL);
|
||||||
|
addflag(sb1->flags, F_NOPOINTS, B_TRUE, NA, NA, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
initprompt(&prompt, "Select your secondary spell school:");
|
initprompt(&prompt, "Select your secondary spell school:");
|
||||||
|
@ -388,6 +389,7 @@ int main(int argc, char **argv) {
|
||||||
}
|
}
|
||||||
if (sb2) {
|
if (sb2) {
|
||||||
addflag(player->flags, F_CANCAST, sb2->contents->first->type->id, NA, NA, NULL);
|
addflag(player->flags, F_CANCAST, sb2->contents->first->type->id, NA, NA, NULL);
|
||||||
|
addflag(sb2->flags, F_NOPOINTS, B_TRUE, NA, NA, NULL);
|
||||||
}
|
}
|
||||||
identify(sb1);
|
identify(sb1);
|
||||||
identify(sb2);
|
identify(sb2);
|
||||||
|
|
81
objects.c
81
objects.c
|
@ -3378,8 +3378,15 @@ void fragments(cell_t *centre, char *what, int speed, int howfar) {
|
||||||
done = B_FALSE;
|
done = B_FALSE;
|
||||||
while (!done) {
|
while (!done) {
|
||||||
c = getcellindir(c, dir);
|
c = getcellindir(c, dir);
|
||||||
if (c && cellwalkable(NULL, c, NULL)) {
|
if (c) {
|
||||||
|
if (cellwalkable(NULL, c, NULL)) {
|
||||||
maxdist++;
|
maxdist++;
|
||||||
|
} else {
|
||||||
|
if (c->lf && !c->type->solid) {
|
||||||
|
maxdist++;
|
||||||
|
}
|
||||||
|
done = B_TRUE;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
done = B_TRUE;
|
done = B_TRUE;
|
||||||
}
|
}
|
||||||
|
@ -3412,10 +3419,19 @@ void fragments(cell_t *centre, char *what, int speed, int howfar) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (speed) {
|
||||||
|
object_t *o;
|
||||||
|
// add object then fire it
|
||||||
|
o = addob(centre->obpile, what);
|
||||||
|
if (o) {
|
||||||
|
fireat(NULL, o, o->amt, dst, speed, NULL);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
// add object
|
// add object
|
||||||
addob(dst->obpile, what);
|
addob(dst->obpile, what);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int gethardness(enum MATERIAL matid) {
|
int gethardness(enum MATERIAL matid) {
|
||||||
material_t *m;
|
material_t *m;
|
||||||
|
@ -4576,6 +4592,20 @@ cell_t *getobpilelocation(obpile_t *op) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// note: should have an entry here for everything which willshatter()
|
||||||
|
char *getshardobname(enum MATERIAL mid, char *buf) {
|
||||||
|
switch (mid) {
|
||||||
|
case MT_GLASS:
|
||||||
|
strcpy(buf, "piece of broken glass");
|
||||||
|
break;
|
||||||
|
case MT_ICE:
|
||||||
|
strcpy(buf, "chunk of ice");
|
||||||
|
break;
|
||||||
|
default: return NULL;
|
||||||
|
}
|
||||||
|
return buf;
|
||||||
|
}
|
||||||
|
|
||||||
char *getshopobname(object_t *o, char *buf, int count) {
|
char *getshopobname(object_t *o, char *buf, int count) {
|
||||||
if (gettechlevel(o->type->id) > getskill(player, SK_TECHUSAGE)) {
|
if (gettechlevel(o->type->id) > getskill(player, SK_TECHUSAGE)) {
|
||||||
// unidentified tech - hide the name
|
// unidentified tech - hide the name
|
||||||
|
@ -9765,6 +9795,13 @@ void potioneffects(lifeform_t *lf, enum OBTYPE oid, object_t *o, enum BLESSTYPE
|
||||||
case OT_POT_GASEOUSFORM:
|
case OT_POT_GASEOUSFORM:
|
||||||
dospelleffects(lf, OT_S_GASEOUSFORM, (potblessed) ? 5 : 1, lf, NULL, lf->cell, potblessed, seen, B_TRUE);
|
dospelleffects(lf, OT_S_GASEOUSFORM, (potblessed) ? 5 : 1, lf, NULL, lf->cell, potblessed, seen, B_TRUE);
|
||||||
break;
|
break;
|
||||||
|
case OT_POT_GROWTH:
|
||||||
|
if (iscursed(o)) {
|
||||||
|
dospelleffects(lf, OT_S_SIZEDOWN, 1, lf, NULL, lf->cell, B_UNCURSED, seen, B_TRUE);
|
||||||
|
} else {
|
||||||
|
dospelleffects(lf, OT_S_SIZEUP, 1, lf, NULL, lf->cell, B_UNCURSED, seen, B_TRUE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
case OT_POT_HEALING:
|
case OT_POT_HEALING:
|
||||||
dospelleffects(lf, OT_S_HEALING,potblessed ? 5 : 1, lf, NULL, lf->cell, potblessed, seen, B_TRUE);
|
dospelleffects(lf, OT_S_HEALING,potblessed ? 5 : 1, lf, NULL, lf->cell, potblessed, seen, B_TRUE);
|
||||||
break;
|
break;
|
||||||
|
@ -10933,6 +10970,7 @@ int shatter(object_t *o, int hitlf, char *damstring, lifeform_t *fromlf) {
|
||||||
case OT_POT_ELEMENTIMMUNE:
|
case OT_POT_ELEMENTIMMUNE:
|
||||||
case OT_POT_ETHEREALNESS:
|
case OT_POT_ETHEREALNESS:
|
||||||
case OT_POT_GASEOUSFORM:
|
case OT_POT_GASEOUSFORM:
|
||||||
|
case OT_POT_GROWTH:
|
||||||
case OT_POT_LEVITATION:
|
case OT_POT_LEVITATION:
|
||||||
case OT_POT_POISON:
|
case OT_POT_POISON:
|
||||||
case OT_POT_POLYMORPH:
|
case OT_POT_POLYMORPH:
|
||||||
|
@ -12390,7 +12428,8 @@ void timeeffectsob(object_t *o) {
|
||||||
|
|
||||||
|
|
||||||
// check each flag for this object...
|
// check each flag for this object...
|
||||||
getflags(o->flags, retflag, &nretflags, F_ACTIVATED, F_EDIBLE, F_MATCONVERT, F_OBHPDRAIN, F_ONFIRE, F_RECHARGE, F_WALKDAM, F_WET, F_NONE);
|
getflags(o->flags, retflag, &nretflags, F_ACTIVATED, F_EDIBLE, F_MATCONVERT, F_OBHPDRAIN, F_ONFIRE,
|
||||||
|
F_RECHARGE, F_REVIVETIMER, F_WALKDAM, F_WET, F_NONE);
|
||||||
for (i = 0; i < nretflags; i++) {
|
for (i = 0; i < nretflags; i++) {
|
||||||
object_t *oo,*nextoo;
|
object_t *oo,*nextoo;
|
||||||
f = retflag[i];
|
f = retflag[i];
|
||||||
|
@ -12531,6 +12570,44 @@ void timeeffectsob(object_t *o) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// regenerates into a lf?
|
||||||
|
if (f->id == F_REVIVETIMER) {
|
||||||
|
cell_t *obloc = NULL;
|
||||||
|
obloc = getoblocation(o);
|
||||||
|
f->val[0]++;
|
||||||
|
limit(&f->val[0], 0, f->val[1]);
|
||||||
|
if (f->val[0] >= f->val[1]) {
|
||||||
|
lifeform_t *lf;
|
||||||
|
cell_t *lfloc = NULL;
|
||||||
|
if (obloc) {
|
||||||
|
if (obloc->lf) {
|
||||||
|
lfloc = getrandomadjcell(obloc, WE_WALKABLE, B_NOEXPAND);
|
||||||
|
} else {
|
||||||
|
lfloc = obloc;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lfloc) {
|
||||||
|
// revive!
|
||||||
|
lf = addmonster(lfloc, f->val[2], NULL, B_FALSE, 1, B_FALSE, NULL);
|
||||||
|
// corpse vanishes
|
||||||
|
removeob(o, o->amt);
|
||||||
|
// announce
|
||||||
|
if (haslos(player, lfloc) || haslos(player, obloc)) {
|
||||||
|
msg("%s comes to life!", obname);
|
||||||
|
interrupt(player);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} else if ((f->val[1] - f->val[0]) <= 10) {
|
||||||
|
if (haslos(player, obloc)) {
|
||||||
|
// pass a perception chekc to see it moving...
|
||||||
|
if (skillcheck(player, SC_SEARCH, 20, 0)) {
|
||||||
|
msg("%s twitches.", obname);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// damaging objects here will damage other objects
|
// damaging objects here will damage other objects
|
||||||
if (f->id == F_WALKDAM) {
|
if (f->id == F_WALKDAM) {
|
||||||
|
|
|
@ -122,6 +122,7 @@ char *getobextrainfo(object_t *o, char *buf);
|
||||||
cell_t *getoblocation(object_t *o);
|
cell_t *getoblocation(object_t *o);
|
||||||
cell_t *getobpilelocation(obpile_t *op);
|
cell_t *getobpilelocation(obpile_t *op);
|
||||||
char *getobname(object_t *o, char *buf, int count);
|
char *getobname(object_t *o, char *buf, int count);
|
||||||
|
char *getshardobname(enum MATERIAL mid, char *buf);
|
||||||
char *getshopobname(object_t *o, char *buf, int count);
|
char *getshopobname(object_t *o, char *buf, int count);
|
||||||
char *getobnametrue(object_t *o, char *buf, int count);
|
char *getobnametrue(object_t *o, char *buf, int count);
|
||||||
char *real_getobname(object_t *o, char *buf, int count, int wantpremods, int wantcondition, int adjustforblind, int wantblesscurse, int showall);
|
char *real_getobname(object_t *o, char *buf, int count, int wantpremods, int wantcondition, int adjustforblind, int wantblesscurse, int showall);
|
||||||
|
|
24
spell.c
24
spell.c
|
@ -8772,6 +8772,30 @@ int dospelleffects(lifeform_t *caster, enum OBTYPE spellid, int power, lifeform_
|
||||||
if (isplayer(caster)) {
|
if (isplayer(caster)) {
|
||||||
msg("You will now be warned of creatures behind you.");
|
msg("You will now be warned of creatures behind you.");
|
||||||
}
|
}
|
||||||
|
} else if ((spellid == OT_S_SIZEUP) || (spellid == OT_S_SIZEDOWN)) {
|
||||||
|
enum LFSIZE origsize,newsize;
|
||||||
|
origsize = getlfsize(caster);
|
||||||
|
if (spellid == OT_S_SIZEUP) {
|
||||||
|
if (origsize >= SZ_ENORMOUS) {
|
||||||
|
fizzle(caster);
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
newsize = origsize + 1;
|
||||||
|
} else { // ie. sizedown
|
||||||
|
if (origsize <= SZ_MINI) {
|
||||||
|
fizzle(caster);
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
newsize = origsize - 1;
|
||||||
|
}
|
||||||
|
if (resizelf(caster, newsize)) {
|
||||||
|
// failed
|
||||||
|
fizzle(caster);
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
if (isplayer(caster) || cansee(player, caster)) {
|
||||||
|
if (seenbyplayer) *seenbyplayer = B_TRUE;
|
||||||
|
}
|
||||||
} else if (spellid == OT_S_SLEEP) {
|
} else if (spellid == OT_S_SLEEP) {
|
||||||
int howlong;
|
int howlong;
|
||||||
target = targcell->lf;
|
target = targcell->lf;
|
||||||
|
|
3
vault.c
3
vault.c
|
@ -1330,6 +1330,9 @@ int handleline(vault_t *v, char *line) {
|
||||||
} else {
|
} else {
|
||||||
dblog("invalid goesin() definition: '%s'", line);
|
dblog("invalid goesin() definition: '%s'", line);
|
||||||
}
|
}
|
||||||
|
} else if (streq(line, "maintainedge")) {
|
||||||
|
addflag(v->flags, F_MAINTAINEDGE, B_TRUE, NA, NA, NULL);
|
||||||
|
ok = B_TRUE;
|
||||||
} else if (strstarts(line, "margin")) {
|
} else if (strstarts(line, "margin")) {
|
||||||
char *p;
|
char *p;
|
||||||
p = line + 6;
|
p = line + 6;
|
||||||
|
|
|
@ -21,5 +21,6 @@ X:exit
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
mayrotate
|
mayrotate
|
||||||
rarity:vrare
|
rarity:vrare
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -22,5 +22,6 @@ scatter(3,1,-4,-2) mon:bear cub:1-3:50
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
mayrotate
|
mayrotate
|
||||||
rarity:uncommon
|
rarity:uncommon
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -35,5 +35,6 @@ scatter(1,1,-2,-2) ob:wooden footstool:0-3
|
||||||
scatter(1,1,-2,-2) ob:random food:0-2
|
scatter(1,1,-2,-2) ob:random food:0-2
|
||||||
mayflipx
|
mayflipx
|
||||||
tag:caveboss
|
tag:caveboss
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -16,5 +16,6 @@ m:mon:sleeping random
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
mayrotate
|
mayrotate
|
||||||
rarity:uncommon
|
rarity:uncommon
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -19,8 +19,8 @@
|
||||||
|
|
||||||
@flags
|
@flags
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
autodoors:50
|
|
||||||
autopop
|
autopop
|
||||||
rarity:frequent
|
rarity:frequent
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -17,5 +17,6 @@ x:exit
|
||||||
@flags
|
@flags
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
rarity:frequent
|
rarity:frequent
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -17,4 +17,5 @@ x:exit
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
rarity:frequent
|
rarity:frequent
|
||||||
mayrotate
|
mayrotate
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
|
@ -26,5 +26,6 @@ shrine
|
||||||
norandom
|
norandom
|
||||||
mayrotate
|
mayrotate
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -33,5 +33,6 @@ atoneof(10,1)(10,3)(10,5) ob:portal to lv1
|
||||||
scatter(1,1,-2,-2) ob:wooden footstool:0-3
|
scatter(1,1,-2,-2) ob:wooden footstool:0-3
|
||||||
scatter(1,1,-2,-2) ob:random food:0-2
|
scatter(1,1,-2,-2) ob:random food:0-2
|
||||||
mayrotate
|
mayrotate
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -42,5 +42,6 @@ scatter(0,0,-1,-1) ob:common weapon:4-5
|
||||||
mayrotate
|
mayrotate
|
||||||
! mayscale
|
! mayscale
|
||||||
rarity:rare
|
rarity:rare
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -15,5 +15,6 @@ o:ob:1-5 random tools
|
||||||
@flags
|
@flags
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
rarity:uncommon
|
rarity:uncommon
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -15,5 +15,6 @@ o:ob:1-5 random technology
|
||||||
@flags
|
@flags
|
||||||
goesin:dungeon
|
goesin:dungeon
|
||||||
rarity:uncommon
|
rarity:uncommon
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
|
@ -20,5 +20,6 @@ mayrotate
|
||||||
rarity:vrare
|
rarity:vrare
|
||||||
! don't link to rest of map. ie this can be in the middle of nowhere.
|
! don't link to rest of map. ie this can be in the middle of nowhere.
|
||||||
nolink
|
nolink
|
||||||
|
maintainedge
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue