Browse Source

Added Perlin Noise 3D

James Peret 1 year ago
parent
commit
e551a510db

+ 1 - 1
Runtime/NoiseGenerator.cs

@@ -31,7 +31,7 @@ namespace KairoEngine.NoiseUtilities
             this.scale = 1f;
             this.offset = new Vector2();
             this.opacity = 1f;
-            GenerateTexture();
+            //GenerateTexture(); // Disabled to fix weird bug when unity starts
         }
 
         public float SamplePoint(float x, float y)

+ 158 - 0
Runtime/PerlinNoise3D.cs

@@ -0,0 +1,158 @@
+using System.Collections;
+using System.Collections.Generic;
+using UnityEngine;
+
+namespace KairoEngine.NoiseUtilities
+{
+    public class PerlinNoise3D
+    {
+        private static int[] permutation = {
+            151,160,137, 91, 90, 15,131, 13,201, 95, 96, 53,194,233,  7,225,
+            140, 36,103, 30, 69,142,  8, 99, 37,240, 21, 10, 23,190,  6,148,
+            247,120,234, 75,  0, 26,197, 62, 94,252,219,203,117, 35, 11, 32,
+            57,177, 33, 88,237,149, 56, 87,174, 20,125,136,171,168, 68,175,
+            74,165, 71,134,139, 48, 27,166, 77,146,158,231, 83,111,229,122,
+            60,211,133,230,220,105, 92, 41, 55, 46,245, 40,244,102,143, 54,
+            65, 25, 63,161,  1,216, 80, 73,209, 76,132,187,208, 89, 18,169,
+            200,196,135,130,116,188,159, 86,164,100,109,198,173,186,  3, 64,
+            52,217,226,250,124,123,  5,202, 38,147,118,126,255, 82, 85,212,
+            207,206, 59,227, 47, 16, 58, 17,182,189, 28, 42,223,183,170,213,
+            119,248,152,  2, 44,154,163, 70,221,153,101,155,167, 43,172,  9,
+            129, 22, 39,253, 19, 98,108,110, 79,113,224,232,178,185,112,104,
+            218,246, 97,228,251, 34,242,193,238,210,144, 12,191,179,162,241,
+            81, 51,145,235,249, 14,239,107, 49,192,214, 31,181,199,106,157,
+            184, 84,204,176,115,121, 50, 45,127,  4,150,254,138,236,205, 93,
+            222,114, 67, 29, 24, 72,243,141,128,195, 78, 66,215, 61,156,180,
+
+            151,160,137, 91, 90, 15,131, 13,201, 95, 96, 53,194,233,  7,225,
+            140, 36,103, 30, 69,142,  8, 99, 37,240, 21, 10, 23,190,  6,148,
+            247,120,234, 75,  0, 26,197, 62, 94,252,219,203,117, 35, 11, 32,
+            57,177, 33, 88,237,149, 56, 87,174, 20,125,136,171,168, 68,175,
+            74,165, 71,134,139, 48, 27,166, 77,146,158,231, 83,111,229,122,
+            60,211,133,230,220,105, 92, 41, 55, 46,245, 40,244,102,143, 54,
+            65, 25, 63,161,  1,216, 80, 73,209, 76,132,187,208, 89, 18,169,
+            200,196,135,130,116,188,159, 86,164,100,109,198,173,186,  3, 64,
+            52,217,226,250,124,123,  5,202, 38,147,118,126,255, 82, 85,212,
+            207,206, 59,227, 47, 16, 58, 17,182,189, 28, 42,223,183,170,213,
+            119,248,152,  2, 44,154,163, 70,221,153,101,155,167, 43,172,  9,
+            129, 22, 39,253, 19, 98,108,110, 79,113,224,232,178,185,112,104,
+            218,246, 97,228,251, 34,242,193,238,210,144, 12,191,179,162,241,
+            81, 51,145,235,249, 14,239,107, 49,192,214, 31,181,199,106,157,
+            184, 84,204,176,115,121, 50, 45,127,  4,150,254,138,236,205, 93,
+            222,114, 67, 29, 24, 72,243,141,128,195, 78, 66,215, 61,156,180
+        };
+
+        const int permutationCount = 255;
+
+        private static Vector3[] directions = {
+            new Vector3( 1f, 1f, 0f),
+            new Vector3(-1f, 1f, 0f),
+            new Vector3( 1f,-1f, 0f),
+            new Vector3(-1f,-1f, 0f),
+            new Vector3( 1f, 0f, 1f),
+            new Vector3(-1f, 0f, 1f),
+            new Vector3( 1f, 0f,-1f),
+            new Vector3(-1f, 0f,-1f),
+            new Vector3( 0f, 1f, 1f),
+            new Vector3( 0f,-1f, 1f),
+            new Vector3( 0f, 1f,-1f),
+            new Vector3( 0f,-1f,-1f),
+
+            new Vector3( 1f, 1f, 0f),
+            new Vector3(-1f, 1f, 0f),
+            new Vector3( 0f,-1f, 1f),
+            new Vector3( 0f,-1f,-1f)
+        };
+
+        private const int directionCount = 15;
+
+        private static float scalar(Vector3 a, Vector3 b)
+        {
+            return a.x * b.x + a.y * b.y + a.z * b.z;
+        }
+
+        private static float smoothDistance(float d)
+        {
+            return d * d * d * (d * (d * 6f - 15f) + 10f);
+        }
+        public static float get3DPerlinNoise(Vector3 point, float frequency)
+        {
+            point *= frequency;
+
+            int flooredPointX0 = Mathf.FloorToInt(point.x);
+            int flooredPointY0 = Mathf.FloorToInt(point.y);
+            int flooredPointZ0 = Mathf.FloorToInt(point.z);
+
+            float distanceX0 = point.x - flooredPointX0;
+            float distanceY0 = point.y - flooredPointY0;
+            float distanceZ0 = point.z - flooredPointZ0;
+
+            float distanceX1 = distanceX0 - 1f;
+            float distanceY1 = distanceY0 - 1f;
+            float distanceZ1 = distanceZ0 - 1f;
+
+            flooredPointX0 &= permutationCount;
+            flooredPointY0 &= permutationCount;
+            flooredPointZ0 &= permutationCount;
+
+            int flooredPointX1 = flooredPointX0 + 1;
+            int flooredPointY1 = flooredPointY0 + 1;
+            int flooredPointZ1 = flooredPointZ0 + 1;
+
+            int permutationX0 = permutation[flooredPointX0];
+            int permutationX1 = permutation[flooredPointX1];
+
+            int permutationY00 = permutation[permutationX0 + flooredPointY0];
+            int permutationY10 = permutation[permutationX1 + flooredPointY0];
+            int permutationY01 = permutation[permutationX0 + flooredPointY1];
+            int permutationY11 = permutation[permutationX1 + flooredPointY1];
+            /*
+                    int permutationZ000 = permutation[permutationY00 + flooredPointZ0];
+                    int permutationZ100 = permutation[permutationY10 + flooredPointZ0];
+                    int permutationZ010 = permutation[permutationY01 + flooredPointZ0];
+                    int permutationZ110 = permutation[permutationY11 + flooredPointZ0];
+                    int permutationZ001 = permutation[permutationY00 + flooredPointZ1];
+                    int permutationZ101 = permutation[permutationY01 + flooredPointZ1];
+                    int permutationZ011 = permutation[permutationY10 + flooredPointZ1];
+                    int permutationZ111 = permutation[permutationY11 + flooredPointZ1];
+            */
+            Vector3 direction000 = directions[permutation[permutationY00 + flooredPointZ0] & directionCount];
+            Vector3 direction100 = directions[permutation[permutationY10 + flooredPointZ0] & directionCount];
+            Vector3 direction010 = directions[permutation[permutationY01 + flooredPointZ0] & directionCount];
+            Vector3 direction110 = directions[permutation[permutationY11 + flooredPointZ0] & directionCount];
+            Vector3 direction001 = directions[permutation[permutationY00 + flooredPointZ1] & directionCount];
+            Vector3 direction101 = directions[permutation[permutationY10 + flooredPointZ1] & directionCount];
+            Vector3 direction011 = directions[permutation[permutationY01 + flooredPointZ1] & directionCount];
+            Vector3 direction111 = directions[permutation[permutationY11 + flooredPointZ1] & directionCount];
+
+            /*
+                    Vector3 direction000 = directions[permutationZ000 & directionCount];
+                    Vector3 direction100 = directions[permutationZ100 & directionCount];
+                    Vector3 direction010 = directions[permutationZ010 & directionCount];
+                    Vector3 direction110 = directions[permutationZ110 & directionCount];
+                    Vector3 direction001 = directions[permutationZ001 & directionCount];
+                    Vector3 direction101 = directions[permutationZ101 & directionCount];
+                    Vector3 direction011 = directions[permutationZ011 & directionCount];
+                    Vector3 direction111 = directions[permutationZ111 & directionCount];
+            */
+
+            float value000 = scalar(direction000, new Vector3(distanceX0, distanceY0, distanceZ0));
+            float value100 = scalar(direction100, new Vector3(distanceX1, distanceY0, distanceZ0));
+            float value010 = scalar(direction010, new Vector3(distanceX0, distanceY1, distanceZ0));
+            float value110 = scalar(direction110, new Vector3(distanceX1, distanceY1, distanceZ0));
+            float value001 = scalar(direction001, new Vector3(distanceX0, distanceY0, distanceZ1));
+            float value101 = scalar(direction101, new Vector3(distanceX1, distanceY0, distanceZ1));
+            float value011 = scalar(direction011, new Vector3(distanceX0, distanceY1, distanceZ1));
+            float value111 = scalar(direction111, new Vector3(distanceX1, distanceY1, distanceZ1));
+
+            float smoothDistanceX = smoothDistance(distanceX0);
+            float smoothDistanceY = smoothDistance(distanceY0);
+            float smoothDistanceZ = smoothDistance(distanceZ0);
+
+            return Mathf.Lerp(
+                Mathf.Lerp(Mathf.Lerp(value000, value100, smoothDistanceX), Mathf.Lerp(value010, value110, smoothDistanceX), smoothDistanceY),
+                Mathf.Lerp(Mathf.Lerp(value001, value101, smoothDistanceX), Mathf.Lerp(value011, value111, smoothDistanceX), smoothDistanceY),
+                smoothDistanceZ);
+        }
+    }
+}

+ 11 - 0
Runtime/PerlinNoise3D.cs.meta

@@ -0,0 +1,11 @@
+fileFormatVersion: 2
+guid: 57a18d642f9b4fc45a6cd58530bf7a80
+MonoImporter:
+  externalObjects: {}
+  serializedVersion: 2
+  defaultReferences: []
+  executionOrder: 0
+  icon: {instanceID: 0}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 99 - 0
Runtime/PerlinNoise3DGizmo.cs

@@ -0,0 +1,99 @@
+using System.Collections;
+using System.Collections.Generic;
+using UnityEngine;
+using UnityEditor;
+
+namespace KairoEngine.NoiseUtilities
+{
+    public class PerlinNoise3DGizmo : MonoBehaviour
+    {
+        public bool cubeBoundries = false;
+        public int size = 10;
+        public int height = 20;
+        public int width = 20;
+        public int depth = 20;
+
+        public float frequency = 1.01f;
+        private Vector3[] points;
+
+        void Start()
+        {
+            InstantiatePoints();
+        }
+
+        private void FixedUpdate()
+        {
+            UpdateMesh();
+        }
+        void UpdateMesh()
+        {
+            if (cubeBoundries)
+            {
+                height = size;
+                width = size;
+                depth = size;
+            }
+            InstantiatePoints();
+        }
+
+        void InstantiatePoints()
+        {
+            points = new Vector3[height * width * depth];
+
+            for (int z = 0, i = 0; z < depth; z++)
+            {
+                for (int y = 0; y < height; y++)
+                {
+                    for (int x = 0; x < width; x++)
+                    {
+                        points[i] = new Vector3(x, y, z);
+                        i++;
+                    }
+                }
+            }
+        }
+
+        private void OnDrawGizmos()
+        {
+            if (points != null)
+            {
+                for (int i = 0; i < points.Length; i++)
+                {
+
+                    float sample = PerlinNoise3D.get3DPerlinNoise(points[i], frequency);
+
+                    sample = (sample + 1f) / 2f;
+                    Gizmos.color = new Color(sample, sample, sample, 1);
+
+                    Gizmos.DrawSphere(points[i], 0.3f);
+                }
+            }
+        }
+
+        [CustomEditor(typeof(PerlinNoise3DGizmo))]
+        public class PerlinNoise3DGizmoEditor : Editor
+        {
+            override public void OnInspectorGUI()
+            {
+                var myScript = target as PerlinNoise3DGizmo;
+
+                myScript.cubeBoundries = GUILayout.Toggle(myScript.cubeBoundries, "Enable Box Size:");
+
+                if (!myScript.cubeBoundries)
+                {
+                    myScript.depth = EditorGUILayout.IntSlider("Depth:", myScript.depth, 1, 30);
+                    myScript.height = EditorGUILayout.IntSlider("Heigth:", myScript.height, 1, 30);
+                    myScript.width = EditorGUILayout.IntSlider("Width:", myScript.width, 1, 30);
+                }
+                else
+                {
+                    myScript.size = EditorGUILayout.IntSlider("Box Size:", myScript.depth, 1, 30);
+                }
+                myScript.frequency = EditorGUILayout.FloatField("Frequency:", myScript.frequency);
+
+
+            }
+        }
+
+    }
+}

+ 11 - 0
Runtime/PerlinNoise3DGizmo.cs.meta

@@ -0,0 +1,11 @@
+fileFormatVersion: 2
+guid: 2bb50982762dc4846a96c4ab6f8c1df3
+MonoImporter:
+  externalObjects: {}
+  serializedVersion: 2
+  defaultReferences: []
+  executionOrder: 0
+  icon: {instanceID: 0}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: