void Start() { //INIT playerCtrl = player.gameObject.GetComponent <CharacterController>(); //ACTIONS BTAction block = new BTAction(Block); BTAction meleeAttack = new BTAction(MeleeAttack); BTAction rangedAttack = new BTAction(RangedAttack); BTAction getCloser = new BTAction(GetCloser); //CONDITIONS BTCondition playerAttacking = new BTCondition(PlayerAttacking); BTCondition playerMelee = new BTCondition(PlayerMelee); BTCondition playerFar = new BTCondition(PlayerFar); //TREE BTSequence seqBlock = new BTSequence(new IBTTask[] { playerAttacking, block }); BTSequence seqMelee = new BTSequence(new IBTTask[] { playerMelee, meleeAttack }); BTSequence seqGetCloser = new BTSequence(new IBTTask[] { playerFar, getCloser }); BTDecorator untilFailGetCloser = new BTDecoratorUntilFail(seqGetCloser); BTRandomSelector rselRanged = new BTRandomSelector(new IBTTask[] { untilFailGetCloser, rangedAttack }); BTSelector selAttack = new BTSelector(new IBTTask[] { seqMelee, rselRanged }); root = new BTSelector(new IBTTask[] { seqBlock, selAttack }); }
private void Start() { SmokeEnemy = new BTSequence(showNode, new BTCheckAttack(underAttack, isAtPlayer, agent), new BTFlyToCover(agent, cover), new BTWait(3f), new BTThrowSmoke(prefabBom, child, underAttack, hasAttacked) ); RotateAroundPlayer = new BTSequence(showNode, new BTTCheckAtPlayer(isAtPlayer), new BTFlyArroundPlayer(isAtPlayer, agent, child, player) ); GoToPlayer = new BTSequence(showNode, new BTCheckAttackDone(hasAttacked, agent), new BTMoveAlly(hasAttacked, isAtPlayer, child, agent, player) ); rootNode = new BTSelector(new List <BTBaseNode> { SmokeEnemy, GoToPlayer, RotateAroundPlayer }); rootNode.Run(); }
// Setup references and default values void Start() { // Get ref to the parent team objects to fill out team lists Transform RedTeamT = GameObject.Find("RedTeam").GetComponent <Transform>(); Transform BlueTeamT = GameObject.Find("BlueTeam").GetComponent <Transform>(); // Add all units to each team foreach (Transform child in RedTeamT) { RedTeam.Add(child.gameObject.GetComponent <Unit>()); } foreach (Transform child in BlueTeamT) { BlueTeam.Add(child.gameObject.GetComponent <Unit>()); } // Setting references layerMask = LayerMask.GetMask("Units"); tilemap = GameObject.Find("GridTileMap").GetComponent <Tilemap>(); tilemapFloor = GameObject.Find("BackroundTileMap").GetComponent <Tilemap>(); //tile floor astar = new Astar(); // access to astar methods ActiveUnitText = GameObject.Find("ActiveUnitText").GetComponent <Text>(); ActiveTeamText = GameObject.Find("ActiveTeamText").GetComponent <Text>(); UnitStateText = GameObject.Find("UnitStateText").GetComponent <Text>(); EnergyText = GameObject.Find("EnergyText").GetComponent <Text>(); HPText = GameObject.Find("HPText").GetComponent <Text>(); // Set red as first turn RedTeamTurn = true; approachSequence = new BTSequence(new List <BTNode> { new MoveToEnemyTask(this), }); attackSequence = new BTSequence(new List <BTNode> { new CheckForEnemyTask(this), new CheckEnemyHPTask(this), new AttackTask(this), }); attackSafeSequence = new BTSequence(new List <BTNode> { new CheckForEnemyTask(this), new AttackSafeTask(this), }); coverSequence = new BTSequence(new List <BTNode> { new MoveToCoverTask(this), }); rootAI = new BTSelector(new List <BTNode> { approachSequence, attackSequence, attackSafeSequence, coverSequence, }); }
private void Start() { CheckSmoke = new BTSequence(showNode, new BTCheckSmoke(isInSmoke, agent) ); AttackTree = new BTSequence(showNode, new CheckPlayerRange(ClosestPlayer, hasWeapon, needsWeapon), new BTMove(agent, ClosestPlayer, showNode, weaponHolder, hasWeapon, cantAttack, lighting, WeaponCol) ); CheckWeapon = new BTSequence(showNode, new FindWeapon(needsWeapon), new BTGoForWeapon(agent, weapon, hasWeapon, needsWeapon, weaponHolder, weapon, lighting, CheckForWeaponCol) ); PatrollTree = new BTSequence(showNode, new BTPatrol(WayPoints, agent, lighting, PatrolCol) ); rootNode = new BTSelector(new List <BTBaseNode> { CheckSmoke, CheckWeapon, AttackTree, PatrollTree }); rootNode.Run(); }
public BTSelector Selector(params BTNode[] cs) { BTSelector node = new BTSelector(cs); node.bt = this; return(node); }
private void Start() { var a = true; // swich false var b = false; // switch true var root = new BTSelector("Root"); { var selectA = new BTSequencer("A"); { var isA = new BTCondition("Is A", () => a); selectA.AddState(isA); var console = new BTAction("Print A", () => Debug.Log("Is A")); selectA.AddState(console); } root.AddState(selectA); var selectB = new BTSequencer("B"); { var isB = new BTCondition("Is B", () => b); selectB.AddState(isB); var console = new BTAction("Print B", () => Debug.Log("Is B")); selectB.AddState(console); } root.AddState(selectB); } BehTree.AddState(root); }
public virtual void CreateBehaviourTree() { IsCoveredAvalibleBTNode isCoveredAvalibleBTNode = new IsCoveredAvalibleBTNode(avaliableCover, player, this); GoToCoverBTNode goToCoverBTNode = new GoToCoverBTNode(agent, this, controller); HealthBTNode healthBTNode = new HealthBTNode(controller); IsCoveredBTNode isCoveredBTNode = new IsCoveredBTNode(transform, player); ChaseBTNode chaseBTNode = new ChaseBTNode(player, agent, this); RangeBTNode chaseRange = new RangeBTNode(controller.ChaseRange, transform, player); ShootBTNode shootBTNode = new ShootBTNode(this, agent); RangeBTNode shootRangeBTNode = new RangeBTNode(controller.ShootRange, transform, player); ObstacleCheck obstacleCheck = new ObstacleCheck(transform, player); //IsShootAvailable isShootAvailable = new IsShootAvailable(transform, player); RangeBTNode meleeRange = new RangeBTNode(controller.MeleeRange, transform, player); MeleeBTNode meleeBTNode = new MeleeBTNode(this, agent); BTSequence chaseSequence = new BTSequence(new List<BTNode> { chaseRange, chaseBTNode }); BTSequence shootSequence = new BTSequence(new List<BTNode> { shootRangeBTNode, obstacleCheck, shootBTNode }); BTSequence meleeSequence = new BTSequence(new List<BTNode> { meleeRange, obstacleCheck, meleeBTNode }); BTSequence goToCoverSequence = new BTSequence(new List<BTNode> { isCoveredAvalibleBTNode, goToCoverBTNode }); BTSelector findCoverSelector = new BTSelector(new List<BTNode> { goToCoverSequence, chaseSequence }); BTSelector tryToFindSelctor = new BTSelector(new List<BTNode> { isCoveredBTNode, findCoverSelector }); BTSequence coverSequence = new BTSequence(new List<BTNode> { healthBTNode, tryToFindSelctor}); rootNode = new BTSelector(new List<BTNode> { coverSequence, meleeSequence, shootSequence, chaseSequence }); }
public override BTNode Init() { base.Init(); animator = GetComponent<Animator>(); BTSelector root = new BTSelector(); BTActionDeath death = new BTActionDeath(gameObject); root.AddChild(death); //领地限制的分支,只能在该范围活动 BTConditionEvaluator evaluatorTerritory = new BTConditionEvaluator(BTLogic.And, false, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorTerritory.AddConditional(new BTCheckWithinDistance(_database.transform, territoryDis, null, BTCheckWithinDistance.DataOpt.FixedPosition), true); BTSimpleParallel goHome = new BTSimpleParallel(); { goHome.SetPrimaryChild(new BTActionCharacterMove(_database.transform, speed, 0.1f, null,BTActionMove.DataOpt.FixedPosition,BTActionMove.UsageOpt.Position, BTDataReadOpt.ReadEveryTick)); goHome.AddChild(new BTActionPlayAnimation(animator, "Walk")); } evaluatorTerritory.child = goHome; root.AddChild(evaluatorTerritory); BTConditionEvaluator evaluatorTarget = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorTarget.AddConditional(new BTCheckExistence(_database.transform, defendDis, "Player", BTCheckExistence.CheckOpt.CheckSphere)); //加一层组合,来判断进行哪个动作 BTSelector actionSelector = new BTSelector(); evaluatorTarget.child = actionSelector; //评估是否有碰撞 BTConditionEvaluator evaluatorCollision = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); BTCheckCollision collision = new BTCheckCollision("Player", tolerance, BTCheckCollision.CheckOpt.RayCast); evaluatorCollision.AddConditional(collision); BTSequence attackSubtre = new BTSequence(); { attackSubtre.AddChild(new BTActionPlayAnimation(animator, "Attack")); } evaluatorCollision.child = attackSubtre; actionSelector.AddChild(evaluatorCollision); //没有碰撞则移动 BTSimpleParallel moveTo = new BTSimpleParallel(); { moveTo.SetPrimaryChild(new BTActionCharacterMove(_database.transform, speed, tolerance, target, BTDataReadOpt.ReadEveryTick)); moveTo.AddChild(new BTActionPlayAnimation(animator, "Walk")); } actionSelector.AddChild(moveTo); root.AddChild(evaluatorTarget); //Idle分支 BTActionPlayAnimation palyIdle = new BTActionPlayAnimation(animator, "Idle"); root.AddChild(palyIdle); return root; }
protected virtual BTSelector InAttackRangeSelector() { BTSelector selector = new BTSelector(new List <BTNode>() { new InAttackRangeCondition(this), new BTSequence(new List <BTNode>() { MoveSequence(), new ForceFailureTask() }), }); return(selector); }
protected virtual BTSelector HasWaypointSelector() { BTSelector selector = new BTSelector(new List <BTNode>() { new HasWaypointCondition(this), new BTSequence(new List <BTNode>() { new SelectRandomWanderPoint(this), MoveSequence(), }), new ForceFailureTask() }); return(selector); }
private void ConstructBehaviourTree() { // Nodes var wonderNode = new WonderNode(_navMeshAgent, gameObject); var coverAvailableNode = new IsCoverAvailableNode(availableCovers, player.transform, this); var goToCoverNode = new GoToCoverNode(this, _navMeshAgent); var healthNode = new HealthNode(GetComponent <EnemyController>(), GetComponent <EnemyController>().lowHealthThreshold); var isCoveredNode = new IsCoveredNode(player.transform, transform); var chaseNode = new ChaseNode(player.transform, _navMeshAgent); var wonderRangeNode = new NotInRangeNode(GetComponent <EnemyController>().chaseRange, player.transform, transform); var chasingRangeNode = new RangeNode(GetComponent <EnemyController>().chaseRange, player.transform, transform); var shootingRangeNode = new RangeNode(GetComponent <EnemyController>().shootRange, player.transform, transform); var shootNode = new ShootNode(_navMeshAgent, this); // Sequences var wonderSequence = new BTSequencer(new List <BTNode> { wonderRangeNode, wonderNode }); var chaseSequence = new BTSequencer(new List <BTNode> { chasingRangeNode, chaseNode }); var shootSequence = new BTSequencer(new List <BTNode> { shootingRangeNode, shootNode }); var goToCoverSequence = new BTSequencer(new List <BTNode> { coverAvailableNode, goToCoverNode }); var findCoverSelector = new BTSelector(new List <BTNode> { goToCoverSequence, chaseSequence }); var tryToTakeCoverSelector = new BTSelector(new List <BTNode> { isCoveredNode, findCoverSelector }); var mainCoverSequence = new BTSequencer(new List <BTNode> { healthNode, tryToTakeCoverSelector }); _rootNode = new BTSelector(new List <BTNode> { wonderSequence, mainCoverSequence, shootSequence, chaseSequence }); }
private void BuildBehaviourTree() { BTActionNode checkAIUnitsCountCriticalNode = new BTActionNode(CheckAIUnitsCountCritical); BTActionNode findWeakestPlayerUnitNode = new BTActionNode(FindWeakestPlayerUnit); BTActionNode findClosetPlayerUnitNode = new BTActionNode(FindClosestPlayerUnit); BTActionNode moveTowardsThePlayerUnitNode = new BTActionNode(MoveTowardsThePlayerUnit); BTActionNode attackPlayerUnitNode = new BTActionNode(AttackPlayerUnit); BTSequence MoveTowardsAndAttackSequence = new BTSequence(new List <BTNode>() { moveTowardsThePlayerUnitNode, attackPlayerUnitNode }); BTSequence WeakestPlayerAttackSequence = new BTSequence(new List <BTNode>() { findWeakestPlayerUnitNode, MoveTowardsAndAttackSequence }); BTSequence aiWeakSequence = new BTSequence(new List <BTNode>() // check if the AI count is less than or eaqual to player count, al { checkAIUnitsCountCriticalNode, WeakestPlayerAttackSequence, }); BTSequence aiStrongSequence = new BTSequence(new List <BTNode>() //moment I am checking againt unit, also can have centralized AI score, => health of all unts + unt count { findClosetPlayerUnitNode, MoveTowardsAndAttackSequence, }); BTSelector selectorRoot = new BTSelector(new List <BTNode>() { aiWeakSequence, aiStrongSequence }); _behvourTree = new BehaviourTree(selectorRoot); }
private void InitializeEnemyPhaseBehaviourTree() { // Returns fail when there are enemies. Success if no enemies found. BTAction BTAct_NoEnemyCheck = new BTAction( () => { // If there are not even one enemy. Nothing to do here. if (EnemyList.Count < 1) { return(BTStatus.Success); } return(BTStatus.Failure); } ); BTAction BTAct_EnemyPhaseStartAnimations = new BTAction( () => { if (EPdoneStartAnimation == false) { EventAnimationController.Instance.ExecutePhaseAnimation(GamePhase.EnemyPhase); EPdoneStartAnimation = true; return(BTStatus.Running); } else if (EventAnimationController.Instance.IsAnimating == false) { EPdoneStartAnimation = false; ControlAreaManager.Instance.SetControlBlockerEnabled(true); return(BTStatus.Success); } return(BTStatus.Running); } ); BTAction BTAct_MoveEnemyPieces = new BTAction( () => { EnemyPiece curEnemy = null; if (EPcurEnemyIndex < EnemyList.Count) { curEnemy = EnemyList[EPcurEnemyIndex]; } switch (curEnemy.TurnStatus) { case EnemyTurnStatus.Unprocessed: curEnemy.ExecuteTurn(); break; case EnemyTurnStatus.Running: return(BTStatus.Running); // Do nothing, just let it run. default: // Both processed and waiting, move on to the next EnemyPiece. EPcurEnemyIndex++; if (EPcurEnemyIndex >= EnemyList.Count) // If went through the whole thing once already. { EPcurEnemyIndex = 0; BoardScroller.Instance.FocusCameraToPos( DungeonManager.Instance.GridPosToWorldPos(GameManager.Instance.Player.PosX, GameManager.Instance.Player.PosY), 0.2f, Graph.InverseExponential); return(BTStatus.Success); } break; } return(BTStatus.Running); } ); BTAction BTAct_AttackPlayer = new BTAction( () => { EnemyPiece curEnemy = null; if (EPcurEnemyIndex < EnemyList.Count) { curEnemy = EnemyList[EPcurEnemyIndex]; } switch (curEnemy.TurnStatus) { case EnemyTurnStatus.Waiting: curEnemy.ExecuteTurn(); break; case EnemyTurnStatus.Running: return(BTStatus.Running); // Do nothing, just let it run. default: // Move on to the next one. Only search for those that are Waiting status. EPcurEnemyIndex++; if (EPcurEnemyIndex >= EnemyList.Count) // If went finish second pass. { return(BTStatus.Success); } break; } return(BTStatus.Running); } ); // Reduce the player's shield by 1 point after end of every enemy turn. BTAction BTAct_ReducePlayersShield = new BTAction( () => { Player.DeductShieldPoints(1); if (Player.TurnStatus == PlayerTurnStatus.Running) { return(BTStatus.Running); } else { EndEnemyPhase(); return(BTStatus.Success); } } ); // BT_Sequence only runs when there are enemy pieces. // Refer to BT_NullCheckSelector below. BTSequence BT_EnemyMovementSequence = new BTSequence(BTAct_MoveEnemyPieces, BTAct_AttackPlayer); // Root is Selector that checks for enemies. // If no enemies, immediately stops (BTAct_NoEnemyCheck returns success). BTSelector BT_NullCheckSelector = new BTSelector(BTAct_NoEnemyCheck, BT_EnemyMovementSequence); BTSequence BT_Root = new BTSequence(BTAct_EnemyPhaseStartAnimations, BT_NullCheckSelector, BTAct_ReducePlayersShield); mEnemyPhaseBehaviourTree = new BehaviourTree(BT_Root); }
public override BTNode Init() { _useAnimEvent = true; base.Init(); animator = GetComponent <Animator>(); characterController = GetComponent <CharacterController>(); BTSelector root = new BTSelector(); //键盘控制的分支 BTConditionEvaluator evaluatorKey = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorKey.AddConditional(new BTCheckKeyOrTouch(BTCheckKeyOrTouch.ActionExecution.None)); BTSimpleParallel translation = new BTSimpleParallel(); { translation.SetPrimaryChild(new BTActionTranslate(_database.transform, speed, BTDataReadOpt.ReadEveryTick)); //translation.AddChild(new BTActionPlayAnimation(animator, "run")); translation.AddChild(new BTActionAnimTransition(animator, "run", GlobalConfig.AC_STATE_Run, -1)); } evaluatorKey.child = translation; root.AddChild(evaluatorKey); //easyJoystick控制的分支 BTConditionEvaluator evaluatorJoystick = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorJoystick.AddConditional(new BTCheckEasyJoystick()); evaluatorJoystick.child = translation; root.AddChild(evaluatorJoystick); //easytouch控制的分支 BTConditionEvaluator evaluatorTouch = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorTouch.AddConditional(new BTCheckEasyTouch()); evaluatorTouch.AddConditional(new BTCheckWithinDistance(_database.transform, 1f, "TargetPositon", BTCheckWithinDistance.DataOpt.TouchPosition), true); BTSimpleParallel pathFind = new BTSimpleParallel(); { pathFind.SetPrimaryChild(new BTActionPathFind()); pathFind.AddChild(new BTActionAnimTransition(animator, "run", GlobalConfig.AC_STATE_Run, -1)); } evaluatorTouch.child = pathFind; root.AddChild(evaluatorTouch); //普通攻击的分支 BTConditionEvaluator evaluatorAttack = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorAttack.AddConditional(new BTCheckAttack(BTCheckAttackOpt.Common)); BTSimpleParallel catchSubtree = new BTSimpleParallel(); { catchSubtree.SetPrimaryChild(new BTActionAnimTransition(animator, "attack", GlobalConfig.AC_STATE_Atk)); var actionAttack = new BTActionAttack(gameObject, animator, "attack", new TrailEvent(0.35f, 0.51f)); actionAttack.SetAnimFramekEvent(0.5f, AttackMode.Single, 100); catchSubtree.AddChild(actionAttack); } evaluatorAttack.child = catchSubtree; root.AddChild(evaluatorAttack); //技能攻击的分支 BTConditionEvaluator evaluatorSkill = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorSkill.AddConditional(new BTCheckAttack(BTCheckAttackOpt.Skill_1)); BTSimpleParallel skillSubtree = new BTSimpleParallel(); { skillSubtree.SetPrimaryChild(new BTActionAnimTransition(animator, "attack_showoff", GlobalConfig.AC_STATE_JUGG_SKILL_Showoff)); var skillAttack = new BTActionAttack(gameObject, animator, "attack_showoff", new TrailEvent(0.35f, 1.3f)); skillAttack.SetAnimFramekEvent(0.6f, AttackMode.Circular, 150); skillAttack.SetAnimFramekEvent(1.0f, AttackMode.Circular, 150); skillSubtree.AddChild(skillAttack); } evaluatorSkill.child = skillSubtree; root.AddChild(evaluatorSkill); BTConditionEvaluator evaluatorSkill_2 = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorSkill_2.AddConditional(new BTCheckAttack(BTCheckAttackOpt.Skill_2)); BTSimpleParallel skill_2Tree = new BTSimpleParallel(); { skill_2Tree.SetPrimaryChild(new BTActionAnimTransition(animator, "attack_spin_odachi", GlobalConfig.AC_STATE_JUGG_SKILL_Spin, 3)); var skillAttack = new BTActionAttack(gameObject, animator, "attack_spin_odachi", new TrailEvent(0.31f, 1.2f, 3)); skillAttack.SetAnimFramekEvent(0.6f, AttackMode.Circular, 150); skillAttack.SetAnimFramekEvent(1.0f, AttackMode.Circular, 150); skill_2Tree.AddChild(skillAttack); } evaluatorSkill_2.child = skill_2Tree; root.AddChild(evaluatorSkill_2); //idle分支 BTActionPlayAnimation palyIdle = new BTActionAnimTransition(animator, "idle", GlobalConfig.AC_STATE_Idle, -1); root.AddChild(palyIdle); return(root); }
private void InitializeBehaviourTree() { #region Farming Behaviour //HARVESTING BTSelector _harvestingBehaviour = new BTSelector(Blackboard, new BTIsEverythingHarvested(Blackboard), new BTHarvestCrops(Blackboard) ); //SEEDING BTSelector _seedingBehaviour = new BTSelector(Blackboard, new BTIsEverythingSeeded(Blackboard), new BTSequencer(Blackboard, new BTSelector(Blackboard, new BTHasItemOfType(Blackboard, typeof(Seeds)), new BTGetSeeds(Blackboard) ), new BTPlantSeeds(Blackboard) ) ); //WATERING BTSelector _wateringBehaviour = new BTSelector(Blackboard, new BTIsEverythingWatered(Blackboard), new BTSequencer(Blackboard, new BTSelector(Blackboard, new BTHasItemOfType(Blackboard, typeof(WateringCan)), new BTGetWateringCan(Blackboard) ), new BTSelector(Blackboard, new BTCurrentItemIsFilledWithType(Blackboard, FillType.Water), new BTGetWaterFromWell(Blackboard) ), new BTWaterCrops(Blackboard, AssignedFarm) ) ); BTSequencer _farmingBehaviour = new BTSequencer(Blackboard, _harvestingBehaviour, _seedingBehaviour, _wateringBehaviour //_fertilizeBehaviour ); #endregion BTSelector _checkForProfession = new BTSelector(Blackboard, new BTInvert(new BTHasProfession(Blackboard, Profession.None)) //,BTDoOwnThing() (of een BTSelector _doOwnThing) ); BTSequencer _handleProfession = new BTSequencer(Blackboard, new BTHasProfession(Blackboard, Profession.Farmer), _farmingBehaviour ); MasterBehaviourTree = new BTSequencer(Blackboard, _checkForProfession, _handleProfession); }
public void Init() { // 条件 BaseCondiction.ExternalFunc IsDeadFun = () => { if (mMonster.mRoleData.mHp <= 0) { return(true); } else { return(false); } }; var Alive = new PreconditionNOT(IsDeadFun, "活"); var Dead = new Precondition(IsDeadFun, "死"); BaseCondiction.ExternalFunc targetFun = () => { Role targetRole = mMonster.mRoleData.GetTargetRole(); if (targetRole) { return(targetRole.mBuffSystem.EnableSelect()); } else { return(false); } }; var hasTarget = new Precondition(targetFun, "发现目标"); var hasNoTarget = new PreconditionNOT(targetFun, "无目标"); BaseCondiction.ExternalFunc AtkRangeFun = () => { Role targetRole = mMonster.mRoleData.GetTargetRole(); if (targetRole) { float dis = Vector3.Distance(targetRole.transform.position, mMonster.transform.position); if (dis <= mMonster.mSkillInfo.mAtkDistance) { return(true); } else { if (dis > 5)//脱离目标 { mMonster.mRoleData.SetTargetRole(-1); } } } return(false); }; var AtkRange = new Precondition(AtkRangeFun, "在攻击范围内"); var NoAtkRange = new PreconditionNOT(AtkRangeFun, "超出攻击范围"); //BaseCondiction.ExternalFunc HpFun = () => { if (mMonster.mRoleData.mHp <= 50) return true; else return false; }; //var HPLess = new Precondition(HpFun, "快死"); //var HPMore = new PreconditionNOT(HpFun, "健康"); BaseCondiction.ExternalFunc CanMoveFun = () => { return(mMonster.mBuffSystem.CanMove()); }; var canMove = new Precondition(CanMoveFun, "能移动"); var cantMove = new PreconditionNOT(CanMoveFun, "不能移动"); BaseCondiction.ExternalFunc CanAtkFun = () => { return(mMonster.mBuffSystem.CanAtk()); }; var canAtk = new Precondition(CanAtkFun, "能攻击"); var cantAtk = new PreconditionNOT(CanAtkFun, "不能攻击"); //BaseCondiction.ExternalFunc EnableSelectFun = () => //{ // Role targetRole = mMonster.mRoleData.GetTargetRole(); // if (targetRole) // { // return targetRole.mBuffSystem.EnableSelect(); // } // return false; //}; //var enableSelect = new Precondition(EnableSelectFun, "能选"); ////var disableSelect = new PreconditionNOT(EnableSelectFun, "不能选"); //BT Tree mRoot = new BTSelector(); mRoot.name = "Root"; mRoot.Activate(); BTSequence DeadSeq = new BTSequence(); { DeadSeq.AddChild(Dead); // 死亡Action DeadSeq.AddChild(new BTActionWait(5)); DeadSeq.AddChild(new ReviveAction(mMonster)); mRoot.AddChild(DeadSeq); } BTSelector AliveSel = new BTSelector(); BTSequence AliveSeq = new BTSequence(); { AliveSeq.AddChild(Alive); AliveSeq.AddChild(AliveSel); mRoot.AddChild(AliveSeq); } BTSequence followSubtree = new BTSequence(); { followSubtree.AddChild(canMove); followSubtree.AddChild(hasTarget); followSubtree.AddChild(NoAtkRange); //followSubtree.AddChild(HPMore); // 追击Action followSubtree.AddChild(new FollowAction(mMonster)); AliveSel.AddChild(followSubtree); } BTSequence atkSeq = new BTSequence(); { atkSeq.AddChild(canAtk); atkSeq.AddChild(hasTarget); atkSeq.AddChild(AtkRange); //atkSeq.AddChild(HPMore); // 攻击Action atkSeq.AddChild(new AttackAction(mMonster)); atkSeq.AddChild(new BTActionWaitRandom(2.0f, 3.0f)); AliveSel.AddChild(atkSeq); } BTSequence patrolSeq = new BTSequence(); { patrolSeq.AddChild(canMove); patrolSeq.AddChild(hasNoTarget); patrolSeq.AddChild(new BTActionWaitRandom(1.0f, 5.0f)); // 巡逻Action patrolSeq.AddChild(new PatrolAction(mMonster)); AliveSel.AddChild(patrolSeq); } BTSequence IdleSeq = new BTSequence(); { IdleSeq.AddChild(hasNoTarget); // 休息Action IdleSeq.AddChild(new IdleAction(mMonster)); AliveSel.AddChild(IdleSeq); } //BTSequence runAwaySeq = new BTSequence(); //{ // runAwaySeq.AddChild(canMove); // runAwaySeq.AddChild(hasTarget); // runAwaySeq.AddChild(HPLess); // // 逃跑Action // runAwaySeq.AddChild(new RunAwayAction(mMonster)); // AliveSel.AddChild(runAwaySeq); //} }
private BTNode LoadBTNode(XmlNode currentNode, AI owner, MacroAIParty party) { XmlNodeList nodeContent = currentNode.ChildNodes; XmlAttributeCollection nodeAttributes = currentNode.Attributes; BTNode node = null; if (currentNode.Name == "behavior") { node = LoadBTNode(nodeContent[0], owner, party); } else if (currentNode.Name == "composite") { BTComposite compNode = null; if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Sequence") { BTSequence seqNode = new BTSequence(); seqNode.CompNodeType = BTCompType.Sequence; compNode = seqNode; } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Selector") { BTSelector selNode = new BTSelector(); selNode.CompNodeType = BTCompType.Selector; compNode = selNode; } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "ParallelAnd") { BTParallelAnd parNode = new BTParallelAnd(); parNode.CompNodeType = BTCompType.ParallelAnd; compNode = parNode; } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "ParallelMain") { BTParallelMain parNode = new BTParallelMain(); parNode.CompNodeType = BTCompType.ParallelMain; compNode = parNode; } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Random") { BTRandom randNode = new BTRandom(); randNode.CompNodeType = BTCompType.Random; compNode = randNode; } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Switch") { BTSwitch swNode = new BTSwitch(); swNode.CompNodeType = BTCompType.Switch; compNode = swNode; } compNode.Children = new List <BTNode>(); foreach (XmlNode nodeItem in nodeContent) { compNode.Children.Add(LoadBTNode(nodeItem, owner, party)); } node = compNode; } else if (currentNode.Name == "decorator") { BTDecorator decNode = null; if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Repeat") { BTRepeat repNode = new BTRepeat(); decNode = repNode; } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Invert") { BTInvert invNode = new BTInvert(); decNode = invNode; } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "UntilFail") { BTUntilFail repNode = new BTUntilFail(); decNode = repNode; } foreach (XmlNode nodeItem in nodeContent) { decNode.Child = LoadBTNode(nodeItem, owner, party); } node = decNode; } else if (currentNode.Name == "leaf") { XmlNodeList parameterList = currentNode.ChildNodes; List <string> parameters = new List <string>(); foreach (XmlNode paramNode in parameterList) { parameters.Add(paramNode.InnerText); } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Check") { if (nodeAttributes["name"] != null) { string actionName = nodeAttributes["name"].Value; BTCheck checkNode = new BTCheck(); checkNode.Action = actionName; checkNode.Parameters = parameters; checkNode.MyAI = owner; checkNode.MyParty = party; node = checkNode; } } if (nodeAttributes["type"] != null && nodeAttributes["type"].Value == "Action") { if (nodeAttributes["name"] != null) { BTLeaf leafNode = (BTLeaf)System.Activator.CreateInstance(System.Type.GetType("BT" + nodeAttributes["name"].Value)); leafNode.Parameters = parameters; leafNode.MyAI = owner; leafNode.MyParty = party; node = leafNode; } } } return(node); }
public override BTNode Init() { _useAnimEvent = true; base.Init(); animator = GetComponent<Animator>(); characterController = GetComponent<CharacterController>(); BTSelector root = new BTSelector(); //键盘控制的分支 BTConditionEvaluator evaluatorKey = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorKey.AddConditional(new BTCheckKeyOrTouch(BTCheckKeyOrTouch.ActionExecution.None)); BTSimpleParallel translation = new BTSimpleParallel(); { translation.SetPrimaryChild(new BTActionTranslate(_database.transform, speed, BTDataReadOpt.ReadEveryTick)); //translation.AddChild(new BTActionPlayAnimation(animator, "run")); translation.AddChild(new BTActionAnimTransition(animator,"run",GlobalConfig.AC_STATE_Run,-1)); } evaluatorKey.child = translation; root.AddChild(evaluatorKey); //easyJoystick控制的分支 BTConditionEvaluator evaluatorJoystick = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorJoystick.AddConditional(new BTCheckEasyJoystick()); evaluatorJoystick.child = translation; root.AddChild(evaluatorJoystick); //easytouch控制的分支 BTConditionEvaluator evaluatorTouch = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorTouch.AddConditional(new BTCheckEasyTouch()); evaluatorTouch.AddConditional(new BTCheckWithinDistance(_database.transform, 1f, "TargetPositon", BTCheckWithinDistance.DataOpt.TouchPosition), true); BTSimpleParallel pathFind = new BTSimpleParallel(); { pathFind.SetPrimaryChild(new BTActionPathFind()); pathFind.AddChild(new BTActionAnimTransition(animator, "run", GlobalConfig.AC_STATE_Run, -1)); } evaluatorTouch.child = pathFind; root.AddChild(evaluatorTouch); //普通攻击的分支 BTConditionEvaluator evaluatorAttack = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorAttack.AddConditional(new BTCheckAttack(BTCheckAttackOpt.Common)); BTSimpleParallel catchSubtree = new BTSimpleParallel(); { catchSubtree.SetPrimaryChild(new BTActionAnimTransition(animator, "attack", GlobalConfig.AC_STATE_Atk)); var actionAttack = new BTActionAttack(gameObject, animator, "attack", new TrailEvent(0.35f, 0.51f)); actionAttack.SetAnimFramekEvent(0.5f, AttackMode.Single, 100); catchSubtree.AddChild(actionAttack); } evaluatorAttack.child = catchSubtree; root.AddChild(evaluatorAttack); //技能攻击的分支 BTConditionEvaluator evaluatorSkill = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorSkill.AddConditional(new BTCheckAttack(BTCheckAttackOpt.Skill_1)); BTSimpleParallel skillSubtree = new BTSimpleParallel(); { skillSubtree.SetPrimaryChild(new BTActionAnimTransition(animator, "attack_showoff", GlobalConfig.AC_STATE_JUGG_SKILL_Showoff)); var skillAttack = new BTActionAttack(gameObject, animator, "attack_showoff", new TrailEvent(0.35f, 1.3f)); skillAttack.SetAnimFramekEvent(0.6f, AttackMode.Circular, 150); skillAttack.SetAnimFramekEvent(1.0f, AttackMode.Circular, 150); skillSubtree.AddChild(skillAttack); } evaluatorSkill.child = skillSubtree; root.AddChild(evaluatorSkill); BTConditionEvaluator evaluatorSkill_2 = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorSkill_2.AddConditional(new BTCheckAttack(BTCheckAttackOpt.Skill_2)); BTSimpleParallel skill_2Tree = new BTSimpleParallel(); { skill_2Tree.SetPrimaryChild(new BTActionAnimTransition(animator, "attack_spin_odachi", GlobalConfig.AC_STATE_JUGG_SKILL_Spin,3)); var skillAttack = new BTActionAttack(gameObject, animator, "attack_spin_odachi", new TrailEvent(0.31f, 1.2f,3)); skillAttack.SetAnimFramekEvent(0.6f, AttackMode.Circular, 150); skillAttack.SetAnimFramekEvent(1.0f, AttackMode.Circular, 150); skill_2Tree.AddChild(skillAttack); } evaluatorSkill_2.child = skill_2Tree; root.AddChild(evaluatorSkill_2); //idle分支 BTActionPlayAnimation palyIdle = new BTActionAnimTransition(animator, "idle", GlobalConfig.AC_STATE_Idle,-1); root.AddChild(palyIdle); return root; }
public override BTNode Init() { base.Init(); animator = GetComponent <Animator>(); BTSelector root = new BTSelector(); BTActionDeath death = new BTActionDeath(gameObject); root.AddChild(death); //领地限制的分支,只能在该范围活动 BTConditionEvaluator evaluatorTerritory = new BTConditionEvaluator(BTLogic.And, false, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorTerritory.AddConditional(new BTCheckWithinDistance(_database.transform, territoryDis, null, BTCheckWithinDistance.DataOpt.FixedPosition), true); BTSimpleParallel goHome = new BTSimpleParallel(); { goHome.SetPrimaryChild(new BTActionCharacterMove(_database.transform, speed, 0.1f, null, BTActionMove.DataOpt.FixedPosition, BTActionMove.UsageOpt.Position, BTDataReadOpt.ReadEveryTick)); goHome.AddChild(new BTActionPlayAnimation(animator, "Walk")); } evaluatorTerritory.child = goHome; root.AddChild(evaluatorTerritory); BTConditionEvaluator evaluatorTarget = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); evaluatorTarget.AddConditional(new BTCheckExistence(_database.transform, defendDis, "Player", BTCheckExistence.CheckOpt.CheckSphere)); //加一层组合,来判断进行哪个动作 BTSelector actionSelector = new BTSelector(); evaluatorTarget.child = actionSelector; //评估是否有碰撞 BTConditionEvaluator evaluatorCollision = new BTConditionEvaluator(BTLogic.And, true, BT.BTConditionEvaluator.ClearChildOpt.OnNotRunning); BTCheckCollision collision = new BTCheckCollision("Player", tolerance, BTCheckCollision.CheckOpt.RayCast); evaluatorCollision.AddConditional(collision); BTSequence attackSubtre = new BTSequence(); { attackSubtre.AddChild(new BTActionPlayAnimation(animator, "Attack")); } evaluatorCollision.child = attackSubtre; actionSelector.AddChild(evaluatorCollision); //没有碰撞则移动 BTSimpleParallel moveTo = new BTSimpleParallel(); { moveTo.SetPrimaryChild(new BTActionCharacterMove(_database.transform, speed, tolerance, target, BTDataReadOpt.ReadEveryTick)); moveTo.AddChild(new BTActionPlayAnimation(animator, "Walk")); } actionSelector.AddChild(moveTo); root.AddChild(evaluatorTarget); //Idle分支 BTActionPlayAnimation palyIdle = new BTActionPlayAnimation(animator, "Idle"); root.AddChild(palyIdle); return(root); }