- [+] fire spells:
- [+] gather flame - l1: nearby fire boosts next spell's power. casttimme 2 - [+] boil blood - l2: when monster dies, it explodes (like a fireball?) - [+] maybe: create player lf BEFORE creating maps - [+] then move player to start pos and add pets etc - [+] then kill mons in los - [+] this will let us correctly adjust hostility even on dlev 1 - [+] goat (yellow 'q', 1hd) - [+] charge - [+] horn attack - [+] eats anything! - [+] f_caneatmaterial - [+] calculate nutrition based on weight... - [+] chimera(9hd, 9tr, mutant) - purple 'm' - goat/lion/wyrm, 3 headed. - [+] LARGE - [+] Morale 13-14 - [+] EVIL - [+] Hostile - [+] swoop - [+] can breath fire - use burning wave - [+] melee attacks: - [+] bite (lion head) (3) - [+] bite (dragon head) (5:w) - [+] gore (horns) (3) - [+] 2 x claw (4) - [+] TOTAL 18 - [+] but... do maxattacks = 4, not 5. - [+] slash attack: chance to remove a head. - [+] this makes it lose one bite attack and (maybe) its breath weapon. - [+] hydra - [+] 5-12 heads - [+] each head has bite attack - [+] hit dice / tr based on heads - [+] regenerate 2 heads each time one is severed
This commit is contained in:
parent
acd641ebc0
commit
4d5fa3c4e7
36
ai.c
36
ai.c
|
@ -1950,7 +1950,8 @@ int aipickup(lifeform_t *lf, object_t *o) {
|
||||||
if ((o->type->id == OT_COFFIN) && (lf->race->id == R_GASCLOUD) && lfhasflagval(lf, F_ORIGRACE, R_VAMPIRE, NA, NA, NULL)) {
|
if ((o->type->id == OT_COFFIN) && (lf->race->id == R_GASCLOUD) && lfhasflagval(lf, F_ORIGRACE, R_VAMPIRE, NA, NA, NULL)) {
|
||||||
return rest(lf, B_TRUE);
|
return rest(lf, B_TRUE);
|
||||||
}
|
}
|
||||||
if (isedible(o)) {
|
// if (isedible(o)) {
|
||||||
|
if (caneat(lf, o)) {
|
||||||
return eat(lf, o);
|
return eat(lf, o);
|
||||||
} else {
|
} else {
|
||||||
return pickup(lf, o, o->amt, B_TRUE, B_TRUE);
|
return pickup(lf, o, o->amt, B_TRUE, B_TRUE);
|
||||||
|
@ -2474,6 +2475,11 @@ int aispellok(lifeform_t *lf, enum OBTYPE spellid, lifeform_t *victim, enum FLAG
|
||||||
if ((ot->id == OT_S_BLINDNESS) && isblind(victim)) {
|
if ((ot->id == OT_S_BLINDNESS) && isblind(victim)) {
|
||||||
specificcheckok = B_FALSE;
|
specificcheckok = B_FALSE;
|
||||||
}
|
}
|
||||||
|
if (ot->id == OT_S_BLOODBOIL) {
|
||||||
|
if (lfhasflag(victim, F_BLOODBOIL)) {
|
||||||
|
specificcheckok = B_FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
if (ot->id == OT_S_DEATHKEEN) {
|
if (ot->id == OT_S_DEATHKEEN) {
|
||||||
if (!isnighttime()) specificcheckok = B_FALSE;
|
if (!isnighttime()) specificcheckok = B_FALSE;
|
||||||
}
|
}
|
||||||
|
@ -2503,6 +2509,28 @@ int aispellok(lifeform_t *lf, enum OBTYPE spellid, lifeform_t *victim, enum FLAG
|
||||||
if ((ot->id == OT_S_DRAINLIFE) && isimmuneto(victim->flags, DT_NECROTIC, B_FALSE)) {
|
if ((ot->id == OT_S_DRAINLIFE) && isimmuneto(victim->flags, DT_NECROTIC, B_FALSE)) {
|
||||||
specificcheckok = B_FALSE;
|
specificcheckok = B_FALSE;
|
||||||
}
|
}
|
||||||
|
if (ot->id == OT_S_GATHERFLAME) {
|
||||||
|
int i,found=B_FALSE;
|
||||||
|
// don't cast if we're made of fire!
|
||||||
|
if ((lf->material->id == MT_FIRE) && (getattrbracket(getattr(lf, A_WIS), A_WIS, NULL) >= AT_AVERAGE)) {
|
||||||
|
specificcheckok = B_FALSE;
|
||||||
|
} else {
|
||||||
|
// must be fire nearby
|
||||||
|
for (i = 0; i < lf->nlos; i++) {
|
||||||
|
if (lf->los[i]->lf && (lf->los[i]->lf->material->id == MT_FIRE)) {
|
||||||
|
found = B_TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (hasobofmaterial(lf->los[i]->obpile, MT_FIRE)) {
|
||||||
|
found = B_TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!found) {
|
||||||
|
specificcheckok = B_FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
if (ot->id == OT_A_FLIP) {
|
if (ot->id == OT_A_FLIP) {
|
||||||
if (getlfsize(victim) > getlfsize(lf)) {
|
if (getlfsize(victim) > getlfsize(lf)) {
|
||||||
specificcheckok = B_FALSE;
|
specificcheckok = B_FALSE;
|
||||||
|
@ -2713,6 +2741,12 @@ int aiwants_real(lifeform_t *lf, object_t *o, int *covets, int *noids, enum OBTY
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (i = 0; i < *nwantflags; i++) {
|
for (i = 0; i < *nwantflags; i++) {
|
||||||
|
// special case to cope with eating objects that aren't normally edible.
|
||||||
|
// eg. goats eating wood due to F_CANEATMATERIAL
|
||||||
|
if ((wantflag[i] == F_EDIBLE) && caneat(lf, o)) {
|
||||||
|
if (covets) *covets = wantflagcovet[i];
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
if (hasflag(o->flags, wantflag[i])) {
|
if (hasflag(o->flags, wantflag[i])) {
|
||||||
if ((wantflag[i] == F_EDIBLE) && !caneat(lf, o)) { // special case
|
if ((wantflag[i] == F_EDIBLE) && !caneat(lf, o)) { // special case
|
||||||
} else {
|
} else {
|
||||||
|
|
77
attack.c
77
attack.c
|
@ -21,6 +21,7 @@ extern lifeform_t *player;
|
||||||
extern lifeform_t *godlf[];
|
extern lifeform_t *godlf[];
|
||||||
|
|
||||||
extern int needredraw;
|
extern int needredraw;
|
||||||
|
extern int statdirty;
|
||||||
|
|
||||||
extern enum ERROR reason;
|
extern enum ERROR reason;
|
||||||
|
|
||||||
|
@ -795,7 +796,22 @@ int attacklf(lifeform_t *lf, lifeform_t *victim, object_t *wep, flag_t *damflag)
|
||||||
if (critical && !lfhasflag(lf, F_PHANTASM)) {
|
if (critical && !lfhasflag(lf, F_PHANTASM)) {
|
||||||
object_t *armour;
|
object_t *armour;
|
||||||
char noun[BUFLEN];
|
char noun[BUFLEN];
|
||||||
|
|
||||||
|
if (lfhasflag(victim, F_CANSEVER) && wep && (getdamtype(wep) == DT_SLASH)) {
|
||||||
|
flag_t *retflag[MAXCANDIDATES],*poss[MAXCANDIDATES],*f;
|
||||||
|
int nretflags = 0,nposs = 0;
|
||||||
|
// select a random sever-able body part
|
||||||
|
getflags(victim->flags, retflag, &nretflags, F_CANSEVER, F_NONE);
|
||||||
|
for (i = 0; i < nretflags; i++) {
|
||||||
|
if (hasbp(victim, retflag[i]->val[0])) {
|
||||||
|
poss[nposs++] = retflag[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
f = poss[rnd(0,nposs-1)];
|
||||||
|
critpos = f->val[0];
|
||||||
|
} else {
|
||||||
critpos = getrandomcorebp(victim, lf);
|
critpos = getrandomcorebp(victim, lf);
|
||||||
|
}
|
||||||
if (critpos == BP_NONE) {
|
if (critpos == BP_NONE) {
|
||||||
strcpy(victimbpname, victimname);
|
strcpy(victimbpname, victimname);
|
||||||
} else {
|
} else {
|
||||||
|
@ -1829,6 +1845,65 @@ void criticalhit(lifeform_t *lf, lifeform_t *victim, enum BODYPART hitpos, int d
|
||||||
if (damtype == DT_PIERCE) damtype = DT_SLASH;
|
if (damtype == DT_PIERCE) damtype = DT_SLASH;
|
||||||
if (damtype == DT_CHOP) damtype = DT_SLASH;
|
if (damtype == DT_CHOP) damtype = DT_SLASH;
|
||||||
|
|
||||||
|
// special case - beheading multiheaded monsters
|
||||||
|
if (lf && victim && (damtype == DT_SLASH)) {
|
||||||
|
flag_t *selflag;
|
||||||
|
selflag = lfhasflagval(victim, F_CANSEVER, hitpos, NA, NA, NULL);
|
||||||
|
if (selflag) {
|
||||||
|
int i,nretflags,num;
|
||||||
|
char dambuf[BUFLEN];
|
||||||
|
char bpname[BUFLEN];
|
||||||
|
flag_t *retflag[MAXCANDIDATES];
|
||||||
|
strcpy(bpname, getbodypartname(victim, hitpos));
|
||||||
|
// special case
|
||||||
|
if (!victim->race->id == R_HYDRA) {
|
||||||
|
// remove it
|
||||||
|
addflag(victim->flags, F_NOBODYPART, hitpos, NA, NA, NULL);
|
||||||
|
// remove hasattack flags
|
||||||
|
getflags(victim->flags, retflag, &nretflags, F_CANCAST, F_HASATTACK, F_NONE);
|
||||||
|
for (i = 0; i < nretflags; i++) {
|
||||||
|
if (retflag[i]->id == F_CANCAST) {
|
||||||
|
if (retflag[i]->val[0] == selflag->val[2]) {
|
||||||
|
killflag(retflag[i]);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
} else if (retflag[i]->id == F_HASATTACK) {
|
||||||
|
if (retflag[i]->val[2] == selflag->val[1]) {
|
||||||
|
killflag(retflag[i]);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (cansee(player, victim)) {
|
||||||
|
char lfname[BUFLEN],vname[BUFLEN];
|
||||||
|
getlfname(victim, vname);
|
||||||
|
if (lf && cansee(player, lf)) { // can see who did it
|
||||||
|
getlfname(lf, lfname);
|
||||||
|
} else {
|
||||||
|
strcpy(lfname, "Something");
|
||||||
|
}
|
||||||
|
msg("^%c%s slice%s off %s%s %s!", getlfcol(victim, CC_VBAD),
|
||||||
|
lfname, isplayer(lf) ? "" : "s", vname, getpossessive(vname), bpname);
|
||||||
|
}
|
||||||
|
// take extra damage based on number of severable limbs
|
||||||
|
num = countflagsofid(victim->race->flags, F_CANSEVER);
|
||||||
|
|
||||||
|
if (victim->race->id == R_HYDRA) {
|
||||||
|
growhydrahead(victim, B_TRUE);
|
||||||
|
} else {
|
||||||
|
sprintf(dambuf, "a severed %s", bpname);
|
||||||
|
losehp(victim, pctof(100/num, victim->maxhp), DT_DIRECT, lf, dambuf);
|
||||||
|
}
|
||||||
|
|
||||||
|
// drop the head
|
||||||
|
if (strlen(selflag->text)) {
|
||||||
|
addob(victim->cell->obpile, selflag->text);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (damtype == DT_BASH) {
|
if (damtype == DT_BASH) {
|
||||||
switch (hitpos) {
|
switch (hitpos) {
|
||||||
default:
|
default:
|
||||||
|
@ -2572,8 +2647,6 @@ void wepeffects(flagpile_t *fp, cell_t *where, flag_t *damflag, int dam) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
getflags(fp, retflag, &nretflags, F_FLAMESTRIKE, F_HEAVYBLOW, F_HITCONFER, F_RACESLAY, F_REVENGE, F_RUSTED, F_NONE);
|
getflags(fp, retflag, &nretflags, F_FLAMESTRIKE, F_HEAVYBLOW, F_HITCONFER, F_RACESLAY, F_REVENGE, F_RUSTED, F_NONE);
|
||||||
for (i = 0; i < nretflags; i++) {
|
for (i = 0; i < nretflags; i++) {
|
||||||
f = retflag[i];
|
f = retflag[i];
|
||||||
|
|
149
data.c
149
data.c
|
@ -3420,6 +3420,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_TRUE, LOF_DONTNEED, NA, NULL);
|
addflag(lastot->flags, F_LOSLOF, B_TRUE, LOF_DONTNEED, NA, NULL);
|
||||||
addflag(lastot->flags, F_PLEASESGOD, R_GODFIRE, 1, NA, NULL);
|
addflag(lastot->flags, F_PLEASESGOD, R_GODFIRE, 1, NA, NULL);
|
||||||
|
addot(OT_S_GATHERFLAME, "harvest flame", "Draws all nearby fire into the caster, boosting the power of their next spell.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
|
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "Your next spell's power will be boosted by the amount of fire consumed.");
|
||||||
|
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "Spell power determines the maximum amount of fire consumed.");
|
||||||
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_SPELLLEVEL, 1, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_MAXPOWER, 5, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_AICASTTOATTACK, ST_ANYWHERE, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_LOSLOF, B_FALSE, LOF_DONTNEED, NA, NULL);
|
||||||
addot(OT_S_SPARK, "flambe", "Creates very hot but short lived burst of flame around the target, dealing 2d3 fire damage to creatures and objects.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
addot(OT_S_SPARK, "flambe", "Creates very hot but short lived burst of flame around the target, dealing 2d3 fire damage to creatures and objects.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, NA, NA, NULL);
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, NA, NA, NULL);
|
||||||
addflag(lastot->flags, F_TARGETTEDSPELL, TT_MONSTER, NA, NA, NULL);
|
addflag(lastot->flags, F_TARGETTEDSPELL, TT_MONSTER, NA, NA, NULL);
|
||||||
|
@ -3443,6 +3451,13 @@ void initobjects(void) {
|
||||||
addflag(lastot->flags, F_LOSLOF, B_TRUE, LOF_DONTNEED, NA, NULL);
|
addflag(lastot->flags, F_LOSLOF, B_TRUE, LOF_DONTNEED, NA, NULL);
|
||||||
addflag(lastot->flags, F_PLEASESGOD, R_GODFIRE, 2, NA, NULL);
|
addflag(lastot->flags, F_PLEASESGOD, R_GODFIRE, 2, NA, NULL);
|
||||||
// l2
|
// l2
|
||||||
|
addot(OT_S_BLOODBOIL, "bloodboil", "Energised the molecules of the target's blood, causing them to explode into flames upon death.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, 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_AICASTTOATTACK, ST_VICTIM, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_TARGETTEDSPELL, TT_MONSTER, NA, NA, NULL);
|
||||||
|
addflag(lastot->flags, F_LOSLOF, B_TRUE, LOF_DONTNEED, NA, NULL);
|
||||||
addot(OT_S_CLEANSINGFIRE, "cleansing fire", "Draws power from nearby fires to heal the caster.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
addot(OT_S_CLEANSINGFIRE, "cleansing fire", "Draws power from nearby fires to heal the caster.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "Spell will affect up to ^bpower^n fires, healing 30% hit points from each.");
|
addflag(lastot->flags, F_EXTRADESC, NA, NA, NA, "Spell will affect up to ^bpower^n fires, healing 30% hit points from each.");
|
||||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, NA, NA, NULL);
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_FIRE, NA, NA, NULL);
|
||||||
|
@ -4021,7 +4036,7 @@ void initobjects(void) {
|
||||||
// mental/psionic
|
// mental/psionic
|
||||||
///////////////////
|
///////////////////
|
||||||
// l1
|
// l1
|
||||||
addot(OT_S_BOOSTCONFIDENCE, "boost confidence", "Instils the target with infinite courage, allowing them to (perhaps foolishly) continue fighting even when all seems lost.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
addot(OT_S_BOOSTCONFIDENCE, "ego boost", "Instils the target with boundless courage, allowing them to (perhaps foolishly) continue fighting even when all seems lost.", MT_NOTHING, 0, OC_SPELL, SZ_TINY);
|
||||||
addflag(lastot->flags, F_SPELLSCHOOL, SS_MENTAL, NA, NA, NULL);
|
addflag(lastot->flags, F_SPELLSCHOOL, SS_MENTAL, NA, NA, NULL);
|
||||||
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);
|
||||||
|
@ -9683,6 +9698,54 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_MINIONS, 20, 1, 3, "goblin warrior");
|
addflag(lastrace->flags, F_MINIONS, 20, 1, 3, "goblin warrior");
|
||||||
addflag(lastrace->flags, F_MORALE, 10, NA, NA, NULL);
|
addflag(lastrace->flags, F_MORALE, 10, NA, NA, NULL);
|
||||||
|
|
||||||
|
addrace(R_CHIMERA, "chimera", 300, 'm', C_MAGENTA, MT_FLESH, RC_MAGIC, "A monstrous hybrid where a goat's rear has been magically attached to a lion's front. It has three heads - a goat's, a lion's and a wyrm's - and a pair of bat-like wings.");
|
||||||
|
setbodytype(lastrace, BT_QUADRAPED);
|
||||||
|
setbodypartname(lastrace, BP_HEAD, "lion's head");
|
||||||
|
addbodypart(lastrace, BP_HEAD2, "dragon's head");
|
||||||
|
addbodypart(lastrace, BP_HEAD3, "goat's head");
|
||||||
|
addbodypart(lastrace, BP_TAIL, NULL);
|
||||||
|
addbodypart(lastrace, BP_WINGS, NULL);
|
||||||
|
addflag(lastrace->flags, F_ALIGNMENT, AL_EVIL, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HOSTILE, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_SIZE, SZ_LARGE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_RARITY, H_ALL, NA, RR_VERYRARE, NULL);
|
||||||
|
addflag(lastrace->flags, F_HITDICE, 9, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_TR, 9, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_STR, AT_HIGH, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_IQ, AT_VLOW, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_AGI, AT_GTAVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_CON, AT_AVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_WIS, AT_VLOW, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_CHA, AT_VLOW, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_MOVESPEED, SP_NORMAL, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_ACTIONSPEED, SP_NORMAL, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_NATURALFLIGHT, B_TRUE, NA, NA, "");
|
||||||
|
addflag(lastrace->flags, F_CANWILL, OT_S_FLIGHT, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_SPELLCASTTEXT, OT_S_FLIGHT, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 4, BP_HEAD, NULL); // lion head
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 3, BP_HEAD2, NULL); // dragon head
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_HORN, 5, BP_HEAD3, NULL); // goat horns
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_CLAWS, 3, NA, NULL); // front lion claws
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_CLAWS, 3, NA, NULL); // front lion claws
|
||||||
|
addflag(lastrace->flags, F_NOISETEXT, N_GETANGRY, SV_CAR, NA, "roars^a roar");
|
||||||
|
addflag(lastrace->flags, F_NOISETEXT, N_GETANGRY, SV_SHOUT, NA, "bleats^an angry bleating");
|
||||||
|
addflag(lastrace->flags, F_NOISETEXT, N_LOWHP, 3, NA, "screeches in pain^screeches of pain");
|
||||||
|
addflag(lastrace->flags, F_CANSEVER, BP_HEAD, BP_HEAD, NA, "lion head");
|
||||||
|
addflag(lastrace->flags, F_CANSEVER, BP_HEAD2, BP_HEAD2, OT_S_BURNINGWAVE, "red wyrm head");
|
||||||
|
addflag(lastrace->flags, F_CANSEVER, BP_HEAD3, BP_HEAD3, NA, "goat head");
|
||||||
|
addflag(lastrace->flags, F_CANWILL, OT_A_SWOOP, NA, NA, "range:2;");
|
||||||
|
addflag(lastrace->flags, F_CANCAST, OT_S_BURNINGWAVE, NA, NA, "pw:6;");
|
||||||
|
addflag(lastrace->flags, F_CASTCHANCE, 40, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_SPELLCASTTEXT, OT_NONE, NA, NA, "unleashes its fiery breath");
|
||||||
|
addflag(lastrace->flags, F_SEEINDARK, 2, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_MORALE, 14, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CARNIVORE, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_WANTSOBFLAG, F_EDIBLE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_FELINE, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_AVIAN, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_EATCONFER, F_MUTABLE, B_TRUE, NA, "100");
|
||||||
|
|
||||||
addrace(R_CENTAUR, "centaur", 500, 'u', C_GREY, MT_FLESH, RC_ANIMAL, "Centaurs look like horses with their neck upwards replaced by a human torso and arms.");
|
addrace(R_CENTAUR, "centaur", 500, 'u', C_GREY, MT_FLESH, RC_ANIMAL, "Centaurs look like horses with their neck upwards replaced by a human torso and arms.");
|
||||||
setbodytype(lastrace, BT_QUADRAPED);
|
setbodytype(lastrace, BT_QUADRAPED);
|
||||||
addbodypart(lastrace, BP_TAIL, NULL);
|
addbodypart(lastrace, BP_TAIL, NULL);
|
||||||
|
@ -10778,6 +10841,43 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_NOCTURNAL, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_NOCTURNAL, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_MORALE, 7, NA, NA, NULL);
|
addflag(lastrace->flags, F_MORALE, 7, NA, NA, NULL);
|
||||||
|
|
||||||
|
addrace(R_HYDRA, "hydra", 300, 'W', C_BLUE, MT_FLESH, RC_DRAGON, "A four legged serpentine reptile, resembling a wyrm except for its many extra heads.");
|
||||||
|
setbodytype(lastrace, BT_QUADRAPED);
|
||||||
|
addbodypart(lastrace, BP_TAIL, NULL);
|
||||||
|
addflag(lastrace->flags, F_ALIGNMENT, AL_EVIL, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HOSTILE, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_SIZE, SZ_HUGE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_RARITY, H_ALL, NA, RR_VERYRARE, NULL);
|
||||||
|
addflag(lastrace->flags, F_HITDICE, 5, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_TR, 11, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_STR, AT_HIGH, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_IQ, IQ_ANIMAL, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_AGI, AT_AVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_CON, AT_AVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_WIS, AT_VLOW, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_CHA, AT_VLOW, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_MOVESPEED, SP_NORMAL, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_ACTIONSPEED, SP_NORMAL, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 4, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 4, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 4, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 4, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 4, NA, NULL);
|
||||||
|
// note: addlf() will add extra teeth attacks based on heads.
|
||||||
|
addflag(lastrace->flags, F_NOISETEXT, N_GETANGRY, SV_CAR, NA, "hisses^a loud hissing");
|
||||||
|
addflag(lastrace->flags, F_NOISETEXT, N_LOWHP, 3, NA, "roars in pain^roars of pain");
|
||||||
|
addflag(lastrace->flags, F_CANSEVER, BP_HEAD, BP_HEAD, NA, "hydra head");
|
||||||
|
//addflag(lastrace->flags, F_CANCAST, OT_S_BURNINGWAVE, NA, NA, "pw:6;");
|
||||||
|
//addflag(lastrace->flags, F_CASTCHANCE, 40, NA, NA, NULL);
|
||||||
|
//addflag(lastrace->flags, F_SPELLCASTTEXT, OT_NONE, NA, NA, "unleashes its fiery breath");
|
||||||
|
addflag(lastrace->flags, F_SEEINDARK, 4, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_MORALE, 10, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_DTIMMUNE, DT_POISON, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CARNIVORE, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_WANTSOBFLAG, F_EDIBLE, NA, NA, NULL);
|
||||||
|
|
||||||
|
|
||||||
addrace(R_KOBOLD, "kobold", 18, 'k', C_BROWN, MT_FLESH, RC_HUMANOID, "An evil humanoid race with doglike features, kobolds are known for their cowardace and prefer to attack from a distance if at all possible.");
|
addrace(R_KOBOLD, "kobold", 18, 'k', C_BROWN, MT_FLESH, RC_HUMANOID, "An evil humanoid race with doglike features, kobolds are known for their cowardace and prefer to attack from a distance if at all possible.");
|
||||||
setbodytype(lastrace, BT_HUMANOID);
|
setbodytype(lastrace, BT_HUMANOID);
|
||||||
setbodypartname(lastrace, BP_HANDS, "paws");
|
setbodypartname(lastrace, BP_HANDS, "paws");
|
||||||
|
@ -13806,6 +13906,42 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_DTVULN, DT_SONIC, NA, NA, NULL);
|
addflag(lastrace->flags, F_DTVULN, DT_SONIC, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_MORALE, 5, NA, NA, NULL);
|
addflag(lastrace->flags, F_MORALE, 5, NA, NA, NULL);
|
||||||
|
|
||||||
|
addrace(R_GOAT, "goat", 37, 'q', C_YELLOW, MT_FLESH, RC_ANIMAL, "Small, horned livestocks animals known for their appetite.");
|
||||||
|
setbodytype(lastrace, BT_QUADRAPED);
|
||||||
|
addbodypart(lastrace, BP_TAIL, NULL);
|
||||||
|
addflag(lastrace->flags, F_ALIGNMENT, AL_NEUTRAL, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_TERRITORIAL, 3, NA , NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_RARITY, H_DUNGEON, NA, RR_UNCOMMON, "");
|
||||||
|
addflag(lastrace->flags, F_RARITY, H_FOREST, NA, RR_COMMON, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_STR, AT_AVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_IQ, IQ_ANIMAL, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_AGI, AT_AVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_CON, AT_VHIGH, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_WIS, AT_LTAVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_STARTATT, A_CHA, AT_AVERAGE, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_SIZE, SZ_MEDIUM, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_MOVESPEED, SP_NORMAL, NA, NA, "");
|
||||||
|
addflag(lastrace->flags, F_ACTIONSPEED, SP_NORMAL, NA, NA, "");
|
||||||
|
addflag(lastrace->flags, F_HITDICE, 1, 2, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_TR, 1, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_HORN, 3, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_HASATTACK, OT_TEETH, 3, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_MAXATTACKS, 1, 1, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANWILL, OT_A_CHARGE, NA, NA, "range:3;");
|
||||||
|
addflag(lastrace->flags, F_NOISETEXT, N_LOWHP, 4, NA, "bleats in pain^bleating");
|
||||||
|
addflag(lastrace->flags, F_NOISETEXT, N_GETANGRY, SV_SHOUT, NA, "bleats^an angry bleating");
|
||||||
|
addflag(lastrace->flags, F_FLEEONHPPCT, 80, NA, NA, "");
|
||||||
|
addflag(lastrace->flags, F_WANTSOBFLAG, F_EDIBLE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_WOOD, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_CLOTH, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_LEATHER, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_PAPER, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_PLASTIC, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_WETPAPER, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_RUBBER, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_SILK, NA, NA, NULL);
|
||||||
|
addflag(lastrace->flags, F_CANEATMATERIAL, MT_PLANT, NA, NA, NULL);
|
||||||
|
|
||||||
addrace(R_GYRFALCON, "gyrfalcon", 1, 'A', C_WHITE, MT_FLESH, RC_ANIMAL, "An enormous falcon, commonly found in arctic climates."); // 'A' for Avian
|
addrace(R_GYRFALCON, "gyrfalcon", 1, 'A', C_WHITE, MT_FLESH, RC_ANIMAL, "An enormous falcon, commonly found in arctic climates."); // 'A' for Avian
|
||||||
setbodytype(lastrace, BT_BIRD);
|
setbodytype(lastrace, BT_BIRD);
|
||||||
|
@ -14817,7 +14953,7 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_CANEATRAW, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_CARNIVORE, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_CARNIVORE, B_TRUE, NA, NA, NULL);
|
||||||
|
|
||||||
addrace(R_DRAGONBLUE, "blue wyrm", 400, 'W', C_BLUE, MT_FLESH, RC_DRAGON, "Blue wyrms are massive reptilian creatures who can (and will) consume almost any living creature.");
|
addrace(R_DRAGONBLUE, "blue wyrm", 400, 'W', C_CYAN, MT_FLESH, RC_DRAGON, "Blue wyrms are massive reptilian creatures who can (and will) consume almost any living creature.");
|
||||||
setbodytype(lastrace, BT_HUMANOID);
|
setbodytype(lastrace, BT_HUMANOID);
|
||||||
addbodypart(lastrace, BP_WINGS, NULL);
|
addbodypart(lastrace, BP_WINGS, NULL);
|
||||||
addbodypart(lastrace, BP_TAIL, NULL);
|
addbodypart(lastrace, BP_TAIL, NULL);
|
||||||
|
@ -14868,7 +15004,7 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_EATCONFER, F_DTRESIST, DT_ELECTRIC, NA, "100");
|
addflag(lastrace->flags, F_EATCONFER, F_DTRESIST, DT_ELECTRIC, NA, "100");
|
||||||
addflag(lastrace->flags, F_EATCONFER, F_ATTRMOD, A_STR, 5, "50");
|
addflag(lastrace->flags, F_EATCONFER, F_ATTRMOD, A_STR, 5, "50");
|
||||||
|
|
||||||
addrace(R_DRAGONBLUEY, "blue wyrmling", 150, 'w', C_BLUE, MT_FLESH, RC_DRAGON, "Blue wyrms are massive reptilian creatures who can (and will) consume almost any living creature.");
|
addrace(R_DRAGONBLUEY, "blue wyrmling", 150, 'w', C_CYAN, MT_FLESH, RC_DRAGON, "Blue wyrms are massive reptilian creatures who can (and will) consume almost any living creature.");
|
||||||
setbodytype(lastrace, BT_HUMANOID);
|
setbodytype(lastrace, BT_HUMANOID);
|
||||||
addbodypart(lastrace, BP_WINGS, NULL);
|
addbodypart(lastrace, BP_WINGS, NULL);
|
||||||
addbodypart(lastrace, BP_TAIL, NULL);
|
addbodypart(lastrace, BP_TAIL, NULL);
|
||||||
|
@ -14919,7 +15055,7 @@ void initrace(void) {
|
||||||
addflag(lastrace->flags, F_CARNIVORE, B_TRUE, NA, NA, NULL);
|
addflag(lastrace->flags, F_CARNIVORE, B_TRUE, NA, NA, NULL);
|
||||||
addflag(lastrace->flags, F_EATCONFER, F_DTRESIST, DT_ELECTRIC, NA, "50");
|
addflag(lastrace->flags, F_EATCONFER, F_DTRESIST, DT_ELECTRIC, NA, "50");
|
||||||
addflag(lastrace->flags, F_EATCONFER, F_ATTRMOD, A_STR, 5, "25");
|
addflag(lastrace->flags, F_EATCONFER, F_ATTRMOD, A_STR, 5, "25");
|
||||||
addrace(R_DRAGONBLUEA, "ancient blue wyrm", 600, 'W', C_BLUE, MT_FLESH, RC_DRAGON, "Blue wyrms are massive reptilian creatures who can (and will) consume almost any living creature.");
|
addrace(R_DRAGONBLUEA, "ancient blue wyrm", 600, 'W', C_CYAN, MT_FLESH, RC_DRAGON, "Blue wyrms are massive reptilian creatures who can (and will) consume almost any living creature.");
|
||||||
setbodytype(lastrace, BT_HUMANOID);
|
setbodytype(lastrace, BT_HUMANOID);
|
||||||
addbodypart(lastrace, BP_WINGS, NULL);
|
addbodypart(lastrace, BP_WINGS, NULL);
|
||||||
addbodypart(lastrace, BP_TAIL, NULL);
|
addbodypart(lastrace, BP_TAIL, NULL);
|
||||||
|
@ -16657,6 +16793,11 @@ void initrace(void) {
|
||||||
addflag(r->flags, F_NOFLEE, B_TRUE, NA, NA, NULL);
|
addflag(r->flags, F_NOFLEE, B_TRUE, NA, NA, NULL);
|
||||||
addflag(r->flags, F_NOSLEEP, B_TRUE, NA, NA, NULL);
|
addflag(r->flags, F_NOSLEEP, B_TRUE, NA, NA, NULL);
|
||||||
addflag(r->flags, F_SEEINVIS, B_TRUE, NA, NA, NULL);
|
addflag(r->flags, F_SEEINVIS, B_TRUE, NA, NA, NULL);
|
||||||
|
} else if (r->raceclass->id == RC_DRAGON) {
|
||||||
|
// wyrms hate hydras
|
||||||
|
if (r->id != R_HYDRA) {
|
||||||
|
addflag(r->flags, F_HATESRACE, R_HYDRA, NA, NA, NULL);
|
||||||
|
}
|
||||||
} else if (r->raceclass->id == RC_GOD) {
|
} else if (r->raceclass->id == RC_GOD) {
|
||||||
addflag(r->flags, F_PIETY, 100, NA, NA, NULL);
|
addflag(r->flags, F_PIETY, 100, NA, NA, NULL);
|
||||||
addflag(r->flags, F_HUMANOID, B_TRUE, NA, NA, NULL);
|
addflag(r->flags, F_HUMANOID, B_TRUE, NA, NA, NULL);
|
||||||
|
|
22
defs.h
22
defs.h
|
@ -1021,6 +1021,7 @@ enum RACE {
|
||||||
R_BOGGART,
|
R_BOGGART,
|
||||||
R_BUGBEAR,
|
R_BUGBEAR,
|
||||||
R_CENTAUR,
|
R_CENTAUR,
|
||||||
|
R_CHIMERA,
|
||||||
R_COCKATRICE,
|
R_COCKATRICE,
|
||||||
R_CREEPINGCLAW,
|
R_CREEPINGCLAW,
|
||||||
R_CRYMIDIA,
|
R_CRYMIDIA,
|
||||||
|
@ -1045,6 +1046,7 @@ enum RACE {
|
||||||
R_HIPPOGRIFF,
|
R_HIPPOGRIFF,
|
||||||
R_HOBGOBLIN,
|
R_HOBGOBLIN,
|
||||||
R_HOBGOBLINWAR,
|
R_HOBGOBLINWAR,
|
||||||
|
R_HYDRA,
|
||||||
R_KOBOLD,
|
R_KOBOLD,
|
||||||
R_LEPRECHAUN,
|
R_LEPRECHAUN,
|
||||||
R_LESHY,
|
R_LESHY,
|
||||||
|
@ -1142,6 +1144,7 @@ enum RACE {
|
||||||
R_DOGDEATH,
|
R_DOGDEATH,
|
||||||
R_DOGWAR,
|
R_DOGWAR,
|
||||||
R_ELEPHANT,
|
R_ELEPHANT,
|
||||||
|
R_GOAT,
|
||||||
R_GYRFALCON,
|
R_GYRFALCON,
|
||||||
R_HARPY,
|
R_HARPY,
|
||||||
R_HAWK,
|
R_HAWK,
|
||||||
|
@ -1589,8 +1592,9 @@ enum OBTYPE {
|
||||||
OT_S_TORNADO,
|
OT_S_TORNADO,
|
||||||
OT_S_WHIRLWIND,
|
OT_S_WHIRLWIND,
|
||||||
OT_S_WINDSHIELD,
|
OT_S_WINDSHIELD,
|
||||||
// -- elemental - fire
|
// -- elemental - fire magic
|
||||||
OT_S_BLADEBURN,
|
OT_S_BLADEBURN,
|
||||||
|
OT_S_BLOODBOIL,
|
||||||
OT_S_BURNINGFEET,
|
OT_S_BURNINGFEET,
|
||||||
OT_S_BURNINGWAVE,
|
OT_S_BURNINGWAVE,
|
||||||
OT_S_CLEANSINGFIRE,
|
OT_S_CLEANSINGFIRE,
|
||||||
|
@ -1599,6 +1603,7 @@ enum OBTYPE {
|
||||||
OT_S_FIREBALL,
|
OT_S_FIREBALL,
|
||||||
OT_S_FLAMEPILLAR,
|
OT_S_FLAMEPILLAR,
|
||||||
OT_S_FLAMEBURST,
|
OT_S_FLAMEBURST,
|
||||||
|
OT_S_GATHERFLAME,
|
||||||
OT_S_IMMOLATE,
|
OT_S_IMMOLATE,
|
||||||
OT_S_METEOR,
|
OT_S_METEOR,
|
||||||
OT_S_PYROMANIA,
|
OT_S_PYROMANIA,
|
||||||
|
@ -2249,8 +2254,10 @@ enum BODYPART {
|
||||||
BP_FRONTLEGS = 15,
|
BP_FRONTLEGS = 15,
|
||||||
BP_WINGS = 16, // <- core bodypart
|
BP_WINGS = 16, // <- core bodypart
|
||||||
BP_TAIL = 17, // <- core bodypart
|
BP_TAIL = 17, // <- core bodypart
|
||||||
|
BP_HEAD2 = 18,
|
||||||
|
BP_HEAD3 = 19,
|
||||||
};
|
};
|
||||||
#define MAXBODYPARTS (18)
|
#define MAXBODYPARTS (20)
|
||||||
|
|
||||||
// depth on a human
|
// depth on a human
|
||||||
|
|
||||||
|
@ -2723,6 +2730,7 @@ enum FLAG {
|
||||||
F_OBATTACKDELAY, // how long weapon takes to attack
|
F_OBATTACKDELAY, // how long weapon takes to attack
|
||||||
F_USESSKILL, // weapon needs skill sk_v0
|
F_USESSKILL, // weapon needs skill sk_v0
|
||||||
F_MAGICBOOST, // boost power of all spells by v0
|
F_MAGICBOOST, // boost power of all spells by v0
|
||||||
|
F_TEMPMAGICBOOST, // boost power of next spell cast (only) by v0
|
||||||
F_WHIP, // this weapon is a whip - use different damtext.
|
F_WHIP, // this weapon is a whip - use different damtext.
|
||||||
F_CANHAVEOBMOD, // weapon can have obmod om_v0 applied
|
F_CANHAVEOBMOD, // weapon can have obmod om_v0 applied
|
||||||
// optional: v1 is chance of randomly having it
|
// optional: v1 is chance of randomly having it
|
||||||
|
@ -2874,6 +2882,13 @@ enum FLAG {
|
||||||
// f_armourrating is used for innate armour.
|
// f_armourrating is used for innate armour.
|
||||||
// f_arboost is used by objects "of protection" which
|
// f_arboost is used by objects "of protection" which
|
||||||
// enhance your armour rating.
|
// enhance your armour rating.
|
||||||
|
F_BLOODBOIL, // lf will explode into flames upon death
|
||||||
|
F_CANSEVER, // critical slash attacks might sever bodypart v0
|
||||||
|
// v1: (optional) this will also remove HASATTACK
|
||||||
|
// flags with v2=this.
|
||||||
|
// v2: (optional) will also remove flags of CANCAST
|
||||||
|
// with v0 = this.
|
||||||
|
// text: object name of severed limb to drop
|
||||||
F_DONEPICKUP, // lf has used their free pickup/drop for this turn.
|
F_DONEPICKUP, // lf has used their free pickup/drop for this turn.
|
||||||
F_DONEKNOWLEDGETRADE, // you've already traded knowledge with this
|
F_DONEKNOWLEDGETRADE, // you've already traded knowledge with this
|
||||||
// person.
|
// person.
|
||||||
|
@ -3164,6 +3179,7 @@ enum FLAG {
|
||||||
F_WANTS, // lf will try to pick up object type val0.
|
F_WANTS, // lf will try to pick up object type val0.
|
||||||
// if val1 = B_COVETS, will even abandon attacks
|
// if val1 = B_COVETS, will even abandon attacks
|
||||||
// for it!
|
// for it!
|
||||||
|
F_WANTSOBMAT, // lf will look for obs of material v0. val1=covets
|
||||||
F_WANTSOBFLAG, // lf will look for obs with this flag. val1=covets
|
F_WANTSOBFLAG, // lf will look for obs with this flag. val1=covets
|
||||||
F_WANTSBETTERWEP, // lf will look for better weapons, val1=covets
|
F_WANTSBETTERWEP, // lf will look for better weapons, val1=covets
|
||||||
F_WANTSBETTERARM, // lf will look for better armour, val1=covets
|
F_WANTSBETTERARM, // lf will look for better armour, val1=covets
|
||||||
|
@ -3295,6 +3311,8 @@ enum FLAG {
|
||||||
// try to change its facing.
|
// try to change its facing.
|
||||||
F_CANTALK, // this lf can talk, even if its raceclass normally
|
F_CANTALK, // this lf can talk, even if its raceclass normally
|
||||||
// wouldn't be able to.
|
// wouldn't be able to.
|
||||||
|
F_CANEATMATERIAL, // this lf can eat objects with material v0,
|
||||||
|
// even if it's not normally edible.
|
||||||
F_AQUATIC, // this race can attack normally in water and suffers no
|
F_AQUATIC, // this race can attack normally in water and suffers no
|
||||||
// movement penalties. they can also swim at master
|
// movement penalties. they can also swim at master
|
||||||
// level.
|
// level.
|
||||||
|
|
57
io.c
57
io.c
|
@ -1450,6 +1450,13 @@ int announceflaggain(lifeform_t *lf, flag_t *f) {
|
||||||
}
|
}
|
||||||
donesomething = B_TRUE;
|
donesomething = B_TRUE;
|
||||||
break;
|
break;
|
||||||
|
case F_BLOODBOIL:
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
msg("A malignant red nimbus surrounds you.");
|
||||||
|
} else if (cansee(player, lf)) {
|
||||||
|
msg("A malignant red nimbus surrounds %s.", lfname);
|
||||||
|
}
|
||||||
|
break;
|
||||||
case F_BREATHWATER:
|
case F_BREATHWATER:
|
||||||
if (isplayer(lf)) {
|
if (isplayer(lf)) {
|
||||||
msg("You can now breath normally underwater.");
|
msg("You can now breath normally underwater.");
|
||||||
|
@ -1947,6 +1954,13 @@ int announceflaggain(lifeform_t *lf, flag_t *f) {
|
||||||
msg("%s %s stunned!",lfname, is(lf));
|
msg("%s %s stunned!",lfname, is(lf));
|
||||||
donesomething = B_TRUE;
|
donesomething = B_TRUE;
|
||||||
break;
|
break;
|
||||||
|
case F_TEMPMAGICBOOST:
|
||||||
|
// don't know if monsters get it
|
||||||
|
// also we only announce GAINING this flag, not losing it
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
msg("Your magical power feels temporarily boosted!");
|
||||||
|
}
|
||||||
|
break;
|
||||||
case F_TREMORSENSE:
|
case F_TREMORSENSE:
|
||||||
if (isplayer(lf)) { // don't know if monsters get it
|
if (isplayer(lf)) { // don't know if monsters get it
|
||||||
msg("You can now 'see' by sensing vibrations around you.");
|
msg("You can now 'see' by sensing vibrations around you.");
|
||||||
|
@ -2168,6 +2182,13 @@ int announceflagloss(lifeform_t *lf, flag_t *f) {
|
||||||
msg("%s can see again.",lfname);
|
msg("%s can see again.",lfname);
|
||||||
donesomething = B_TRUE;
|
donesomething = B_TRUE;
|
||||||
break;
|
break;
|
||||||
|
case F_BLOODBOIL:
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
msg("A calming blue nimbus surrounds you.");
|
||||||
|
} else if (cansee(player, lf)) {
|
||||||
|
msg("A calming blue nimbus surrounds %s.", lfname);
|
||||||
|
}
|
||||||
|
break;
|
||||||
case F_BREATHWATER:
|
case F_BREATHWATER:
|
||||||
if (isplayer(lf)) {
|
if (isplayer(lf)) {
|
||||||
msg("%s can no longer breath underwater.",lfname);
|
msg("%s can no longer breath underwater.",lfname);
|
||||||
|
@ -11552,10 +11573,23 @@ void showlfstats(lifeform_t *lf, int showall) {
|
||||||
|
|
||||||
// unarmed attacks
|
// unarmed attacks
|
||||||
op = addobpile(NULL, NULL, NULL);
|
op = addobpile(NULL, NULL, NULL);
|
||||||
for (f = lf->flags->first ; f ; f = f->next) {
|
getflags(lf->flags, retflag, &nretflags, F_HASATTACK, F_NONE);
|
||||||
if (f->id == F_HASATTACK) {
|
for (i = 0; i < nretflags; i++) {
|
||||||
object_t *o;
|
object_t *o;
|
||||||
objecttype_t *ot;
|
objecttype_t *ot;
|
||||||
|
int instances = 1;
|
||||||
|
int n;
|
||||||
|
|
||||||
|
f = retflag[i];
|
||||||
|
for (n = i+1 ; n < nretflags; n++) {
|
||||||
|
if ((retflag[n]->val[0] == f->val[0]) &&
|
||||||
|
(retflag[n]->val[1] == f->val[1]) &&
|
||||||
|
(retflag[n]->val[2] == f->val[2]) &&
|
||||||
|
streq(retflag[n]->text, f->text)) {
|
||||||
|
instances++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ot = findot(f->val[0]);
|
ot = findot(f->val[0]);
|
||||||
o = addobfast(op, ot->id);
|
o = addobfast(op, ot->id);
|
||||||
if (o) {
|
if (o) {
|
||||||
|
@ -11581,7 +11615,12 @@ void showlfstats(lifeform_t *lf, int showall) {
|
||||||
}
|
}
|
||||||
|
|
||||||
doheadingsmall(mainwin, y2, x2, ftext, "Innate Attack");
|
doheadingsmall(mainwin, y2, x2, ftext, "Innate Attack");
|
||||||
|
// add '2 x whatever' for multiples.
|
||||||
|
if (instances == 1) {
|
||||||
wprintw(mainwin, "%s", buf);
|
wprintw(mainwin, "%s", buf);
|
||||||
|
} else {
|
||||||
|
wprintw(mainwin, "%d x %s", instances, buf);
|
||||||
|
}
|
||||||
if (strlen(dambuf)) {
|
if (strlen(dambuf)) {
|
||||||
if (lorelev >= PR_BEGINNER) setcol(mainwin, lorecol);
|
if (lorelev >= PR_BEGINNER) setcol(mainwin, lorecol);
|
||||||
wprintw(mainwin, "%s", dambuf);
|
wprintw(mainwin, "%s", dambuf);
|
||||||
|
@ -11589,9 +11628,13 @@ void showlfstats(lifeform_t *lf, int showall) {
|
||||||
}
|
}
|
||||||
y2++;
|
y2++;
|
||||||
} // end if o
|
} // end if o
|
||||||
} // end if fid == hasattack
|
// now skip over multiple instances of the same flag
|
||||||
|
if (instances >= 2) {
|
||||||
|
i += (instances-1);
|
||||||
|
}
|
||||||
} // end for each flag
|
} // end for each flag
|
||||||
|
|
||||||
|
|
||||||
// no attacks at all?
|
// no attacks at all?
|
||||||
if ((nweps == 0) && !op->first) {
|
if ((nweps == 0) && !op->first) {
|
||||||
snprintf(buf, BUFLEN, "N/A");
|
snprintf(buf, BUFLEN, "N/A");
|
||||||
|
@ -12849,6 +12892,14 @@ void showlfstats(lifeform_t *lf, int showall) {
|
||||||
isplayer(lf) ? "your" : "its", boost);
|
isplayer(lf) ? "your" : "its", boost);
|
||||||
y++;
|
y++;
|
||||||
}
|
}
|
||||||
|
f = lfhasknownflag(lf, F_TEMPMAGICBOOST);
|
||||||
|
if (f && (f->known)) {
|
||||||
|
int boost;
|
||||||
|
sumflags(lf->flags, F_TEMPMAGICBOOST, &boost, NULL, NULL);
|
||||||
|
mvwprintw(mainwin, y, 0, "The power of %s next spell will be boosted by %d.",
|
||||||
|
isplayer(lf) ? "your" : "its", boost);
|
||||||
|
y++;
|
||||||
|
}
|
||||||
f = lfhasknownflag(lf, F_MINDSHIELD);
|
f = lfhasknownflag(lf, F_MINDSHIELD);
|
||||||
if (f && (f->known)) {
|
if (f && (f->known)) {
|
||||||
mvwprintw(mainwin, y, 0, "%s are protected from psionic attacks.", you(lf));
|
mvwprintw(mainwin, y, 0, "%s are protected from psionic attacks.", you(lf));
|
||||||
|
|
131
lf.c
131
lf.c
|
@ -768,6 +768,11 @@ int caneat(lifeform_t *lf, object_t *o) {
|
||||||
return B_FALSE;
|
return B_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// note: must do this check _before_ call to isedible()!
|
||||||
|
if (lfhasflagval(lf, F_CANEATMATERIAL, o->material->id, NA, NA, NULL)) {
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
if (!isedible(o)) {
|
if (!isedible(o)) {
|
||||||
reason = E_WRONGOBTYPE;
|
reason = E_WRONGOBTYPE;
|
||||||
return B_FALSE;
|
return B_FALSE;
|
||||||
|
@ -1145,6 +1150,8 @@ int canreachbp(lifeform_t *lf, lifeform_t *victim, enum BODYPART bp) {
|
||||||
// upper
|
// upper
|
||||||
case BP_EYES:
|
case BP_EYES:
|
||||||
case BP_HEAD:
|
case BP_HEAD:
|
||||||
|
case BP_HEAD2:
|
||||||
|
case BP_HEAD3:
|
||||||
case BP_EARS:
|
case BP_EARS:
|
||||||
case BP_NECK:
|
case BP_NECK:
|
||||||
case BP_SHOULDERS:
|
case BP_SHOULDERS:
|
||||||
|
@ -1768,12 +1775,27 @@ int castspell(lifeform_t *lf, enum OBTYPE sid, lifeform_t *targlf, object_t *tar
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
if ((sid == OT_S_GATHERFLAME) && (lf->material->id == MT_FIRE)) {
|
||||||
|
if (getattrbracket(getattr(lf, A_WIS), A_WIS, NULL) >= AT_AVERAGE) {
|
||||||
|
char ch;
|
||||||
|
ch = askchar("Casting this while made of flame will harm you, continue?","yn", "n", B_TRUE, B_FALSE);
|
||||||
|
if (ch != 'y') {
|
||||||
|
msg("Cancelled.");
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// stop hiding
|
// stop hiding
|
||||||
killflagsofid(lf->flags, F_HIDING);
|
killflagsofid(lf->flags, F_HIDING);
|
||||||
// take time
|
// take time
|
||||||
taketime(lf, getspellspeed(lf));
|
taketime(lf, getspellspeed(lf));
|
||||||
|
|
||||||
if (!fromob) {
|
if (!fromob) {
|
||||||
|
flag_t *retflag[MAXCANDIDATES];
|
||||||
|
int nretflags,tempboost = 0,i;
|
||||||
// lose mp
|
// lose mp
|
||||||
losemp(lf, cost);
|
losemp(lf, cost);
|
||||||
|
|
||||||
|
@ -1806,6 +1828,20 @@ int castspell(lifeform_t *lf, enum OBTYPE sid, lifeform_t *targlf, object_t *tar
|
||||||
power += countplantsinsight(lf);
|
power += countplantsinsight(lf);
|
||||||
limit(&power, NA, 10);
|
limit(&power, NA, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
tempboost = 0;
|
||||||
|
getflags(lf->flags, retflag, &nretflags, F_TEMPMAGICBOOST, F_NONE);
|
||||||
|
for (i = 0; i < nretflags; i++) {
|
||||||
|
tempboost += retflag[i]->val[0];
|
||||||
|
killflag(retflag[i]);
|
||||||
|
}
|
||||||
|
if (tempboost) {
|
||||||
|
power += tempboost;
|
||||||
|
if (isplayer(lf)) {
|
||||||
|
msg("^gYour spell's power is boosted!^n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (!willflag && real_getmr(lf, B_ONLYEXTERNAL) && skillcheck(lf, SC_RESISTMAG, 20 + power, 0) && !isgod(lf)) {
|
if (!willflag && real_getmr(lf, B_ONLYEXTERNAL) && skillcheck(lf, SC_RESISTMAG, 20 + power, 0) && !isgod(lf)) {
|
||||||
if (power > 1) {
|
if (power > 1) {
|
||||||
// half strength
|
// half strength
|
||||||
|
@ -2581,18 +2617,11 @@ int continuerepairing(lifeform_t *lf, flag_t *repairflag) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int countinnateattacks(lifeform_t *lf) {
|
int countinnateattacks(lifeform_t *lf) {
|
||||||
int count = 0,i;
|
|
||||||
flag_t *f;
|
|
||||||
flag_t *retflag[MAXCANDIDATES];
|
flag_t *retflag[MAXCANDIDATES];
|
||||||
int nretflags;
|
int nretflags;
|
||||||
getflags(lf->flags, retflag, &nretflags, F_HASATTACK, F_NONE);
|
getflags(lf->flags, retflag, &nretflags, F_HASATTACK, F_NONE);
|
||||||
for (i = 0; i < nretflags; i++) {
|
return nretflags;
|
||||||
f = retflag[i];
|
|
||||||
if (f->id == F_HASATTACK) count++;
|
|
||||||
}
|
}
|
||||||
return count;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int countlegs(lifeform_t *lf) {
|
int countlegs(lifeform_t *lf) {
|
||||||
enum BODYPART bp;
|
enum BODYPART bp;
|
||||||
|
@ -3257,8 +3286,18 @@ void die(lifeform_t *lf) {
|
||||||
amt = pctof( rnd(1,soulflag->val[0]), lf->maxhp);
|
amt = pctof( rnd(1,soulflag->val[0]), lf->maxhp);
|
||||||
limit(&amt, 1, NA);
|
limit(&amt, 1, NA);
|
||||||
gainhp(souleater, amt);
|
gainhp(souleater, amt);
|
||||||
|
// copy some flags
|
||||||
|
copyflag(souleater->flags, lf->flags, F_BLOODBOIL);
|
||||||
// drop bones
|
// drop bones
|
||||||
addob(corpsecell->obpile, "pile of ash");
|
addob(corpsecell->obpile, "pile of ash");
|
||||||
|
} else if (lfhasflag(lf, F_BLOODBOIL)) {
|
||||||
|
if (haslos(player, corpsecell)) {
|
||||||
|
char lfname[BUFLEN];
|
||||||
|
getlfname(lf, lfname);
|
||||||
|
msg("%s explodes into flames!", lfname);
|
||||||
|
}
|
||||||
|
// explode into flames
|
||||||
|
addobsinradius(corpsecell, 1, DT_COMPASS, "medium fire", B_TRUE, NULL);
|
||||||
} else if ((lf->lastdamtype == DT_BASH) && lfhasflag(lf, F_FROZEN)) {
|
} else if ((lf->lastdamtype == DT_BASH) && lfhasflag(lf, F_FROZEN)) {
|
||||||
// shattered
|
// shattered
|
||||||
fragments(corpsecell, "chunk of ice", 2, UNLIMITED);
|
fragments(corpsecell, "chunk of ice", 2, UNLIMITED);
|
||||||
|
@ -4237,16 +4276,20 @@ int eat(lifeform_t *lf, object_t *o) {
|
||||||
// get total nutrition
|
// get total nutrition
|
||||||
nutrition = getnutrition(o);
|
nutrition = getnutrition(o);
|
||||||
|
|
||||||
|
|
||||||
if (nutrition == 0) {
|
if (nutrition == 0) {
|
||||||
// this might happen if you purposely try to eat a potion.
|
// this might happen if you purposely try to eat something non-edible but drinkable
|
||||||
// technically a potion will pass above checks because you can
|
// (eg. a potion). also when you have f_caneatmaterial and you something which
|
||||||
// drink it.
|
// isn't normally edible (ie. a goat eating wood).
|
||||||
|
if (lfhasflagval(lf, F_CANEATMATERIAL, o->material->id, NA, NA, NULL)) {
|
||||||
|
// nutrition based on object weight
|
||||||
|
nutrition = getobweight(o)*5;
|
||||||
|
} else {
|
||||||
if (isplayer(lf)) {
|
if (isplayer(lf)) {
|
||||||
msg("That doesn't seem very nutritious...");
|
msg("That doesn't seem very nutritious...");
|
||||||
}
|
}
|
||||||
return B_TRUE;
|
return B_TRUE;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// only do this check for the player - basically it should
|
// only do this check for the player - basically it should
|
||||||
|
@ -4342,7 +4385,7 @@ int eat(lifeform_t *lf, object_t *o) {
|
||||||
sprintf(taste, "The raw meat tastes disgusting!");
|
sprintf(taste, "The raw meat tastes disgusting!");
|
||||||
} else if (hasflagval(o->flags, F_CORPSEOF, R_CHICKEN, NA, NA, NULL)) {
|
} else if (hasflagval(o->flags, F_CORPSEOF, R_CHICKEN, NA, NA, NULL)) {
|
||||||
sprintf(taste, "Tastes like chicken!");
|
sprintf(taste, "Tastes like chicken!");
|
||||||
} else if (f->val[1] >= 20) {
|
} else if (f && (f->val[1] >= 20)) {
|
||||||
sprintf(taste, "Yum!");
|
sprintf(taste, "Yum!");
|
||||||
} else {
|
} else {
|
||||||
strcpy(taste, "");
|
strcpy(taste, "");
|
||||||
|
@ -7183,6 +7226,8 @@ int getbodyparthitchance(enum BODYPART bp) {
|
||||||
case BP_SECWEAPON: return 0;
|
case BP_SECWEAPON: return 0;
|
||||||
case BP_EYES: return 1;
|
case BP_EYES: return 1;
|
||||||
case BP_HEAD: return 2;
|
case BP_HEAD: return 2;
|
||||||
|
case BP_HEAD2: return 2;
|
||||||
|
case BP_HEAD3: return 2;
|
||||||
case BP_WAIST: return 3;
|
case BP_WAIST: return 3;
|
||||||
case BP_HANDS: return 3;
|
case BP_HANDS: return 3;
|
||||||
case BP_FEET: return 3;
|
case BP_FEET: return 3;
|
||||||
|
@ -7234,6 +7279,10 @@ char *getbodypartname(lifeform_t *lf, enum BODYPART bp) {
|
||||||
return "eyes";
|
return "eyes";
|
||||||
case BP_HEAD:
|
case BP_HEAD:
|
||||||
return "head";
|
return "head";
|
||||||
|
case BP_HEAD2:
|
||||||
|
return "second head";
|
||||||
|
case BP_HEAD3:
|
||||||
|
return "third head";
|
||||||
case BP_NECK:
|
case BP_NECK:
|
||||||
return "neck";
|
return "neck";
|
||||||
case BP_BODY:
|
case BP_BODY:
|
||||||
|
@ -7268,6 +7317,8 @@ char *getbodypartequipname(enum BODYPART bp) {
|
||||||
case BP_LEFTFINGER:
|
case BP_LEFTFINGER:
|
||||||
case BP_HANDS:
|
case BP_HANDS:
|
||||||
case BP_HEAD:
|
case BP_HEAD:
|
||||||
|
case BP_HEAD2:
|
||||||
|
case BP_HEAD3:
|
||||||
case BP_BODY:
|
case BP_BODY:
|
||||||
case BP_FRONTLEGS:
|
case BP_FRONTLEGS:
|
||||||
case BP_BACKLEGS:
|
case BP_BACKLEGS:
|
||||||
|
@ -8302,6 +8353,7 @@ int getattacks(lifeform_t *lf, int *min, int *max) {
|
||||||
if (f) {
|
if (f) {
|
||||||
minattacks = f->val[0];
|
minattacks = f->val[0];
|
||||||
maxattacks = f->val[1];
|
maxattacks = f->val[1];
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
minattacks = countinnateattacks(lf);
|
minattacks = countinnateattacks(lf);
|
||||||
maxattacks = countinnateattacks(lf);
|
maxattacks = countinnateattacks(lf);
|
||||||
|
@ -8786,6 +8838,15 @@ char *real_getlfname(lifeform_t *lf, char *buf, lifeform_t *usevis, int showall,
|
||||||
strcat(descstring, " ");
|
strcat(descstring, " ");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (lf->race->id == R_HYDRA) {
|
||||||
|
int nheads;
|
||||||
|
char numbuf[BUFLEN];
|
||||||
|
nheads = countflagsofid(lf->flags, F_HASATTACK);
|
||||||
|
numtotext(nheads, numbuf);
|
||||||
|
strcat(descstring, numbuf);
|
||||||
|
strcat(descstring, "-headed ");
|
||||||
|
}
|
||||||
|
|
||||||
// need a certain amount of race knowledge to recognise ai traits
|
// need a certain amount of race knowledge to recognise ai traits
|
||||||
if (lorelev < PR_SKILLED) {
|
if (lorelev < PR_SKILLED) {
|
||||||
dobehaviour = B_FALSE;
|
dobehaviour = B_FALSE;
|
||||||
|
@ -11436,6 +11497,40 @@ int gotosleep(lifeform_t *lf, int onpurpose) {
|
||||||
return B_FALSE;
|
return B_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void growhydrahead(lifeform_t *lf, int announce) {
|
||||||
|
flag_t *f;
|
||||||
|
char vname[BUFLEN];
|
||||||
|
int dr = 0;
|
||||||
|
f = lfhasflagval(lf, F_HASATTACK, OT_TEETH, NA, NA, NULL);
|
||||||
|
dr = f->val[1]; // remember dr
|
||||||
|
if (announce) {
|
||||||
|
// remove one hasattack flag so that the name string
|
||||||
|
// is correct.
|
||||||
|
killflag(f);
|
||||||
|
getlfname(lf, vname);
|
||||||
|
// regrow
|
||||||
|
if (cansee(player, lf)) {
|
||||||
|
msg("^%c%s grow%s two more heads!", getlfcol(lf, CC_GOOD), vname, isplayer(lf) ? "" : "s");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (announce) {
|
||||||
|
// add two more attack flags, since we removed one before.
|
||||||
|
addtempflag(lf->flags, F_HASATTACK, OT_TEETH, dr, NA, NULL, FROMRACE);
|
||||||
|
addtempflag(lf->flags, F_HASATTACK, OT_TEETH, dr, NA, NULL, FROMRACE);
|
||||||
|
} else {
|
||||||
|
// just add one
|
||||||
|
addtempflag(lf->flags, F_HASATTACK, OT_TEETH, dr, NA, NULL, FROMRACE);
|
||||||
|
}
|
||||||
|
// also add extra hp
|
||||||
|
lf->maxhp += HITDIESIDES;
|
||||||
|
gainhp(lf, HITDIESIDES);
|
||||||
|
if (isplayer(lf)) statdirty = B_TRUE;
|
||||||
|
// adjust TR
|
||||||
|
f = hasflag(lf->flags, F_TR);
|
||||||
|
f->val[0]++;
|
||||||
|
}
|
||||||
|
|
||||||
flag_t *hasbleedinginjury(lifeform_t *lf, enum BODYPART bp) {
|
flag_t *hasbleedinginjury(lifeform_t *lf, enum BODYPART bp) {
|
||||||
flag_t *f, *retflag[MAXCANDIDATES];
|
flag_t *f, *retflag[MAXCANDIDATES];
|
||||||
int nretflags,i;
|
int nretflags,i;
|
||||||
|
@ -11960,6 +12055,16 @@ int injure(lifeform_t *lf, enum BODYPART where, enum DAMTYPE damtype, enum INJUR
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (where == BP_TAIL) {
|
||||||
|
if (lf->race->id == R_MANTICORE) {
|
||||||
|
flag_t *f;
|
||||||
|
// can't use spike volley
|
||||||
|
f = hasflagval(lf->flags, F_CANWILL, OT_S_SPIKEVOLLEY, NA, NA, NULL);
|
||||||
|
if (f) killflag(f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
return B_FALSE;
|
return B_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
1
lf.h
1
lf.h
|
@ -286,6 +286,7 @@ void givestartobs(lifeform_t *lf, object_t *targob, flagpile_t *fp);
|
||||||
void givestartskills(lifeform_t *lf, flagpile_t *fp);
|
void givestartskills(lifeform_t *lf, flagpile_t *fp);
|
||||||
map_t *gotolev(lifeform_t *lf, int depth, object_t *fromstairs);
|
map_t *gotolev(lifeform_t *lf, int depth, object_t *fromstairs);
|
||||||
int gotosleep(lifeform_t *lf, int onpurpose);
|
int gotosleep(lifeform_t *lf, int onpurpose);
|
||||||
|
void growhydrahead(lifeform_t *lf, int announce);
|
||||||
flag_t *hasbleedinginjury(lifeform_t *lf, enum BODYPART bp);
|
flag_t *hasbleedinginjury(lifeform_t *lf, enum BODYPART bp);
|
||||||
int hasfreeaction(lifeform_t *lf);
|
int hasfreeaction(lifeform_t *lf);
|
||||||
int real_hasfreeaction(lifeform_t *lf, enum FLAG exception);
|
int real_hasfreeaction(lifeform_t *lf, enum FLAG exception);
|
||||||
|
|
10
map.c
10
map.c
|
@ -6148,6 +6148,16 @@ void finalisemonster(lifeform_t *lf, lifeform_t *leader, flagpile_t *wantflags,
|
||||||
copyflags(lf->flags, v->flags, F_STAYINROOM);
|
copyflags(lf->flags, v->flags, F_STAYINROOM);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (lf->race->id == R_HYDRA) {
|
||||||
|
int nextra,i;
|
||||||
|
// they always have at least 5 heads. add more...
|
||||||
|
// grow extra heads
|
||||||
|
nextra = rnd(0,7);
|
||||||
|
for (i = 0; i < nextra; i++) {
|
||||||
|
growhydrahead(lf, B_FALSE);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
getflags(lf->flags, retflag, &nretflags, F_LIFEOB, F_NONE);
|
getflags(lf->flags, retflag, &nretflags, F_LIFEOB, F_NONE);
|
||||||
for (i = 0; i < nretflags; i++) {
|
for (i = 0; i < nretflags; i++) {
|
||||||
|
|
23
nexus.c
23
nexus.c
|
@ -131,6 +131,8 @@ int main(int argc, char **argv) {
|
||||||
enum SKILLLEVEL slev;
|
enum SKILLLEVEL slev;
|
||||||
flag_t *retflag[MAXCANDIDATES];
|
flag_t *retflag[MAXCANDIDATES];
|
||||||
int nretflags;
|
int nretflags;
|
||||||
|
map_t fakemap;
|
||||||
|
cell_t fakecell;
|
||||||
|
|
||||||
atexit(cleanup);
|
atexit(cleanup);
|
||||||
|
|
||||||
|
@ -256,6 +258,15 @@ int main(int argc, char **argv) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// add player in fake cell
|
||||||
|
createfakes(&fakemap, &fakecell);
|
||||||
|
real_addlf(&fakecell, startrace->id, 1, C_PLAYER); // this will assign 'player'
|
||||||
|
// give them basic abilities
|
||||||
|
addflag(player->flags, F_CANWILL, OT_A_CHECKSTAIRS, NA, NA, NULL);
|
||||||
|
addflag(player->flags, F_CANWILL, OT_A_PRAY, NA, NA, NULL);
|
||||||
|
addflag(player->flags, F_CANWILL, OT_A_TRAIN, NA, NA, NULL);
|
||||||
|
addflag(player->flags, F_CANWILL, OT_A_DEBUG, NA, NA, NULL); /////////
|
||||||
|
|
||||||
// make the initial level
|
// make the initial level
|
||||||
newworld = B_TRUE;
|
newworld = B_TRUE;
|
||||||
|
|
||||||
|
@ -288,6 +299,7 @@ int main(int argc, char **argv) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// add player in the starting position
|
// add player in the starting position
|
||||||
|
|
||||||
//where = real_getrandomadjcell(where, WE_WALKABLE, B_ALLOWEXPAND, LOF_DONTNEED, NULL);
|
//where = real_getrandomadjcell(where, WE_WALKABLE, B_ALLOWEXPAND, LOF_DONTNEED, NULL);
|
||||||
where = findobinmap(dmap, OT_PLAYERSTART);
|
where = findobinmap(dmap, OT_PLAYERSTART);
|
||||||
if (!where) {
|
if (!where) {
|
||||||
|
@ -296,19 +308,16 @@ int main(int argc, char **argv) {
|
||||||
more();
|
more();
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
movelf(player, where);
|
||||||
|
// new remove fakes
|
||||||
|
killfakes(&fakemap, &fakecell);
|
||||||
|
|
||||||
|
|
||||||
// this is the hole which you fell down to get here.
|
// this is the hole which you fell down to get here.
|
||||||
addobfast(where->obpile, OT_HOLEINROOF);
|
addobfast(where->obpile, OT_HOLEINROOF);
|
||||||
// kill any objects which were already there, or which fell down the hole
|
// kill any objects which were already there, or which fell down the hole
|
||||||
killallobsexcept(where->obpile, OT_HOLEINROOF, OT_NONE);
|
killallobsexcept(where->obpile, OT_HOLEINROOF, OT_NONE);
|
||||||
|
|
||||||
// now add the player
|
|
||||||
real_addlf(where, startrace->id, 1, C_PLAYER); // this will assign 'player'
|
|
||||||
// give them basic abilities
|
|
||||||
addflag(player->flags, F_CANWILL, OT_A_CHECKSTAIRS, NA, NA, NULL);
|
|
||||||
addflag(player->flags, F_CANWILL, OT_A_PRAY, NA, NA, NULL);
|
|
||||||
addflag(player->flags, F_CANWILL, OT_A_TRAIN, NA, NA, NULL);
|
|
||||||
addflag(player->flags, F_CANWILL, OT_A_DEBUG, NA, NA, NULL); /////////
|
|
||||||
/*o = hasob(where->obpile, OT_PLAYERSTART);
|
/*o = hasob(where->obpile, OT_PLAYERSTART);
|
||||||
killob(o);*/
|
killob(o);*/
|
||||||
|
|
||||||
|
|
|
@ -14736,6 +14736,13 @@ int getcritchance(lifeform_t *lf, object_t *o, lifeform_t *victim) {
|
||||||
chance *= 2;
|
chance *= 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// extra crit chance if you can sever victim's limbs
|
||||||
|
if (victim && lfhasflag(victim, F_CANSEVER)) {
|
||||||
|
if (o && (getdamtype(o) == DT_SLASH)) {
|
||||||
|
chance += 30;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return chance;
|
return chance;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
57
spell.c
57
spell.c
|
@ -4280,6 +4280,15 @@ int dospelleffects(lifeform_t *caster, enum OBTYPE spellid, int power, lifeform_
|
||||||
|
|
||||||
teleportto(caster, targcell, B_TRUE);
|
teleportto(caster, targcell, B_TRUE);
|
||||||
setfacing(caster, target->facing);
|
setfacing(caster, target->facing);
|
||||||
|
} else if (spellid == OT_S_BLOODBOIL) {
|
||||||
|
if (!target) {
|
||||||
|
target = targcell->lf;
|
||||||
|
}
|
||||||
|
if (!target || lfhasflag(target, F_BLOODBOIL)) {
|
||||||
|
fizzle(caster);
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
|
addflag(target->flags, F_BLOODBOIL, B_TRUE, NA, NA, NULL);
|
||||||
} else if (spellid == OT_S_LOWERMETAB) {
|
} else if (spellid == OT_S_LOWERMETAB) {
|
||||||
flag_t *f;
|
flag_t *f;
|
||||||
// ie. 2 - 4
|
// ie. 2 - 4
|
||||||
|
@ -6919,6 +6928,54 @@ int dospelleffects(lifeform_t *caster, enum OBTYPE spellid, int power, lifeform_
|
||||||
}
|
}
|
||||||
polymorphto(target, R_GASCLOUD, howlong);
|
polymorphto(target, R_GASCLOUD, howlong);
|
||||||
}
|
}
|
||||||
|
} else if (spellid == OT_S_GATHERFLAME) {
|
||||||
|
cell_t *c;
|
||||||
|
int amt = 0,i;
|
||||||
|
if (!target) target = caster;
|
||||||
|
// override castername
|
||||||
|
getlfname(target, castername);
|
||||||
|
// all flame in sight
|
||||||
|
for (i = 0; i < target->nlos; i++) {
|
||||||
|
c = target->los[i];
|
||||||
|
if (c->lf && (c->lf->material->id == MT_FIRE)) {
|
||||||
|
if (gettr(c->lf) <= power) {
|
||||||
|
char buf[BUFLEN];
|
||||||
|
// instadeath
|
||||||
|
sprintf(buf, "being sucked into %s", castername);
|
||||||
|
losehp(c->lf, c->lf->maxhp, DT_DIRECT, target, buf);
|
||||||
|
if (isplayer(c->lf)) {
|
||||||
|
msg("Your essence is sucked into %s!", castername);
|
||||||
|
} else if (cansee(player, c->lf)) {
|
||||||
|
char lfname[BUFLEN];
|
||||||
|
getlfname(c->lf, lfname);
|
||||||
|
msg("%s%s essence is sucked into %s!", lfname, getpossessive(lfname), castername);
|
||||||
|
}
|
||||||
|
amt++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (isdead(target)) { // consumed yourself?
|
||||||
|
return B_FALSE;
|
||||||
|
}
|
||||||
|
// now gather flame from cells in los
|
||||||
|
for (i = 0; (i < target->nlos) && (amt < power); i++) {
|
||||||
|
object_t *o, *nexto;
|
||||||
|
for (o = target->los[i]->obpile->first ; o ; o = nexto) {
|
||||||
|
nexto = o->next;
|
||||||
|
if (o->material->id == MT_FIRE) {
|
||||||
|
removeob(o, ALL);
|
||||||
|
amt++;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (amt) {
|
||||||
|
// boost spells...
|
||||||
|
addflag(target->flags, F_TEMPMAGICBOOST, amt, NA, NA, NULL);
|
||||||
|
} else {
|
||||||
|
fizzle(caster);
|
||||||
|
return B_TRUE;
|
||||||
|
}
|
||||||
} else if (spellid == OT_S_GLACIATE) {
|
} else if (spellid == OT_S_GLACIATE) {
|
||||||
object_t *o,*nexto;
|
object_t *o,*nexto;
|
||||||
int donesomething = B_FALSE;
|
int donesomething = B_FALSE;
|
||||||
|
|
35
text.c
35
text.c
|
@ -1142,6 +1142,11 @@ char *getkillverb(lifeform_t *victim, object_t *wep, enum DAMTYPE damtype, int d
|
||||||
canbehead = B_FALSE;
|
canbehead = B_FALSE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// can't behead multiheaded things at the moment...
|
||||||
|
if (victim && hasbp(victim, BP_HEAD) && hasbp(victim, BP_HEAD2)) {
|
||||||
|
canbehead = B_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
if (canbehead) {
|
if (canbehead) {
|
||||||
if (victim && (victim->race->id == R_EARTHWYRM)) {
|
if (victim && (victim->race->id == R_EARTHWYRM)) {
|
||||||
return "bisect";
|
return "bisect";
|
||||||
|
@ -2006,6 +2011,36 @@ char *numtotext(int num, char *buf) {
|
||||||
case 10:
|
case 10:
|
||||||
snprintf(buf, BUFLEN, "ten");
|
snprintf(buf, BUFLEN, "ten");
|
||||||
break;
|
break;
|
||||||
|
case 11:
|
||||||
|
snprintf(buf, BUFLEN, "eleven");
|
||||||
|
break;
|
||||||
|
case 12:
|
||||||
|
snprintf(buf, BUFLEN, "twelve");
|
||||||
|
break;
|
||||||
|
case 13:
|
||||||
|
snprintf(buf, BUFLEN, "thirteen");
|
||||||
|
break;
|
||||||
|
case 14:
|
||||||
|
snprintf(buf, BUFLEN, "fourteen");
|
||||||
|
break;
|
||||||
|
case 15:
|
||||||
|
snprintf(buf, BUFLEN, "fifteen");
|
||||||
|
break;
|
||||||
|
case 16:
|
||||||
|
snprintf(buf, BUFLEN, "sixteen");
|
||||||
|
break;
|
||||||
|
case 17:
|
||||||
|
snprintf(buf, BUFLEN, "seventeen");
|
||||||
|
break;
|
||||||
|
case 18:
|
||||||
|
snprintf(buf, BUFLEN, "eighteen");
|
||||||
|
break;
|
||||||
|
case 19:
|
||||||
|
snprintf(buf, BUFLEN, "nineteen");
|
||||||
|
break;
|
||||||
|
case 20:
|
||||||
|
snprintf(buf, BUFLEN, "twenty");
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
snprintf(buf, BUFLEN, "%d",num);
|
snprintf(buf, BUFLEN, "%d",num);
|
||||||
break;
|
break;
|
||||||
|
|
Loading…
Reference in New Issue