title: C# flocking system works in Unity but is completely random in AR
body: <p>I have created a flocking system using 2 c# scripts. There are some custom behaviours set up that cause the objects to seek a goal and then not seek it. This creates an inward outward effect, like it's breathing. This works perfectly in the unity editor but in the built AR, the particle movement follows the scripted behaviour for about 5-10 seconds but then the particles seem to get a mind of there own and fly out randomly. I can't figure why they are behaving so differently. Someone suggested that maybe the <code>AR Session Origin </code> isn't behaving as it should. I had an image target set up but it behaves this way regardless of using the target or not. If anyone has had this problem before or knows a place to look to work out what the problem is I'd really appreciate it! I am building to Android if that makes a difference
  <a href="https://youtu.be/Fq8KRT2yC0M" rel="nofollow noreferrer"><strong>Video of working</strong></a>
  <a href="https://youtu.be/v0nBdGB73xA" rel="nofollow noreferrer"><strong>Video of not working</strong></a></p>
  <p><strong>FlockManager</strong></p>
  <pre><code>using System.Collections.Generic;
  using UnityEngine;
  
  public class FlockManager : MonoBehaviour //mono is script API
  {
      //particles is a list type GO
      public List&lt;GameObject&gt; particles;
      public GameObject particlePrefab;
      // public int particleCount;
      public Vector3 range = new Vector3(2,2,2);
      public Material[] mats;
  
      public bool seekGoal = true;
      public bool obedient = true;
      public bool willful = false;
  
      [Range(0, 200)]
      public int neighbourDistance =50;
  
      [Range(0,2)]
      public float maxForce = 1.0f;
  
      [Range(0,5)]
      public float maxvelocity = 2.0f;
      
      public int[] dataSet = new int[] {128, 135, 151, 168, 187, 206, 229, 253, 279, 307, 338, 371, 407, 446, 487, 533};
      // Declare and set array element values.
      
      int dataIndex = 0;
  
      //export is a keyword. look it up later. 
  
      // Start is called before the first frame update
      void Start()
      {
          // particles = new GameObject[particleCount];
          generateParticles(128);
          willful = false;
          // int time = (int)Time.time;
          InvokeRepeating(&quot;toggleSeek&quot;, 0f, 5f);
          
      //    Invoke(&quot;delayAndAdd&quot;, 10f);
  
         InvokeRepeating(&quot;setParticleNumbers&quot;, 0f, 10f);
  
  
      }
  
      // void delayAndAdd()
      // {
      //     generateParticles(300);
      // }
  
      void setParticleNumbers()
      {
          if(dataIndex == dataSet.Length)
          {
              dataIndex = 0;
          }
          generateParticles(dataSet[dataIndex]);
          dataIndex = dataIndex + 1;
  
  
      }
  
      
      void toggleSeek()
      {
          seekGoal = !seekGoal;
          obedient = !obedient;
          willful = !willful;
      }
  
      void generateParticles(int numberOfParticles)
      {
          var difference = numberOfParticles - particles.Count;
          //moving this out of start so that we can manipulate the number of gameobjects in the flock rather than just starting them.
          //for every particle in difference, either create or destroy a particle based on number of particles. 
          if(difference &gt;= 0)
          {
              for(int i = 0; i &lt; difference; i++)
          {
              addParticle(); 
          }
          }
           else
          {
              for(int i = 0; i &lt; difference * -1; i++)
          {
              //remove from screen
              Destroy(particles[particles.Count - 1]); 
              //remove from mem.
              particles.RemoveAt(particles.Count - 1);
            
          }
  
          }
          
  
      }
  
      void addParticle()
      {
          
          Vector3 particlePos = new Vector3(Random.Range(-range.x, range.x), Random.Range(-range.y, range.y), Random.Range(-range.z, range.z));
          var GO = Instantiate(particlePrefab, this.transform.position + particlePos, Quaternion.identity) as GameObject;
          GO.GetComponent&lt;FlockParticleBehaviour&gt;().manager = this.gameObject;
          particles.Add(GO);
          GO.GetComponent&lt;Renderer&gt;().material = mats[Random.Range(0,mats.Length)];
  
          //create gameobject, make it the manager then adds it to the list
      }
  }
  </code></pre>
  <p><strong>FlockParticleBehaviour</strong></p>
  <pre><code>using System.Collections.Generic;
  using UnityEngine;
  
  public class FlockParticleBehaviour : MonoBehaviour
  {
      public GameObject manager;
      public Vector3 location = Vector3.zero;
      public Vector3 velocity;
      Vector3 goalPos = Vector3.zero;
      Vector3 currentForce; //this is a current force position. pushes particle around by adding all the other forces
  
      // Start is called before the first frame update
      void Start()
      {
          velocity = new Vector3(Random.Range(0.01f, 0.1f), Random.Range(0.01f, 0.1f), Random.Range(0.01f, 0.1f));
          location = new Vector3(this.gameObject.transform.position.x, this.gameObject.transform.position.y, this.gameObject.transform.position.z);
      }
  
  //component vector pointing towards where you want them to go.
      Vector3 seek(Vector3 target)
      {
          return(target - location);
      }
  
      void applyForce(Vector3 f)
      {
          Vector3 force = new Vector3(f.x, f.y, f.z);
          if(force.magnitude &gt; manager.GetComponent&lt;FlockManager&gt;().maxForce)
          {
              force = force.normalized;
              force *= manager.GetComponent&lt;FlockManager&gt;().maxForce;
          }
          this.GetComponent&lt;Rigidbody&gt;().AddForce(force);
  
          if(this.GetComponent&lt;Rigidbody&gt;().velocity.magnitude &gt; manager.GetComponent&lt;FlockManager&gt;().maxvelocity)
          {
              this.GetComponent&lt;Rigidbody&gt;().velocity = this.GetComponent&lt;Rigidbody&gt;().velocity.normalized;
              this.GetComponent&lt;Rigidbody&gt;().velocity *= manager.GetComponent&lt;FlockManager&gt;().maxvelocity;
          }
  
          Debug.DrawRay(this.transform.position, force, Color.white);
  
      }
  
      Vector3 align()
      {
          float neighbourdist = manager.GetComponent&lt;FlockManager&gt;().neighbourDistance;
          Vector3 sum = Vector3.zero;
          int count = 0;
          foreach (GameObject other in manager.GetComponent&lt;FlockManager&gt;().particles)
          {
              if(other == this.gameObject) continue;
  
              float d = Vector3.Distance(location, other.GetComponent&lt;FlockParticleBehaviour&gt;().location);
  
              if (d &lt; neighbourdist) {
                  sum += other.GetComponent&lt;FlockParticleBehaviour&gt;().velocity;
                  count++;
              }
          }
          if (count &gt;0)
          {
              sum /= count;
              Vector3 steer = sum - velocity;
              return steer;
          }
  
          return Vector3.zero;
      }
  
  
      Vector3 cohesion()
      {
          float neighbourdist = manager.GetComponent&lt;FlockManager&gt;().neighbourDistance;
          Vector3 sum = Vector3.zero;
          int count = 0;
          foreach (GameObject other in manager.GetComponent&lt;FlockManager&gt;().particles)
          {
              if(other == this.gameObject) continue;
  
              float d = Vector3.Distance(location, other.GetComponent&lt;FlockParticleBehaviour&gt;().location);
              if(d &lt; neighbourdist)
              {
                  sum += other.GetComponent&lt;FlockParticleBehaviour&gt;().location;
                  count++;
              }
          }
  
          if (count &gt; 0)
          {
              sum /= count;
              return seek(sum);
          }
  
          return Vector3.zero;
      }
  
  
      void flock()
      {
          location = this.transform.position;
          velocity = this.GetComponent&lt;Rigidbody&gt;().velocity;
  
          if(manager.GetComponent&lt;FlockManager&gt;().obedient &amp;&amp; Random.Range(0,50) &lt;=1)
          {
              Vector3 ali = align();
              Vector3 coh = cohesion();
              Vector3 gl;
  
              if(manager.GetComponent&lt;FlockManager&gt;().seekGoal)
              {
                  gl = seek(goalPos);
                  currentForce = gl + ali +coh;
              }
              else
              currentForce = ali + coh;
  
              currentForce = currentForce.normalized;
          }
  
          if(manager.GetComponent&lt;FlockManager&gt;().willful &amp;&amp; Random.Range(0,50)&lt;=1)
          {
              if(Random.Range(0,50)&lt;1) //change direction
              currentForce = new Vector3(Random.Range(0.01f, 0.1f), Random.Range(0.01f, 0.1f),Random.Range(0.01f, 0.1f));
          }
  
          applyForce(currentForce);
  
      }
  
      // Update is called once per frame
      void Update()
      {
          flock();
          goalPos = manager.transform.position;
      }
  }
  </code></pre>