Ejemplo n.º 1
0
bool
psionic_mob_fight(struct creature *ch, struct creature *precious_vict)
{
    struct creature *vict = NULL;

    if (!is_fighting(ch))
        return false;

    // pick an enemy
    if (!(vict = choose_opponent(ch, precious_vict)))
        return false;

    int aggression = calculate_mob_aggression(ch, vict);

    // Psions can't really do anything when there's a psishield in place
    if (AFF3_FLAGGED(vict, AFF3_PSISHIELD)
        && can_cast_spell(ch, SPELL_PSIONIC_SHATTER)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_PSIONIC_SHATTER);
        return true;
    }
    // Prioritize healing with aggression
    if (GET_HIT(ch) < (GET_MAX_HIT(ch) * MIN(20, MAX(80, aggression)) / 100)
        && can_cast_spell(ch, SPELL_WOUND_CLOSURE)) {
        cast_spell(ch, ch, NULL, NULL, SPELL_WOUND_CLOSURE);
        return true;
    }

    if (aggression > 75) {
        // extremely aggressive - just attack hard
        if (can_cast_spell(ch, SKILL_PSIBLAST)) {
            perform_offensive_skill(ch, vict, SKILL_PSIBLAST);
            return true;
        } else if (GET_POSITION(vict) > POS_SITTING
            && can_cast_spell(ch, SPELL_EGO_WHIP)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_EGO_WHIP);
            return true;
        }
    }
    if (aggression > 50) {
        // somewhat aggressive - balance attacking with crippling
        if (GET_MANA(ch) < GET_MAX_MANA(ch) / 2
            && can_cast_spell(ch, SKILL_PSIDRAIN)
            && can_psidrain(ch, vict, NULL, false)) {
            perform_psidrain(ch, vict);
            return true;
        } else if (!affected_by_spell(vict, SPELL_PSYCHIC_CRUSH)
            && can_cast_spell(ch, SPELL_PSYCHIC_CRUSH)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_PSYCHIC_CRUSH);
            return true;
        } else if (!affected_by_spell(vict, SPELL_MOTOR_SPASM)
            && can_cast_spell(ch, SPELL_MOTOR_SPASM)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_MOTOR_SPASM);
            return true;
        } else if (!affected_by_spell(ch, SPELL_ADRENALINE)
            && can_cast_spell(ch, SPELL_ADRENALINE)) {
            cast_spell(ch, ch, NULL, NULL, SPELL_ADRENALINE);
            return true;
        } else if (GET_POSITION(vict) > POS_SITTING
            && can_cast_spell(ch, SPELL_EGO_WHIP)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_EGO_WHIP);
            return true;
        } else if (can_cast_spell(ch, SKILL_PSIBLAST)) {
            perform_offensive_skill(ch, vict, SKILL_PSIBLAST);
            return true;
        }
    }
    if (aggression > 25) {
        // not very aggressive - play more defensively
        if (IS_PSIONIC(vict)
            && !affected_by_spell(ch, SPELL_PSYCHIC_RESISTANCE)
            && can_cast_spell(ch, SPELL_PSYCHIC_RESISTANCE)) {
            cast_spell(ch, ch, NULL, NULL, SPELL_PSYCHIC_RESISTANCE);
            return true;
        } else if (!IS_CONFUSED(vict)
            && can_cast_spell(ch, SPELL_CONFUSION)
            && (IS_MAGE(vict) || IS_PSIONIC(vict) || IS_CLERIC(vict) ||
                IS_KNIGHT(vict) || IS_PHYSIC(vict))) {
            cast_spell(ch, vict, NULL, NULL, SPELL_CONFUSION);
            return true;
        } else if (GET_MOVE(ch) < GET_MAX_MOVE(ch) / 4
            && can_cast_spell(ch, SPELL_ENDURANCE)) {
            cast_spell(ch, ch, NULL, NULL, SPELL_ENDURANCE);
            return true;
        } else if (GET_MOVE(ch) < GET_MAX_MOVE(ch) / 4
            && can_cast_spell(ch, SPELL_DERMAL_HARDENING)) {
            cast_spell(ch, ch, NULL, NULL, SPELL_DERMAL_HARDENING);
            return true;
        } else if (!AFF2_FLAGGED(ch, AFF2_VERTIGO)
            && can_cast_spell(ch, SPELL_VERTIGO)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_VERTIGO);
            return true;
        } else if (!affected_by_spell(vict, SPELL_PSYCHIC_FEEDBACK)
            && can_cast_spell(ch, SPELL_PSYCHIC_FEEDBACK)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_PSYCHIC_FEEDBACK);
            return true;
        } else if (!affected_by_spell(vict, SPELL_WEAKNESS)
            && can_cast_spell(ch, SPELL_WEAKNESS)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_WEAKNESS);
            return true;
        } else if (!affected_by_spell(vict, SPELL_CLUMSINESS)
            && can_cast_spell(ch, SPELL_CLUMSINESS)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_CLUMSINESS);
            return true;
        } else if (can_cast_spell(ch, SKILL_PSIBLAST)) {
            perform_offensive_skill(ch, vict, SKILL_PSIBLAST);
            return true;
        }
    }
    if (aggression > 5) {
        // attempt to neutralize or get away
        if (GET_POSITION(vict) > POS_SLEEPING
            && can_cast_spell(ch, SPELL_MELATONIC_FLOOD)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_MELATONIC_FLOOD);
            return true;
        } else if (can_cast_spell(ch, SPELL_ASTRAL_SPELL)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_ASTRAL_SPELL);
            return true;
        } else if (can_cast_spell(ch, SPELL_AMNESIA)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_AMNESIA);
            return true;
        } else if (can_cast_spell(ch, SPELL_FEAR)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_FEAR);
            return true;
        }
    }

    return false;
}
Ejemplo n.º 2
0
bool
can_psidrain(struct creature *ch, struct creature *vict, int *out_dist, bool msg)
{
    const char *to_char = NULL;
    const char *to_vict = NULL;
    int dist;

    if (CHECK_SKILL(ch, SKILL_PSIDRAIN) < 30 || !IS_PSIONIC(ch)) {
        to_char = "You have no idea how.";
        goto failure;
    }

    if (ROOM_FLAGGED(ch->in_room, ROOM_NOPSIONICS) && GET_LEVEL(ch) < LVL_GOD) {
        to_char = "Psychic powers are useless here!";
        goto failure;
    }

    if (GET_LEVEL(vict) >= LVL_AMBASSADOR && GET_LEVEL(ch) < GET_LEVEL(vict)) {
        to_char = "You cannot locate them.";
        to_vict = "$n has just tried to psidrain you.";
        goto failure;
    }

    if (vict == ch) {
        to_char = "Ha ha... Funny!";
        goto failure;
    }

    if (is_fighting(ch) && vict->in_room != ch->in_room) {
        to_char = "You cannot focus outside the room during battle!";
        goto failure;
    }

    if (ch->in_room != vict->in_room &&
        ch->in_room->zone != vict->in_room->zone) {
        to_char = "$N is not in your zone.";
        goto failure;
    }

    if (ROOM_FLAGGED(vict->in_room, ROOM_NOPSIONICS)
        && GET_LEVEL(ch) < LVL_GOD) {
        to_char = "Psychic powers are useless where $E is!";
        goto failure;
    }

    if (!ok_to_attack(ch, vict, msg))
        return false;

    if (GET_MOVE(ch) < 20) {
        to_char = "You are too physically exhausted.";
        goto failure;
    }

    dist = find_distance(ch->in_room, vict->in_room);
    if (out_dist)
        *out_dist = dist;
    if (dist > ((GET_LEVEL(ch) / 6))) {
        to_char = "$N is out of your psychic range.";
        goto failure;
    }

    if (NULL_PSI(vict)) {
        to_char = "It is pointless to attempt this on $M.";
        goto failure;
    }

    return true;

failure:
    if (msg) {
        if (to_char)
            act(to_char, false, ch, NULL, vict, TO_CHAR);
        if (to_vict)
            act(to_vict, false, ch, NULL, vict, TO_VICT);
    }
    return false;
}
Ejemplo n.º 3
0
/* say_spell erodes buf, buf1, buf2 */
void
say_spell (struct char_data *ch, int spellnum, struct char_data *tch,
		   struct obj_data *tobj)
{
	char lbuf[256];
	const char *format;

	struct char_data *i;
	int j, ofs = 0;

	*buf = '\0';
	strcpy (lbuf, skill_name (spellnum));

	while (lbuf[ofs])
	{
		for (j = 0; *(syls[j].org); j++)
		{
			if (!strncmp (syls[j].org, lbuf + ofs, strlen (syls[j].org)))
			{
				strcat (buf, syls[j].news);
				ofs += strlen (syls[j].org);
				break;
			}
		}
		/* i.e., we didn't find a match in syls[] */
		if (!*syls[j].org)
		{
			log ("No entry in syllable table for substring of '%s'", lbuf);
			ofs++;
		}
	}

	if (tch != NULL && IN_ROOM (tch) == IN_ROOM (ch))
	{
		if (tch == ch)
		{
			if (IS_PSIONIC (ch) && (GET_LEVEL (ch) != LVL_IMPL))
			{
				format =
					"$n congiunge le mani sulla testa e chiude i suoi occhi.";
			}
			else
			{
				format =
					"$n chiude i suoi occhi e lancia sul suo tricorder il processo, '%s'.";
			}
		}
		else
		{
			if (IS_PSIONIC (ch) && (GET_LEVEL (ch) != LVL_IMPL))
			{
				format =
					"$n posa una mano sulla testa e punta l'altra su $N e chiude gli occhi.";
			}
			else
			{
				format =
					"$n punta il suo tricorder a $N e lancia  il processo, '%s'.";
			}
		}
	}
	else if (tobj != NULL &&
			 ((IN_ROOM (tobj) == IN_ROOM (ch)) || (tobj->carried_by == ch)))
	{
		if (IS_PSIONIC (ch) && (GET_LEVEL (ch) != LVL_IMPL))
		{
			format = "$n congiunge le mani su $p e chiude i suoi occhi.";
		}
		else
		{
			format =
				"$n punta il suo tricorder a $p e lancia il processo, '%s'.";
		}
	}
	else
	{
		if (IS_PSIONIC (ch) && (GET_LEVEL (ch) != LVL_IMPL))
		{
			format =
				"$n congiunge le mani sulla testa e chiude i suoi occhi.";
		}
		else
		{
			format = "$n lancia sul suo tricorder il processo, '%s'.";
		}
	}

