Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /**************************************
- Copyright Unluck Software
- www.chemicalbliss.com
- ***************************************/
- using UnityEngine;
- public class FlockChild:MonoBehaviour{
- [HideInInspector]
- public FlockController _spawner; //Reference to the flock controller that spawned this bird
- [HideInInspector]
- public Vector3 _wayPoint; //Waypoint used to steer towards
- public float _speed; //Current speed of bird
- [HideInInspector]
- public bool _dived =true; //Indicates if this bird has recently performed a dive movement
- [HideInInspector]
- public float _stuckCounter; //prevents looping around a waypoint by increasing minimum distance to waypoint
- [HideInInspector]
- public float _damping; //Damping used for steering (steer speed)
- [HideInInspector]
- public bool _soar = true; // Indicates if this is soaring
- [HideInInspector]
- public bool _landing; // Indicates if bird is landing or sitting idle
- [HideInInspector]
- public float _targetSpeed; // Max bird speed
- [HideInInspector]
- public bool _move = true; // Indicates if bird can fly
- public GameObject _model; // Reference to bird model
- public Transform _modelT; // Reference to bird model transform (caching tranform to avoid any extra getComponent calls)
- [HideInInspector]
- public float _avoidValue; //Random value used to check for obstacles. Randomized to lessen uniformed behaviour when avoiding
- [HideInInspector]
- public float _avoidDistance; //How far from an obstacle this can be before starting to avoid it
- float _soarTimer;
- bool _instantiated;
- static int _updateNextSeed = 0;
- int _updateSeed = -1;
- [HideInInspector]
- public bool _avoid = true;
- public Transform _thisT; //Reference to the transform component
- public Vector3 _landingPosOffset;
- //[HideInInspector]
- public bool Obstacle = false;
- public void Start(){
- FindRequiredComponents(); //Check if references to transform and model are set (These should be set in the prefab to avoid doind this once a bird is spawned, click "Fill" button in prefab)
- Wander(0.0f);
- SetRandomScale();
- _thisT.position = findWaypoint();
- RandomizeStartAnimationFrame();
- InitAvoidanceValues();
- _speed = _spawner._minSpeed;
- _spawner._activeChildren++;
- _instantiated = true;
- if(_spawner._updateDivisor > 1){
- int _updateSeedCap = _spawner._updateDivisor -1;
- _updateNextSeed++;
- this._updateSeed = _updateNextSeed;
- _updateNextSeed = _updateNextSeed % _updateSeedCap;
- }
- }
- public void Update() {
- //Skip frames
- if (_spawner._updateDivisor <=1 || _spawner._updateCounter == _updateSeed){
- SoarTimeLimit();
- CheckForDistanceToWaypoint();
- RotationBasedOnWaypointOrAvoidance();
- LimitRotationOfModel();
- }
- if ((_wayPoint.y+_thisT.parent.transform.position.y) <= 0)
- {
- Debug.Log("under the terrain");
- }
- }
- public void OnDisable() {
- CancelInvoke();
- _spawner._activeChildren--;
- }
- public void OnEnable() {
- if(_instantiated){
- _spawner._activeChildren++;
- if(_landing){
- _model.GetComponent<Animation>().Play(_spawner._idleAnimation);
- }else{
- _model.GetComponent<Animation>().Play(_spawner._flapAnimation);
- }
- }
- }
- public void FindRequiredComponents(){
- if(_thisT == null) _thisT = transform;
- if(_model == null) _model = _thisT.Find("Model").gameObject;
- if(_modelT == null) _modelT = _model.transform;
- }
- public void RandomizeStartAnimationFrame(){
- foreach(AnimationState state in _model.GetComponent<Animation>()) {
- state.time = Random.value * state.length;
- }
- }
- public void InitAvoidanceValues(){
- _avoidValue = Random.Range(.3f, .1f);
- if(_spawner._birdAvoidDistanceMax != _spawner._birdAvoidDistanceMin){
- _avoidDistance = Random.Range(_spawner._birdAvoidDistanceMax , _spawner._birdAvoidDistanceMin);
- return;
- }
- _avoidDistance = _spawner._birdAvoidDistanceMin;
- }
- public void SetRandomScale(){
- float sc = Random.Range(_spawner._minScale, _spawner._maxScale);
- _thisT.localScale=new Vector3(sc,sc,sc);
- }
- //Soar Timeout - Limits how long a bird can soar
- public void SoarTimeLimit(){
- if(this._soar && _spawner._soarMaxTime > 0){
- if(_soarTimer > _spawner._soarMaxTime){
- this.Flap();
- _soarTimer = 0.0f;
- }else {
- _soarTimer+=_spawner._newDelta;
- }
- }
- }
- public void CheckForDistanceToWaypoint(){
- if(!_landing && (_thisT.position - _wayPoint).magnitude < _spawner._waypointDistance+_stuckCounter){
- Wander(0.0f);
- _stuckCounter=0.0f;
- }else if(!_landing){
- _stuckCounter+=_spawner._newDelta;
- }else{
- _stuckCounter=0.0f;
- }
- }
- public void RotationBasedOnWaypointOrAvoidance(){
- Vector3 lookit = _wayPoint - _thisT.position;
- if(_targetSpeed > -1 && lookit != Vector3.zero){
- Quaternion rotation = Quaternion.LookRotation(lookit);
- _thisT.rotation = Quaternion.Slerp(_thisT.rotation, rotation, _spawner._newDelta * _damping);
- }
- if(_spawner._childTriggerPos){
- if((_thisT.position - _spawner._posBuffer).magnitude < 1){
- _spawner.SetFlockRandomPosition();
- }
- }
- _speed = Mathf.Lerp(_speed, _targetSpeed, _spawner._newDelta* 2.5f);
- //Position forward based on object rotation
- if(_move){
- _thisT.position += _thisT.forward*_speed*_spawner._newDelta;
- if(_avoid && _spawner._birdAvoid)
- {
- Avoidance();
- }
- }
- }
- public void Avoidance() {
- RaycastHit hitF = new RaycastHit();
- RaycastHit hitD = new RaycastHit();
- Vector3 fwd = _modelT.forward;
- Quaternion rot = Quaternion.identity;
- Vector3 rotE = Vector3.zero;
- Vector3 pos = Vector3.zero;
- pos = _thisT.position;
- rot = _thisT.rotation;
- rotE = _thisT.rotation.eulerAngles;
- bool ForwardRay = Physics.Raycast(_modelT.position, (_wayPoint-_modelT.position), out hitF, _avoidDistance, _spawner._avoidanceMask);
- if (ForwardRay)
- {
- //Debug.Log(!this._landing);
- Obstacle = true;
- //Debug.Log(_wayPoint.y + " " + _thisT.position.y);
- if (_wayPoint.y < _thisT.position.y)
- //if (DownRay) //(_wayPoint.y < _thisT.localPosition.y)
- {
- if (Physics.Raycast(_modelT.position, -Vector3.up, out hitD, _avoidDistance, _spawner._avoidanceMask))
- {
- rotE.x += _spawner._birdAvoidVerticalForce*_spawner._newDelta*_damping*0.1f;
- rotE.z += _spawner._birdAvoidHorizontalForce*_spawner._newDelta*_damping*0.1f;
- rot.eulerAngles = rotE;
- Debug.Log("down");
- _thisT.rotation = rot;
- _wayPoint.y -= _spawner._birdAvoidVerticalForce*_spawner._newDelta*.01f;
- }
- else //if (!this._landing)
- {
- rotE.x -= _spawner._birdAvoidVerticalForce*_spawner._newDelta*_damping*0.5f;
- rotE.z -= _spawner._birdAvoidHorizontalForce*_spawner._newDelta*_damping*0.5f;
- rot.eulerAngles = rotE;
- //Debug.Log("up");
- _thisT.rotation = rot;
- _wayPoint.y += _spawner._birdAvoidVerticalForce*_spawner._newDelta*.01f;
- }
- }
- /*else if (this._landing)
- {
- rotE.x -= _spawner._birdAvoidVerticalForce*_spawner._newDelta*_damping*.1f;
- rotE.y += _spawner._birdAvoidHorizontalForce*_spawner._newDelta*_damping*.1f;
- rot.eulerAngles = rotE;
- Debug.Log("left");
- _thisT.rotation = rot;
- }*/
- else //if (!this._landing)
- {
- rotE.x -= _spawner._birdAvoidVerticalForce*_spawner._newDelta*_damping*0.5f;
- rotE.z -= _spawner._birdAvoidHorizontalForce*_spawner._newDelta*_damping*0.5f;
- rot.eulerAngles = rotE;
- //Debug.Log("up");
- _thisT.rotation = rot;
- _wayPoint.y += _spawner._birdAvoidVerticalForce*_spawner._newDelta*.01f;
- }
- }
- else
- {
- Obstacle = false;
- }
- /*
- if (Physics.Raycast(_thisT.position, fwd+(_modelT.right*_avoidValue), out hit, _avoidDistance, _spawner._avoidanceMask)){
- rotE.y -= _spawner._birdAvoidHorizontalForce*_spawner._newDelta*_damping;
- rot.eulerAngles = rotE;
- Debug.Log(AvoidanceNum + "right");
- _thisT.rotation = rot;
- r= true;
- }else if (Physics.Raycast(_thisT.position, fwd+(_modelT.right*-_avoidValue), out hit, _avoidDistance, _spawner._avoidanceMask)){
- rotE.y += _spawner._birdAvoidHorizontalForce*_spawner._newDelta*_damping;
- rot.eulerAngles = rotE;
- Debug.Log(AvoidanceNum + "left");
- _thisT.rotation = rot;
- r= true;
- }
- if (_spawner._birdAvoidDown && !this._landing && Physics.Raycast(_thisT.position, -Vector3.up, out hit, _avoidDistance, _spawner._avoidanceMask)){
- rotE.x -= _spawner._birdAvoidVerticalForce*_spawner._newDelta*_damping;
- rot.eulerAngles = rotE;
- Debug.Log(AvoidanceNum + "down");
- _thisT.rotation = rot;
- pos.y += _spawner._birdAvoidVerticalForce*_spawner._newDelta*.01f;
- _thisT.position = pos;
- r= true;
- }else if (_spawner._birdAvoidUp && !this._landing && Physics.Raycast(_thisT.position, Vector3.up, out hit, _avoidDistance, _spawner._avoidanceMask)){
- rotE.x += _spawner._birdAvoidVerticalForce*_spawner._newDelta*_damping;
- rot.eulerAngles = rotE;
- Debug.Log(AvoidanceNum + "up");
- _thisT.rotation = rot;
- pos.y -= _spawner._birdAvoidVerticalForce*_spawner._newDelta*.01f;
- _thisT.position = pos;
- r= true;
- }*/
- }
- public void LimitRotationOfModel(){
- Quaternion rot = Quaternion.identity;
- Vector3 rotE = Vector3.zero;
- rot = _modelT.localRotation;
- rotE = rot.eulerAngles;
- if((_soar && _spawner._flatSoar|| _spawner._flatFly && !_soar)&& _wayPoint.y > _thisT.position.y||_landing){
- rotE.x = Mathf.LerpAngle(_modelT.localEulerAngles.x, -_thisT.localEulerAngles.x, _spawner._newDelta * 1.75f);
- rot.eulerAngles = rotE;
- _modelT.localRotation = rot;
- }else{
- rotE.x = Mathf.LerpAngle(_modelT.localEulerAngles.x, 0.0f, _spawner._newDelta * 1.75f);
- rot.eulerAngles = rotE;
- _modelT.localRotation = rot;
- }
- }
- public void Wander(float delay){
- if((!_landing) && (!Obstacle)){
- _damping = Random.Range(_spawner._minDamping, _spawner._maxDamping);
- _targetSpeed = Random.Range(_spawner._minSpeed, _spawner._maxSpeed);
- Invoke("SetRandomMode", delay);
- }
- }
- public void SetRandomMode(){
- CancelInvoke("SetRandomMode");
- if(!_dived && Random.value < _spawner._soarFrequency){
- Soar();
- }else if(!_dived && Random.value < _spawner._diveFrequency){
- Dive();
- }else{
- Flap();
- }
- }
- public void Flap(){
- if(_move){
- if(this._model != null) _model.GetComponent<Animation>().CrossFade(_spawner._flapAnimation, .5f);
- _soar=false;
- animationSpeed();
- _wayPoint = findWaypoint();
- if (_wayPoint.y < 0) _wayPoint.y = 0f;
- _dived = false;
- }
- }
- public Vector3 findWaypoint(){
- Vector3 t = Vector3.zero;
- t.x = Random.Range(-_spawner._spawnSphere, _spawner._spawnSphere) + _spawner._posBuffer.x;
- t.z = Random.Range(-_spawner._spawnSphereDepth, _spawner._spawnSphereDepth) + _spawner._posBuffer.z;
- t.y = Random.Range(-_spawner._spawnSphereHeight, _spawner._spawnSphereHeight) + _spawner._posBuffer.y;
- return t;
- }
- public void Soar(){
- if(_move){
- _model.GetComponent<Animation>().CrossFade(_spawner._soarAnimation, 1.5f);
- _wayPoint= findWaypoint();
- _soar = true;
- }
- }
- public void Dive(){
- if(_spawner._soarAnimation!=null){
- _model.GetComponent<Animation>().CrossFade(_spawner._soarAnimation, 1.5f);
- }else{
- foreach(AnimationState state in _model.GetComponent<Animation>()) {
- if(_thisT.position.y < _wayPoint.y +25){
- state.speed = 0.1f;
- }
- }
- }
- _wayPoint= findWaypoint();
- _wayPoint.y -= _spawner._diveValue;
- _dived = true;
- }
- public void animationSpeed(){
- foreach(AnimationState state in _model.GetComponent<Animation>()) {
- if(!_dived && !_landing){
- state.speed = Random.Range(_spawner._minAnimationSpeed, _spawner._maxAnimationSpeed);
- }else{
- state.speed = _spawner._maxAnimationSpeed;
- }
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement