/// <summary> /// Creates the allowed targets. /// </summary> /// <returns>The allowed targets.</returns> /// <param name="origin">Origin.</param> /// <param name="entityManager">Entity manager.</param>` /// <param name="skill">Skill.</param> public static SelectableTargetManager CreateAllowedTargets(BattleEntity origin, BattleEntityManagerComponent entityManager, ICombatSkill skill) { HashSet<BattleEntity> entitySet = new HashSet<BattleEntity>(entityManager.allEntities); List<SelectableTarget> targetList = new List<SelectableTarget>(); Dictionary<BattleEntity, SelectableTarget> targetMap = new Dictionary<BattleEntity, SelectableTarget>(); // filter FilterSkill(entitySet, skill); // populate targets if(origin.isPC) { PopulateSelectableTargets(targetList, (PCBattleEntity) origin, entitySet, skill); } else { PopulateSelectableTargets(targetList, (EnemyBattleEntity) origin, entitySet, skill); } // create map foreach(SelectableTarget target in targetList) { foreach(BattleEntity entity in target.entities) { targetMap[entity] = target; } } return new SelectableTargetManager(skill, targetList, targetMap); }
public IBattleAction ResolveAction(BattleEntityManagerComponent entityManager, EnemyBattleEntity enemyEntity) { // for each skill, lets evaulate if we will use it float totalWeight = 0; List<AISkillResultSet> possibleSkills = new List<AISkillResultSet>(); foreach(AISkillComposite composite in mSkillComposites) { SelectableTargetManager selectManager = SelectableTargetManager.CreateAllowedTargets(enemyEntity, entityManager, composite.skill); HashSet<BattleEntity> targetSet = new HashSet<BattleEntity>(); foreach(SelectableTarget target in selectManager.targetList) { foreach(BattleEntity entity in target.entities) { targetSet.Add(entity); } } // filter targets composite.targetFilter.FilterEntities(enemyEntity, targetSet); // filter condition composite.conditionFilter.FilterEntities(enemyEntity, targetSet); // if we still have targets, save, otherwise move on if(targetSet.Count == 0) { continue; } // lets save this and move on totalWeight += composite.weight; AISkillResultSet result = new AISkillResultSet(); result.possibleTargets = targetSet; result.composite = composite; result.selectManager = selectManager; possibleSkills.Add(result); } if(possibleSkills.Count == 0) { throw new Exception("We should make sure we set this a default skill, like attack"); } // first, if we have no items or 1 item, just use that instead of randoming to our skill if(possibleSkills.Count == 1) { AISkillResultSet result = possibleSkills[0]; return GenerateBattleAction(enemyEntity, result, entityManager); } // now lets random the weight and see where it lies float calculatedValue = UnityEngine.Random.Range(0, totalWeight); // lets use that skill, we will iterate there adding weights to see if we lie within our weight foreach(AISkillResultSet result in possibleSkills) { if(calculatedValue <= result.composite.weight) { return GenerateBattleAction(enemyEntity, result, entityManager); } // decrement the value, its the same as using a cursor calculatedValue -= result.composite.weight; } throw new Exception("Failed to find an appropriate skill, random failed"); }
/// <summary> /// Creates the target resolver. This should handle turning a selected target into a resolved target /// </summary> /// <returns>The target resolver.</returns> /// <param name="target">Target.</param> /// <param name="manager">Manager.</param> public static ITargetResolver CreateTargetResolver(SelectableTarget target, BattleEntityManagerComponent manager) { switch(target.resolvedTargetType) { case ResolvedTargetEnum.SINGLE: return new TargetResolverSingle(target.entities[0]); case ResolvedTargetEnum.SELF_ROW: PCBattleEntity entity = (PCBattleEntity) target.entities[0]; return new TargetResolverRow(entity.pcCharacter.rowPosition, manager); case ResolvedTargetEnum.SELF: return new TargetResolverSingle(target.entities[0]); case ResolvedTargetEnum.ENEMY_ALL: return new TargetResolverAll(true, manager); case ResolvedTargetEnum.ALLY_ROW_MIDDLE: return new TargetResolverRow(PCCharacter.RowPosition.MIDDLE, manager); case ResolvedTargetEnum.ALLY_ROW_FRONT: return new TargetResolverRow(PCCharacter.RowPosition.FRONT, manager); case ResolvedTargetEnum.ALLY_ROW_BACK: return new TargetResolverRow(PCCharacter.RowPosition.BACK, manager); case ResolvedTargetEnum.ALLY_ALL: return new TargetResolverAll(false, manager); } return null; // TODO turn into target classes }
// UNITY LIFE CYCLE void Awake() { mBattleEventQueue = new Queue<IBattleEvent>(); mActionRequiredQueue = new Queue<BattleEntity>(); mGameState = GameState.INTRO; mCombatExecutor = new CombatOperationExecutor(); mEntityManager = GetComponent<BattleEntityManagerComponent>(); // first create our battle system for other components to initialize BattleSystem.OnServiceStart(this); }
/// <summary> /// For single targets /// </summary> /// <param name="targetEnum">Target enum.</param> /// <param name="entityManager">Entity manager.</param> public TargetResolverRow(PCCharacter.RowPosition rowPosition, BattleEntityManagerComponent manager) { mRowPosition = rowPosition; mBattleEntityManager = manager; }
void Awake() { mTurnQueue = new Queue<PCBattleEntity>(); this.mEntityManager = GetComponent<BattleEntityManagerComponent> (); this.currentSelectedSkill = null; this.decisionState = DecisionState.IDLE; }
/// <summary> /// For single targets /// </summary> /// <param name="targetEnum">Target enum.</param> /// <param name="entityManager">Entity manager.</param> public TargetResolverAll(bool isEnemy, BattleEntityManagerComponent manager) { mIsEnemy = isEnemy; mBattleEntityManager = manager; }
void Awake() { mEntityManager = GameObject.FindGameObjectWithTag(Tags.BATTLE_CONTROLLER).GetComponent<BattleEntityManagerComponent>(); mTransform = GetComponent<RectTransform>(); EnsureLayout (); }
private IBattleAction GenerateBattleAction(EnemyBattleEntity enemyEntity, AISkillResultSet result, BattleEntityManagerComponent entityManager) { List<BattleEntity> possibleList = new List<BattleEntity>(result.possibleTargets); AISkillComposite composite = result.composite; // choose random target int index = 0; // default to first index we know exists if(possibleList.Count > 1) { index = Mathf.FloorToInt(UnityEngine.Random.Range(0, possibleList.Count)); } // get the selected / random index BattleEntity targetEntity = possibleList[index]; // create a list so we can create the proper TargetResolver // TODO this can be optimized to remove this step, its a lot of work SelectableTarget selectableTarget = result.selectManager.GetSelectableTarget(targetEntity); if(selectableTarget == null) { Debug.Log("F**k.. target was not found in AI ActivateSkill"); } // get the target resolver ITargetResolver targetResolver = TargetResolverFactory.CreateTargetResolver(selectableTarget, entityManager); return BattleActionFactory.CreateBattleAction (composite.skill, enemyEntity, targetResolver); }