Exemplo n.º 1
0
        public override void OnComplete()
        {
            //BattleAction action = new BattleAction(target.actorId, 0x765D, (uint) HitEffect.Hit, 0, (byte) HitDirection.None);
            errorResult = null;

            // todo: implement auto attack damage bonus in Character.OnAttack

            /*
             * ≪Auto-attack Damage Bonus≫
             * Class        Bonus 1       Bonus 2
             * Pugilist     Intelligence  Strength
             * Gladiator    Mind          Strength
             * Marauder     Vitality      Strength
             * Archer       Dexterity     Piety
             * Lancer       Piety         Strength
             * Conjurer     Mind          Piety
             * Thaumaturge  Mind          Piety
             * The above damage bonus also applies to “Shot” attacks by archers.
             */
            // handle paralyze/intimidate/sleep/whatever in Character.OnAttack


            // todo: Change this to use a BattleCommand like the other states

            //List<BattleAction> actions = new List<BattleAction>();
            CommandResultContainer actions = new CommandResultContainer();

            var i = 0;

            for (int hitNum = 0; hitNum < 1 /* owner.GetMod((uint) Modifier.HitCount)*/; hitNum++)
            {
                CommandResult action = new CommandResult(target.actorId, 0x765D, (uint)HitEffect.Hit, 100, (byte)HitDirection.None, (byte)hitNum);
                action.commandType    = CommandType.AutoAttack;
                action.actionType     = ActionType.Physical;
                action.actionProperty = (ActionProperty)owner.GetMod(Modifier.AttackType);
                // evasion, miss, dodge, etc to be handled in script, calling helpers from scripts/weaponskills.lua
                // temporary evade/miss/etc function to test hit effects
                action.DoAction(owner, target, null, actions);
            }

            // todo: this is f****n stupid, probably only need *one* error packet, not an error for each action
            CommandResult[] errors = (CommandResult[])actions.GetList().ToArray().Clone();
            CommandResult   error  = null;// new BattleAction(0, null, 0, 0);
            //owner.DoActions(null, actions.GetList(), ref error);
            //owner.OnAttack(this, actions[0], ref errorResult);
            var anim = (uint)(17 << 24 | 1 << 12);

            owner.DoBattleAction(22104, anim, actions.GetList());
        }
Exemplo n.º 2
0
        //The order of messages that appears after using a command is:

        //1. Cast start messages. (ie "You begin casting... ")
        //2. Messages from buffs that activate before the command actually starts, like Power Surge or Presence of Mind. (This may be wrong and these could be the same as 4.)
        //3. If the command is a multi-hit command, this is where the "You use [command] on [target]" message goes

        //Then, for each hit:
        //4. Buffs that activate before a command hits, like Blindside
        //5. The hit itself. For single hit commands this message is "Your [command] hits [target] for x damage" for multi hits it's "[Target] takes x points of damage"
        //6. Stoneskin falling off
        //6. Buffs that activate after a command hits, like Aegis Boon and Divine Veil

        //After all hits
        //7. If it's a multi-hit command there's a "{numhits]fold attack..." message or if all hits miss an "All attacks missed" message
        //8. Buffs that fall off after the skill ends, like Excruciate

        //For every target defeated:
        //8. Defeat message
        //9. EXP message
        //10. EXP chain message


        //folder is probably temporary until move to cached scripts is complete
        public void DoBattleCommand(BattleCommand command, string folder)
        {
            //List<BattleAction> actions = new List<BattleAction>();
            CommandResultContainer actions = new CommandResultContainer();

            var  targets   = command.targetFind.GetTargets();
            bool hitTarget = false;

            if (targets.Count > 0)
            {
                statusEffects.CallLuaFunctionByFlag((uint)StatusEffectFlags.ActivateOnCommandStart, "onCommandStart", this, command, actions);

                foreach (var chara in targets)
                {
                    ushort hitCount    = 0;
                    ushort totalDamage = 0;
                    for (int hitNum = 1; hitNum <= command.numHits; hitNum++)
                    {
                        var action = new CommandResult(chara.actorId, command, (byte)GetHitDirection(chara), (byte)hitNum);

                        //uncached script
                        lua.LuaEngine.CallLuaBattleCommandFunction(this, command, folder, "onSkillFinish", this, chara, command, action, actions);
                        //cached script
                        //skill.CallLuaFunction(owner, "onSkillFinish", this, chara, command, action, actions);
                        if (action.hitType > HitType.Evade && action.hitType != HitType.Resist)
                        {
                            hitTarget = true;
                            hitCount++;
                            totalDamage += action.amount;
                        }
                    }

                    if (command.numHits > 1)
                    {
                        //30442: [hitCount]fold Attack! [chara] takes a total of totalDamage points of damage.
                        //30450: All attacks miss!
                        ushort textId = (ushort)(hitTarget ? 30442 : 30450);
                        actions.AddAction(new CommandResult(chara.actorId, textId, 0, totalDamage, (byte)hitCount));
                    }
                }

                statusEffects.CallLuaFunctionByFlag((uint)StatusEffectFlags.ActivateOnCommandFinish, "onCommandFinish", this, command, actions);
            }
            else
            {
                actions.AddAction(new CommandResult(actorId, 30202, 0));
            }

            //Now that we know if we hit the target we can check if the combo continues
            if (this is Player)
            {
                if (command.isCombo && hitTarget)
                {
                    ((Player)this).SetCombos(command.comboNextCommandId);
                }
                else
                {
                    ((Player)this).SetCombos();
                }
            }

            CommandResult error = new CommandResult(actorId, 0, 0);

            DelMP(command.CalculateMpCost(this));
            DelTP(command.CalculateTpCost(this));
            actions.CombineLists();
            DoBattleAction(command.id, command.battleAnimation, actions.GetList());
        }