//given a function f: float -> float, this method computes fills in all the y values of each Vector3 in the vectors array by doing y=f(x) public static Vector3[] fillYValues(Vector3[] vectors, InterpolateFunction func) { for (int i = 0; i < vectors.Length; i++) { vectors[i].y = func(vectors[i].x); } return(vectors); }
public static T SmoothSampleArray <T>(T[] arr, float t, InterpolateFunction <T> interpolator) { float smoothIdx = t * (arr.Length - 1); int leftIdx = Mathf.FloorToInt(smoothIdx); int rightIdx = (int)Mathf.Min(leftIdx + 1, arr.Length - 1);//Mathf.CeilToInt(t * (arr.Length - 1)); T leftElement = arr[leftIdx]; T rightElement = arr[rightIdx]; float mixAmt = smoothIdx - leftIdx; return(interpolator(leftElement, rightElement, mixAmt)); }
// Start is called before the first frame update public void ManagedStart() { InterpolateFunction baseTerrainGeneration = (x) => { if (x < -7.5f) { return(-2f); } else if (-7.5f <= x && x < -5.5) { return(1.5f * (x + 1.5f) + 7f); } else if (-5.5f <= x && x < 0f) { return(-1.5f * (x + 1.5f) - 5); } else if (0f <= x && x < 5.5f) { return(1.5f * (x - 1.5f) - 5f); } else if (5.5f <= x && x < 7.5f) { return(-1.5f * (x - 1.5f) + 7f); } else { return(-2f); } }; Vector3[] baseTerrain = PerlinNoise.fillYValues(PerlinNoise.makeEmpty(-15, 15), baseTerrainGeneration); InterpolateFunction fifthOrder = (x) => (float)(6 * Math.Pow(x, 5) - 15 * Math.Pow(x, 4) + 10 * Math.Pow(x, 3)); Vector3[] iter2 = PerlinNoise.perlinNoise(-15, 0.5f, 0.25f, 60, fifthOrder); Vector3[] iter3 = PerlinNoise.perlinNoise(-15, 0.25f, 0.125f, 120, fifthOrder); Vector3[] extraPerlinMountain = PerlinNoise.vec3ArrayConcat(PerlinNoise.makeEmpty(-15, -7.5f), PerlinNoise.perlinNoiseSmoothStartEnd(-7.5f, 0.5f, 1, 30, fifthOrder), PerlinNoise.makeEmpty(7.5f, 15f)); Vector3[] terrainLine = PerlinNoise.vec3ArrayYSum(baseTerrain, iter2, iter3, extraPerlinMountain); translateDown(terrainLine, 1f); graph(terrainLine); }
//same as the perlin noise function, but with initial point and final point (0,0). public static Vector3[] perlinNoiseSmoothStartEnd(float start, float freq, float max, int numOfSegs, InterpolateFunction func) { List <Vector3> pointsOfLine = new List <Vector3>(); Vector3 segStart = new Vector3(start, 0f, 0f); Vector3 segEnd; Vector3[] segmentPoints; for (int i = 0; i < numOfSegs - 1; i++) { segEnd = new Vector3(start + (i + 1) * freq, (float)random.NextDouble() * max, 0); segmentPoints = interpolate(segStart, segEnd, func); pointsOfLine.AddRange(segmentPoints); segStart = segEnd; } segEnd = new Vector3(start + numOfSegs * freq, 0, 0); segmentPoints = interpolate(segStart, segEnd, func); pointsOfLine.AddRange(segmentPoints); return(pointsOfLine.ToArray()); }
//Given a start point, an end point, and a function for interpolation, returns a curve that starts from the start point and ends at the end point public static Vector3[] interpolate(Vector3 start, Vector3 end, InterpolateFunction func) { InterpolateFunction adjusted = (x) => (end.y - start.y) * func((x - start.x) / (end.x - start.x)) + start.y; return(fillYValues(makeEmpty(start.x, end.x), adjusted)); }