void hit(struct char_data *ch, struct char_data *victim, int type) { struct obj_data *wielded = GET_EQ(ch, WEAR_WIELD); int w_type, victim_ac, calc_thaco, dam, diceroll; /* Do some sanity checking, in case someone flees, etc. */ if (IN_ROOM(ch) != IN_ROOM(victim)) { if (FIGHTING(ch) && FIGHTING(ch) == victim) stop_fighting(ch); return; } /* Find the weapon type (for display purposes only) */ if (wielded && GET_OBJ_TYPE(wielded) == ITEM_WEAPON) w_type = GET_OBJ_VAL(wielded, 3) + TYPE_HIT; else { if (IS_NPC(ch) && ch->mob_specials.attack_type != 0) w_type = ch->mob_specials.attack_type + TYPE_HIT; else w_type = TYPE_HIT; } /* Calculate chance of hit. Lower THAC0 is better for attacker. */ calc_thaco = compute_thaco(ch, victim); /* Calculate the raw armor including magic armor. Lower AC is better for defender. */ victim_ac = compute_armor_class(victim) / 10; /* roll the die and take your chances... */ diceroll = rand_number(1, 20); /* * Decide whether this is a hit or a miss. * * Victim asleep = hit, otherwise: * 1 = Automatic miss. * 2..19 = Checked vs. AC. * 20 = Automatic hit. */ if (diceroll == 20 || !AWAKE(victim)) dam = TRUE; else if (diceroll == 1) dam = FALSE; else dam = (calc_thaco - diceroll <= victim_ac); if (!dam) /* the attacker missed the victim */ damage(ch, victim, 0, type == SKILL_BACKSTAB ? SKILL_BACKSTAB : w_type); else { /* okay, we know the guy has been hit. now calculate damage. */ /* Start with the damage bonuses: the damroll and strength apply */ dam = str_app[STRENGTH_APPLY_INDEX(ch)].todam; dam += GET_DAMROLL(ch); /* Maybe holding arrow? */ if (wielded && GET_OBJ_TYPE(wielded) == ITEM_WEAPON) { /* Add weapon-based damage if a weapon is being wielded */ dam += dice(GET_OBJ_VAL(wielded, 1), GET_OBJ_VAL(wielded, 2)); } else { /* If no weapon, add bare hand damage instead */ if (IS_NPC(ch)) dam += dice(ch->mob_specials.damnodice, ch->mob_specials.damsizedice); else dam += rand_number(0, 2); /* Max 2 bare hand damage for players */ } /* * Include a damage multiplier if victim isn't ready to fight: * * Position sitting 1.33 x normal * Position resting 1.66 x normal * Position sleeping 2.00 x normal * Position stunned 2.33 x normal * Position incap 2.66 x normal * Position mortally 3.00 x normal * * Note, this is a hack because it depends on the particular * values of the POSITION_XXX constants. */ if (GET_POS(victim) < POS_FIGHTING) dam *= 1 + (POS_FIGHTING - GET_POS(victim)) / 3; /* at least 1 hp damage min per hit */ dam = MAX(1, dam); if (type == SKILL_BACKSTAB) damage(ch, victim, dam * backstab_mult(GET_LEVEL(ch)), SKILL_BACKSTAB); else damage(ch, victim, dam, w_type); } }
void hit(struct char_data * ch, struct char_data * victim, int type) { struct obj_data *wielded = GET_EQ(ch, WEAR_WIELD); int w_type, victim_ac, calc_thaco, dam, diceroll; /* check if the character has a fight trigger */ fight_mtrigger(ch); /* Do some sanity checking, in case someone flees, etc. */ if (!char_within_range_of_vict(ch, victim) || \ (IN_ROOM(ch) != IN_ROOM(victim))) { if (FIGHTING(ch) && (FIGHTING(ch) == victim)) stop_fighting(ch); return; } /* Find the weapon type (for display purposes only) */ if (wielded && GET_OBJ_TYPE(wielded) == ITEM_WEAPON) w_type = GET_OBJ_VAL(wielded, 3) + TYPE_HIT; else { if (IS_NPC(ch) && (ch->mob_specials.attack_type != 0)) w_type = ch->mob_specials.attack_type + TYPE_HIT; else w_type = TYPE_HIT; } /* Calculate the THAC0 of the attacker */ if (!IS_NPC(ch)) calc_thaco = thaco((int) GET_CLASS(ch), (int) GET_LEVEL(ch)); else /* THAC0 for monsters is set in the HitRoll */ calc_thaco = 20; calc_thaco -= str_app[STRENGTH_APPLY_INDEX(ch)].tohit; calc_thaco -= GET_HITROLL(ch); calc_thaco -= (int) ((GET_INT(ch) - 13) / 1.5); /* Intelligence helps! */ calc_thaco -= (int) ((GET_WIS(ch) - 13) / 1.5); /* So does wisdom */ /* Calculate the raw armor including magic armor. Lower AC is better. */ victim_ac = compute_armor_class(victim) / 10; /* roll the die and take your chances... */ diceroll = number(1, 20); /* decide whether this is a hit or a miss */ if ((((diceroll < 20) && AWAKE(victim)) && ((diceroll == 1) || ((calc_thaco - diceroll) > victim_ac)))) { /* the attacker missed the victim */ if (type == SKILL_BACKSTAB) damage(ch, victim, 0, SKILL_BACKSTAB); else damage(ch, victim, 0, w_type); } else { /* okay, we know the guy has been hit. now calculate damage. */ /* Start with the damage bonuses: the damroll and strength apply */ dam = str_app[STRENGTH_APPLY_INDEX(ch)].todam; dam += GET_DAMROLL(ch); /* Maybe holding arrow? */ if (wielded && GET_OBJ_TYPE(wielded) == ITEM_WEAPON) { /* Add weapon-based damage if a weapon is being wielded */ dam += dice(GET_OBJ_VAL(wielded, 1), GET_OBJ_VAL(wielded, 2)); } else { /* If no weapon, add bare hand damage instead */ if (IS_NPC(ch)) { dam += dice(ch->mob_specials.damnodice, ch->mob_specials.damsizedice); } else { dam += number(0, 2); /* Max 2 bare hand damage for players */ } } /* * Include a damage multiplier if victim isn't ready to fight: * * Position sitting 1.33 x normal * Position resting 1.66 x normal * Position sleeping 2.00 x normal * Position stunned 2.33 x normal * Position incap 2.66 x normal * Position mortally 3.00 x normal * * Note, this is a hack because it depends on the particular * values of the POSITION_XXX constants. */ if (GET_POS(victim) < POS_FIGHTING) dam *= 1 + (POS_FIGHTING - GET_POS(victim)) / 3; /* at least 1 hp damage min per hit */ dam = MAX(1, dam); if (type == SKILL_BACKSTAB) { dam *= backstab_mult(GET_LEVEL(ch)); damage(ch, victim, dam, SKILL_BACKSTAB); } else damage(ch, victim, dam, w_type); } /* check if the victim has a hitprcnt trigger */ hitprcnt_mtrigger(victim); }