diff --git a/Assets/Scripts/TerrainGeneration/TerrainGenerator.cs b/Assets/Scripts/TerrainGeneration/TerrainGenerator.cs
index 7c29e1562478bd08e45982a58d82abcf9a59213f..0dfe74af70958562f28acffc041a45f5161be28c 100644
--- a/Assets/Scripts/TerrainGeneration/TerrainGenerator.cs
+++ b/Assets/Scripts/TerrainGeneration/TerrainGenerator.cs
@@ -41,18 +41,29 @@ public class TerrainGenerator : MonoBehaviour
     [Tooltip("How tall the terrain is. May be changed to allow for higher terrains.")]
     public float terrainHeight = 600;
 
+    [Tooltip("What percentage of threads available should we use?")]
+    public float threadsUsage = 0.7f;
+
+    public int MaxThreads => Mathf.FloorToInt(Environment.ProcessorCount * threadsUsage);
+
+
     [Header("Autogenerated values")]
     [Tooltip("Which terrain grid are we on right now?")]
     public Vector2Int currentGridPosition;
 
+    [Tooltip("Array of terrains to reuse.")]
+    public Terrain[] terrains = new Terrain[9];
+
     [Tooltip("Dictionary of previously loaded terrains.")]
     public Dictionary<Vector2Int, TerrainData> previouslyLoaded = new();
 
-    public Queue<TerrainGenThread> threadsToRun = new();
+    public Queue<TerrainGenThread> queuedThreads = new();
 
     public ConcurrentBag<TerrainGenThread> completedGenerators = new();
 
-    public int threadsCount = 0;
+
+    [Header("Stats")]
+    public int runningThreads = 0;
 
     /// <summary>
     /// Apply the terrain that was generated by genThread.
@@ -78,24 +89,29 @@ public class TerrainGenerator : MonoBehaviour
         if (!previouslyLoaded.ContainsKey(gridPos) || forceRefresh)
         {
             TerrainData data = Instantiate(Resources.Load<TerrainData>("Template"));
-            TerrainGenThread genThread = new(this, data, crawlPos, gridPos);
+            TerrainGenThread tGenThread = new(this, data, crawlPos, gridPos);
+            previouslyLoaded[gridPos] = data;
 
-            threadsCount++;
-
-            if (threadsCount >= Environment.ProcessorCount)
+            if (runningThreads >= MaxThreads)
             {
-                threadsToRun.Enqueue(genThread);
+                // Too many threads.
+                queuedThreads.Enqueue(tGenThread);
             }
             else
             {
-                ThreadStart starter = new(genThread.Generate);
-                Thread thread = new(starter);
-                previouslyLoaded[gridPos] = data;
-                thread.Start();
+                StartThread(tGenThread);
             }
         }
     }
 
+    private void StartThread(TerrainGenThread tGenThread)
+    {
+        runningThreads++;
+        ThreadStart starter = new(tGenThread.Generate);
+        Thread thread = new(starter);
+        thread.Start();
+    }
+
     public virtual void GenerateSurronding(Vector2 initCrawlPos, bool forceRefresh = false)
     {
         int count = 0;
@@ -113,6 +129,7 @@ public class TerrainGenerator : MonoBehaviour
 
     private void Update()
     {
+        // Check for refresh.
         if (refresh)
         {
             refresh = false;
@@ -123,10 +140,33 @@ public class TerrainGenerator : MonoBehaviour
             GenerateSurronding(crawlStartPosition, true);
         }
 
-        if (completedGenerators.TryTake(out TerrainGenThread tGenThread))
+        // Check for queued threads.
+        if (queuedThreads.TryDequeue(out TerrainGenThread queuedThread)
+            && runningThreads < MaxThreads)
         {
-            ApplyGeneratedTerrain(tGenThread);
-            threadsCount--;
+            StartThread(queuedThread);
         }
+
+        // Check for completed generators.
+        if (completedGenerators.TryTake(out TerrainGenThread completedThread))
+        {
+            ApplyGeneratedTerrain(completedThread);
+            runningThreads--;
+        }
+    }
+
+    /// <summary>
+    /// Gets the square distance between two points.
+    /// If A is located at (0,0) and B is located at (5,-10),
+    /// the distance would be 5+10=15.
+    /// </summary>
+    /// <param name="a">A position on the grid.</param>
+    /// <param name="b">Another position.</param>
+    /// <returns></returns>
+    public int SquareDistance(Vector2Int a, Vector2Int b)
+    {
+        Vector2Int diff = b - a;
+
+        return Mathf.Abs(diff.x) + Mathf.Abs(diff.y);
     }
 }