//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()); }