Esempio n. 1
0
 public Monster_Spell_Effect_Flag(int index, Monster_Spell_Flag method, GF gf, bool timed, Timed_Effect flag,
                                  random_value Base, random_value dam, int chance, bool save, Object_Flag res_flag, random_value power)
 {
     this.index    = index;
     this.method   = method;
     this.gf       = gf;
     this.timed    = timed;
     this.flag     = flag;
     this.Base     = Base;
     this.dam      = dam;
     this.chance   = chance;
     this.save     = save;
     this.res_flag = res_flag;
     this.power    = power;
 }
        public bool timed; /* true if timed, false if permanent */

        #endregion Fields

        #region Constructors

        public Monster_Spell_Effect_Flag(int index, Monster_Spell_Flag method, GF gf, bool timed, Timed_Effect flag,
            random_value Base, random_value dam, int chance, bool save, Object_Flag res_flag, random_value power)
        {
            this.index = index;
            this.method = method;
            this.gf = gf;
            this.timed = timed;
            this.flag = flag;
            this.Base = Base;
            this.dam = dam;
            this.chance = chance;
            this.save = save;
            this.res_flag = res_flag;
            this.power = power;
        }
Esempio n. 3
0
        static long max_dam(Monster_Race r_ptr)
        {
            int rlev, i;
            int melee_dam = 0, atk_dam = 0, spell_dam = 0;
            int dam = 1;

            /* Extract the monster level, force 1 for town monsters */
            rlev = ((r_ptr.level >= 1) ? r_ptr.level : 1);

            /* Assume single resist for the elemental attacks */
            spell_dam = Monster_Spell_Flag.best_spell_power(r_ptr, 1);

            /* Hack - Apply over 10 rounds */
            spell_dam *= 10;

            /* Scale for frequency and availability of mana / ammo */
            if (spell_dam != 0)
            {
                int freq = r_ptr.freq_spell;

                /* Hack -- always get 1 shot */
                if (freq < 10)
                {
                    freq = 10;
                }

                /* Adjust for frequency */
                spell_dam = spell_dam * freq / 100;
            }

            /* Check attacks */
            for (i = 0; i < 4; i++)
            {
                if (r_ptr.blow[i] == null)
                {
                    continue;
                }
                /* Extract the attack infomation */
                Monster_Blow.RBE effect = r_ptr.blow[i].effect;
                Monster_Blow.RBM method = r_ptr.blow[i].method;
                int d_dice = r_ptr.blow[i].d_dice;
                int d_side = r_ptr.blow[i].d_side;

                /* Hack -- no more attacks */
                if (method == null)
                {
                    continue;
                }

                /* Assume maximum damage*/
                atk_dam = (int)blow_effect(effect, d_dice * d_side, r_ptr.level);

                /*stun definitely most dangerous*/
                if (method == Monster_Blow.RBM.PUNCH || method == Monster_Blow.RBM.KICK ||
                    method == Monster_Blow.RBM.BUTT || method == Monster_Blow.RBM.CRUSH)
                {
                    atk_dam *= 4;
                    atk_dam /= 3;
                }
                else if (method == Monster_Blow.RBM.CLAW || method == Monster_Blow.RBM.BITE)
                {
                    atk_dam *= 7;
                    atk_dam /= 5;
                }


                /* Normal melee attack */
                if (!r_ptr.flags.has(Monster_Flag.NEVER_BLOW.value))
                {
                    /* Keep a running total */
                    melee_dam += atk_dam;
                }
            }

            /*
             * Apply damage over 10 rounds. We assume that the monster has to make contact first.
             * Hack - speed has more impact on melee as has to stay in contact with player.
             * Hack - this is except for pass wall and kill wall monsters which can always get to the player.
             * Hack - use different values for huge monsters as they strike out to range 2.
             */
            if (r_ptr.flags.test(Monster_Flag.SIZE, Monster_Flag.KILL_WALL.value, Monster_Flag.PASS_WALL.value))
            {
                melee_dam *= 10;
            }
            else
            {
                melee_dam = melee_dam * 3 + melee_dam * Misc.extract_energy[r_ptr.speed + (r_ptr.spell_flags.has(Monster_Spell_Flag.HASTE.value) ? 5 : 0)] / 7;
            }

            /*
             * Scale based on attack accuracy. We make a massive number of assumptions here and just use monster level.
             */
            melee_dam = melee_dam * Math.Min(45 + rlev * 3, 95) / 100;

            /* Hack -- Monsters that multiply ignore the following reductions */
            if (!r_ptr.flags.has(Monster_Flag.MULTIPLY.value))
            {
                /*Reduce damamge potential for monsters that move randomly */
                if (r_ptr.flags.test(Monster_Flag.SIZE, Monster_Flag.RAND_25.value, Monster_Flag.RAND_50.value))
                {
                    int reduce = 100;

                    if (r_ptr.flags.has(Monster_Flag.RAND_25.value))
                    {
                        reduce -= 25;
                    }
                    if (r_ptr.flags.has(Monster_Flag.RAND_50.value))
                    {
                        reduce -= 50;
                    }

                    /*even moving randomly one in 8 times will hit the player*/
                    reduce += (100 - reduce) / 8;

                    /* adjust the melee damage*/
                    melee_dam = (melee_dam * reduce) / 100;
                }

                /*monsters who can't move aren't nearly as much of a combat threat*/
                if (r_ptr.flags.has(Monster_Flag.NEVER_MOVE.value))
                {
                    if (r_ptr.spell_flags.has(Monster_Spell_Flag.TELE_TO.value) ||
                        r_ptr.spell_flags.has(Monster_Spell_Flag.BLINK.value))
                    {
                        /* Scale for frequency */
                        melee_dam = melee_dam / 5 + 4 * melee_dam * r_ptr.freq_spell / 500;

                        /* Incorporate spell failure chance */
                        if (!r_ptr.flags.has(Monster_Flag.STUPID.value))
                        {
                            melee_dam = melee_dam / 5 + 4 * melee_dam * Math.Min(75 + (rlev + 3) / 4, 100) / 500;
                        }
                    }
                    else if (r_ptr.flags.has(Monster_Flag.INVISIBLE.value))
                    {
                        melee_dam /= 3;
                    }
                    else
                    {
                        melee_dam /= 5;
                    }
                }
            }

            /* But keep at a minimum */
            if (melee_dam < 1)
            {
                melee_dam = 1;
            }

            /*
             * Combine spell and melee damage
             */
            dam = (spell_dam + melee_dam);

            r_ptr.highest_threat = (short)dam;
            r_ptr.spell_dam      = spell_dam;           /*AMF:DEBUG*/
            r_ptr.melee_dam      = melee_dam;           /*AMF:DEBUG*/

            /*
             * Adjust for speed.  Monster at speed 120 will do double damage,
             * monster at speed 100 will do half, etc.  Bonus for monsters who can haste self.
             */
            dam = (dam * Misc.extract_energy[r_ptr.speed + (r_ptr.spell_flags.has(Monster_Spell_Flag.HASTE.value) ? 5 : 0)]) / 10;

            /*
             * Adjust threat for speed -- multipliers are more threatening.
             */
            if (r_ptr.flags.has(Monster_Flag.MULTIPLY.value))
            {
                r_ptr.highest_threat = (short)((r_ptr.highest_threat * Misc.extract_energy[r_ptr.speed + (r_ptr.spell_flags.has(Monster_Spell_Flag.HASTE.value) ? 5 : 0)]) / 5);
            }

            /*
             * Adjust threat for friends.
             */
            if (r_ptr.flags.has(Monster_Flag.FRIENDS.value))
            {
                r_ptr.highest_threat *= 2;
            }
            else if (r_ptr.flags.has(Monster_Flag.FRIEND.value))
            {
                r_ptr.highest_threat = (short)(r_ptr.highest_threat * 3 / 2);
            }

            /*but deep in a minimum*/
            if (dam < 1)
            {
                dam = 1;
            }

            /* We're done */
            return(dam);
        }