	sprintf (buf1, format, skill_name (spellnum));
	sprintf (buf2, format, buf);

	for (i = world[IN_ROOM (ch)].people; i; i = i->next_in_room)
	{
		if (i == ch || i == tch || !i->desc || !AWAKE (i))
			continue;
		if (GET_CLASS (ch) == GET_CLASS (i))
			perform_act (buf1, ch, tobj, tch, i);
		else
			perform_act (buf2, ch, tobj, tch, i);
	}

	if (tch != NULL && tch != ch && IN_ROOM (tch) == IN_ROOM (ch))
	{
		if (IS_PSIONIC (ch) && (GET_LEVEL (ch) != LVL_IMPL))
		{
			sprintf (buf1,
					 "$n posa una mano sulla testa e punta l'altra su di te.");
		}
		else
		{
			sprintf (buf1,
					 "$n ti punta il suo tricorder e lancia il processo, '%s'.",
					 GET_CLASS (ch) ==
					 GET_CLASS (tch) ? skill_name (spellnum) : buf);
		}
		act (buf1, FALSE, ch, NULL, tch, TO_VICT);
	}
}
Ejemplo n.º 4
0
void
psionic_best_attack(struct creature *ch, struct creature *vict)
{
    int aggression = calculate_mob_aggression(ch, vict);

    // Psions can't really do anything when there's a psishield in place
    if (AFF3_FLAGGED(vict, AFF3_PSISHIELD)
        && can_cast_spell(ch, SPELL_PSIONIC_SHATTER)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_PSIONIC_SHATTER);
        return;
    }
    if (aggression > 75) {
        // extremely aggressive - just attack hard
        if (!affected_by_spell(vict, SPELL_PSYCHIC_SURGE)
            && can_cast_spell(ch, SPELL_PSYCHIC_SURGE)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_PSYCHIC_SURGE);
            return;
        } else if (can_cast_spell(ch, SKILL_PSIBLAST)) {
            perform_offensive_skill(ch, vict, SKILL_PSIBLAST);
            return;
        } else if (GET_POSITION(vict) > POS_SITTING
            && can_cast_spell(ch, SPELL_EGO_WHIP)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_EGO_WHIP);
            return;
        }
    }
    if (aggression > 50) {
        // somewhat aggressive - balance attacking with crippling
        if (!affected_by_spell(vict, SPELL_PSYCHIC_CRUSH)
            && can_cast_spell(ch, SPELL_PSYCHIC_CRUSH)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_PSYCHIC_CRUSH);
            return;
        } else if (!affected_by_spell(vict, SPELL_MOTOR_SPASM)
            && can_cast_spell(ch, SPELL_MOTOR_SPASM)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_MOTOR_SPASM);
            return;
        } else if (GET_POSITION(vict) > POS_SITTING
            && can_cast_spell(ch, SPELL_EGO_WHIP)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_EGO_WHIP);
            return;
        } else if (can_cast_spell(ch, SKILL_PSIBLAST)) {
            perform_offensive_skill(ch, vict, SKILL_PSIBLAST);
            return;
        }
    }
    if (aggression > 25) {
        // not very aggressive - play more defensively
        if (!IS_CONFUSED(vict)
            && can_cast_spell(ch, SPELL_CONFUSION)
            && (IS_MAGE(vict) || IS_PSIONIC(vict) || IS_CLERIC(vict) ||
                IS_KNIGHT(vict) || IS_PHYSIC(vict))) {
            cast_spell(ch, vict, NULL, NULL, SPELL_CONFUSION);
            return;
        } else if (!AFF2_FLAGGED(ch, AFF2_VERTIGO)
            && can_cast_spell(ch, SPELL_VERTIGO)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_VERTIGO);
            return;
        } else if (!affected_by_spell(vict, SPELL_PSYCHIC_FEEDBACK)
            && can_cast_spell(ch, SPELL_PSYCHIC_FEEDBACK)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_PSYCHIC_FEEDBACK);
            return;
        } else if (nullpsi_is_advisable(vict)
            && can_cast_spell(ch, SPELL_NULLPSI)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_NULLPSI);
            return;
        } else if (can_cast_spell(ch, SKILL_PSIBLAST)) {
            perform_offensive_skill(ch, vict, SKILL_PSIBLAST);
            return;
        }
    }
    if (aggression > 5) {
        // attempt to neutralize or get away
        if (GET_POSITION(vict) > POS_SLEEPING
            && can_cast_spell(ch, SPELL_MELATONIC_FLOOD)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_MELATONIC_FLOOD);
            return;
        } else if (can_cast_spell(ch, SPELL_ASTRAL_SPELL)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_ASTRAL_SPELL);
            return;
        } else if (can_cast_spell(ch, SPELL_AMNESIA)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_AMNESIA);
            return;
        } else if (can_cast_spell(ch, SPELL_FEAR)) {
            cast_spell(ch, vict, NULL, NULL, SPELL_FEAR);
            return;
        }
    }
    // desperation - just attack full force, as hard as possible
    if (!affected_by_spell(vict, SPELL_PSYCHIC_SURGE)
        && can_cast_spell(ch, SPELL_PSYCHIC_SURGE)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_PSYCHIC_SURGE);
        return;
    } else if (!affected_by_spell(vict, SPELL_PSYCHIC_CRUSH)
        && can_cast_spell(ch, SPELL_PSYCHIC_CRUSH)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_PSYCHIC_CRUSH);
        return;
    } else if (!affected_by_spell(vict, SPELL_MOTOR_SPASM)
        && can_cast_spell(ch, SPELL_MOTOR_SPASM)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_MOTOR_SPASM);
        return;
    } else if (can_cast_spell(ch, SKILL_PSIBLAST)) {
        perform_offensive_skill(ch, vict, SKILL_PSIBLAST);
        return;
    } else if (GET_POSITION(vict) > POS_SITTING
        && can_cast_spell(ch, SPELL_EGO_WHIP)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_EGO_WHIP);
        return;
    } else if (GET_POSITION(vict) > POS_SLEEPING
        && can_cast_spell(ch, SPELL_MELATONIC_FLOOD)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_MELATONIC_FLOOD);
        return;
    } else if (can_cast_spell(ch, SPELL_ASTRAL_SPELL)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_ASTRAL_SPELL);
        return;
    } else if (can_cast_spell(ch, SPELL_AMNESIA)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_AMNESIA);
        return;
    } else if (can_cast_spell(ch, SPELL_FEAR)) {
        cast_spell(ch, vict, NULL, NULL, SPELL_FEAR);
        return;
    } else {
        hit(ch, vict, TYPE_UNDEFINED);
    }
}
Ejemplo n.º 5
0
int
invalid_char_class(struct creature *ch, struct obj_data *obj)
{
    // Protected object
    if (IS_PC(ch) &&
        obj->shared->owner_id != 0 && obj->shared->owner_id != GET_IDNUM(ch)) {
        return true;
    }
    // Unapproved object
    if (!OBJ_APPROVED(obj) && !is_tester(ch) && GET_LEVEL(ch) < LVL_IMMORT)
        return true;

    // Anti class restrictions
    if ((IS_OBJ_STAT(obj, ITEM_ANTI_MAGIC_USER) && IS_MAGIC_USER(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_CLERIC) && IS_CLERIC(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_WARRIOR) && IS_WARRIOR(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_THIEF) && IS_THIEF(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_BARB) && IS_BARB(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_PSYCHIC) && IS_PSYCHIC(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_PHYSIC) && IS_PHYSIC(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_CYBORG) && IS_CYBORG(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_KNIGHT) && IS_KNIGHT(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_RANGER) && IS_RANGER(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_BARD) && IS_BARD(ch)) ||
        (IS_OBJ_STAT(obj, ITEM_ANTI_MONK) && IS_MONK(ch)) ||
        (IS_OBJ_STAT2(obj, ITEM2_ANTI_MERC) && IS_MERC(ch)))
        return true;

    // Required class restrictions - any one of them must be met
    if ((IS_OBJ_STAT3(obj, ITEM3_REQ_MAGE) && IS_MAGE(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_CLERIC) && IS_CLERIC(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_THIEF) && IS_THIEF(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_WARRIOR) && IS_WARRIOR(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_BARB) && IS_BARB(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_PSIONIC) && IS_PSIONIC(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_PHYSIC) && IS_PHYSIC(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_CYBORG) && IS_CYBORG(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_KNIGHT) && IS_KNIGHT(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_RANGER) && IS_RANGER(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_BARD) && IS_BARD(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_MONK) && IS_MONK(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_VAMPIRE) && IS_VAMPIRE(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_MERCENARY) && IS_MERC(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_SPARE1) && IS_SPARE1(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_SPARE2) && IS_SPARE2(ch))
        || (IS_OBJ_STAT3(obj, ITEM3_REQ_SPARE3) && IS_SPARE3(ch)))
        return false;

    // A required class existed and the creature didn't fulfill any
    if (IS_OBJ_STAT3(obj, ITEM3_REQ_MAGE
            | ITEM3_REQ_CLERIC
            | ITEM3_REQ_THIEF
            | ITEM3_REQ_WARRIOR
            | ITEM3_REQ_BARB
            | ITEM3_REQ_PSIONIC
            | ITEM3_REQ_PHYSIC
            | ITEM3_REQ_CYBORG
            | ITEM3_REQ_KNIGHT
            | ITEM3_REQ_RANGER
            | ITEM3_REQ_BARD
            | ITEM3_REQ_MONK
            | ITEM3_REQ_VAMPIRE
            | ITEM3_REQ_MERCENARY
            | ITEM3_REQ_SPARE1 | ITEM3_REQ_SPARE2 | ITEM3_REQ_SPARE3))
        return true;

    // Passes all tests
    return false;
}