public void GatherResource(ResourceNode resource) { if (_isDead) { return; } if (!canGather) { return; } if (resource.Equals(GatheringTarget)) { return; } if (GatheringTarget) { GatheringTarget.RemoveGatherer(teamId); } _enemyUnit = null; _isGathering = false; inResourceRange = false; // Get a Random point around the resource within the gathering radius // var vector2 = Random.insideUnitCircle.normalized * resource.gatherRadius; // var destination = resource.transform.position + new Vector3(vector2.x, 0, vector2.y); var resourcePosition = resource.transform.position; var randomPosition = Random.insideUnitCircle * resource.gatherRadius; var destination = resourcePosition + new Vector3(randomPosition.x, 0, randomPosition.y); NavMesh.SamplePosition(destination, out var hit, 3f, NavMesh.AllAreas); GatheringTarget = resource; MoveTo(hit.position, false); _currentState = UnitState.Gathering; }
public void MoveTo(Vector3 destination, bool forceChangeState = true) { if (_isDead) { return; } if (forceChangeState) { switch (_currentState) { case UnitState.Combat: _enemyUnit = null; _isAttacking = false; break; case UnitState.Gathering: inResourceRange = false; _isGathering = false; GatheringTarget.RemoveGatherer(teamId); GatheringTarget = null; break; case UnitState.Idle: case UnitState.Moving: _currentState = UnitState.Moving; _animator.SetInteger("unitState", 1); break; case UnitState.Building: inBuildingRange = false; _isBuilding = false; BuildingTarget.RemoveBuilder(); BuildingTarget = null; break; default: throw new ArgumentOutOfRangeException(); } _agent.stoppingDistance = 0; } _animator.SetInteger("unitState", 1); _agent.speed = moveSpeed.GetValue(); _agent.SetDestination(destination); }
public void Attack(Building enemy) { if (_isAttacking) { return; } if (enemy.teamId == teamId) { return; } switch (_currentState) { case UnitState.Gathering: GatheringTarget.RemoveGatherer(teamId); _isGathering = false; GatheringTarget = null; inResourceRange = false; break; case UnitState.Building: BuildingTarget.RemoveBuilder(); _isBuilding = false; BuildingTarget = null; inBuildingRange = false; break; case UnitState.Idle: break; case UnitState.Moving: break; case UnitState.Combat: break; default: throw new ArgumentOutOfRangeException(); } _enemyUnit = null; _enemyBuilding = enemy; _currentState = UnitState.Combat; _agent.stoppingDistance = attackRadius.GetValue(); }
private void Update() { if (_isDead) { return; } if (Math.Abs(_currentAttackRadius - attackRadius.GetValue()) > 0) { _currentAttackRadius = attackRadius.GetValue(); UpdateAttackRange(); } if (_currentState == UnitState.Moving && _agent.remainingDistance <= 0) { _currentState = UnitState.Idle; _animator.SetInteger("unitState", 0); } if (_currentState == UnitState.Moving || _currentState == UnitState.Idle) { if (_detectedEnemyUnits.Count > 0) { _enemyUnit = _detectedEnemyUnits[0]; _currentState = UnitState.Combat; } else if (_detectecEnemyBuildings.Count > 0) { _enemyBuilding = _detectecEnemyBuildings[0]; _currentState = UnitState.Combat; } } if (_currentState == UnitState.Combat) { if (_agent.remainingDistance >= attackRadius.GetValue()) { _animator.SetInteger("unitState", 1); } if (_enemyUnit) { if (_enemyUnit._isDead) { _detectedEnemyUnits.Remove(_enemyUnit); _enemyUnit = null; _isAttacking = false; return; } var dist = Vector3.Distance(_enemyUnit.transform.position, transform.position); if (dist <= attackRadius.GetValue()) { FaceTransform(_enemyUnit.transform); if (!_isAttacking) { _isAttacking = true; StartCoroutine(AttackTarget()); } } else { GoToTarget(dist); } } else if (_enemyBuilding) { if (_enemyBuilding.IsDead) { _detectecEnemyBuildings.Remove(_enemyBuilding); _enemyBuilding = null; _isAttacking = false; return; } var dist = Vector3.Distance(_enemyBuilding.transform.position, transform.position); if (dist <= attackRadius.GetValue()) { FaceTransform(_enemyBuilding.transform); if (!_isAttacking) { _isAttacking = true; StartCoroutine(AttackTarget()); } } else { GoToTarget(dist); } } else { _currentState = UnitState.Idle; _animator.SetInteger("unitState", 0); } } if (_currentState == UnitState.Gathering) { if (!GatheringTarget) { _isGathering = false; inResourceRange = false; _currentState = UnitState.Idle; _animator.SetInteger("unitState", 0); } // Physics.SphereCast(transform.position, _gatheringTarget.gatherRadius, out var hit, gameObject.layer); else if (inResourceRange) { if (!_isGathering && _agent.remainingDistance <= GatheringTarget.gatherRadius) { _animator.SetInteger("unitState", 2); GatheringTarget.AddGatherer(teamId); _isGathering = true; } FaceTransform(GatheringTarget.transform); } } if (_currentState == UnitState.Building) { if (!BuildingTarget) { _isBuilding = false; inBuildingRange = false; _currentState = UnitState.Idle; _animator.SetInteger("unitState", 0); } else if (inBuildingRange) { if (!_isBuilding && _agent.remainingDistance <= BuildingTarget.buildingRadius) { _animator.SetInteger("unitState", 2); BuildingTarget.AddBuilder(); _isBuilding = true; } FaceTransform(BuildingTarget.transform); } } if (_currentHitPoints < maxHitPoints) { if (!_unitHealthBar.gameObject.activeInHierarchy) { _unitHealthBar.gameObject.SetActive(true); } } else if (_currentState == UnitState.Idle && !_isSelected) { _unitHealthBar.gameObject.SetActive(false); } }