/// <summary> /// Returns a grid point at the given point. /// Assumes the point is within the bounds of the grid. /// </summary> /// <param name="point"></param> /// <param name="result"></param> public void GridPointAtUnchecked(Vec3d point, GridPoint3d result) { point = ToGridSpace(point); result.SetWeights( SlurMath.Fract(point.X, out int i0), SlurMath.Fract(point.Y, out int j0), SlurMath.Fract(point.Z, out int k0) ); j0 *= _nx; k0 *= _nxy; int i1 = i0 + 1; int j1 = j0 + _nx; int k1 = k0 + _nxy; var corners = result.Corners; corners[0] = i0 + j0 + k0; corners[1] = i1 + j0 + k0; corners[2] = i0 + j1 + k0; corners[3] = i1 + j1 + k0; corners[4] = i0 + j0 + k1; corners[5] = i1 + j0 + k1; corners[6] = i0 + j1 + k1; corners[7] = i1 + j1 + k1; }
/// <summary> /// Returns the noise value at the given coordinates. /// </summary> /// <param name="x"></param> /// <param name="y"></param> /// <returns></returns> public static double ValueAt(double x, double y) { // separate whole and fractional components x = SlurMath.Fract(x, out int i); y = SlurMath.Fract(y, out int j); // wrap to perm table i &= 255; j &= 255; // calculate noise contributions from each corner double n00 = GradDot(ToIndex(i, j), x, y); double n10 = GradDot(ToIndex(i + 1, j), x - 1.0, y); double n01 = GradDot(ToIndex(i, j + 1), x, y - 1.0); double n11 = GradDot(ToIndex(i + 1, j + 1), x - 1.0, y - 1.0); // eased values for x and y x = SlurMath.HermiteC2(x); y = SlurMath.HermiteC2(y); // bilinear interpolation return(SlurMath.Lerp( SlurMath.Lerp(n00, n10, x), SlurMath.Lerp(n01, n11, x), y)); }
/// <inheritdoc /> protected sealed override double ValueAtLinear(Vec3d point) { point = ToGridSpace(point); double u = SlurMath.Fract(point.X, out int i0); double v = SlurMath.Fract(point.Y, out int j0); double w = SlurMath.Fract(point.Z, out int k0); int i1 = WrapX(i0 + 1); int j1 = WrapY(j0 + 1) * CountX; int k1 = WrapZ(k0 + 1) * CountXY; i0 = WrapX(i0); j0 = WrapY(j0) * CountX; k0 = WrapZ(k0) * CountXY; var vals = Values; return(SlurMath.Lerp( SlurMath.Lerp( SlurMath.Lerp(vals[i0 + j0 + k0], vals[i1 + j0 + k0], u), SlurMath.Lerp(vals[i0 + j1 + k0], vals[i1 + j1 + k0], u), v), SlurMath.Lerp( SlurMath.Lerp(vals[i0 + j0 + k1], vals[i1 + j0 + k1], u), SlurMath.Lerp(vals[i0 + j1 + k1], vals[i1 + j1 + k1], u), v), w)); }
/// <summary> /// Returns a grid point at the given point. /// </summary> /// <param name="point"></param> /// <param name="result"></param> public void GridPointAt(Vec3d point, GridPoint3d result) { point = ToGridSpace(point); result.SetWeights( SlurMath.Fract(point.X, out int i0), SlurMath.Fract(point.Y, out int j0), SlurMath.Fract(point.Z, out int k0) ); int i1 = WrapX(i0 + 1); int j1 = WrapY(j0 + 1) * _nx; int k1 = WrapZ(k0 + 1) * _nxy; i0 = WrapX(i0); j0 = WrapY(j0) * _nx; k0 = WrapZ(k0) * _nxy; var corners = result.Corners; corners[0] = i0 + j0 + k0; corners[1] = i1 + j0 + k0; corners[2] = i0 + j1 + k0; corners[3] = i1 + j1 + k0; corners[4] = i0 + j0 + k1; corners[5] = i1 + j0 + k1; corners[6] = i0 + j1 + k1; corners[7] = i1 + j1 + k1; }
/// <summary> /// Returns the noise value at the given coordinates /// </summary> /// <param name="x"></param> /// <param name="y"></param> /// <param name="z"></param> /// <returns></returns> public static double ValueAt(double x, double y, double z) { // separate whole and fractional components x = SlurMath.Fract(x, out int i); y = SlurMath.Fract(y, out int j); z = SlurMath.Fract(z, out int k); // calculate noise contributions from each corner double n000 = GradDot(ToIndex(i, j, k), x, y, z); double n100 = GradDot(ToIndex(i + 1, j, k), x - 1.0, y, z); double n010 = GradDot(ToIndex(i, j + 1, k), x, y - 1.0, z); double n110 = GradDot(ToIndex(i + 1, j + 1, k), x - 1.0, y - 1.0, z); double n001 = GradDot(ToIndex(i, j, k + 1), x, y, z - 1.0); double n101 = GradDot(ToIndex(i + 1, j, k + 1), x - 1.0, y, z - 1.0); double n011 = GradDot(ToIndex(i, j + 1, k + 1), x, y - 1.0, z - 1.0); double n111 = GradDot(ToIndex(i + 1, j + 1, k + 1), x - 1.0, y - 1.0, z - 1.0); // eased values for each dimension x = SlurMath.HermiteC2(x); y = SlurMath.HermiteC2(y); z = SlurMath.HermiteC2(z); // trilinear interpolation return(SlurMath.Lerp( SlurMath.Lerp( SlurMath.Lerp(n000, n100, x), SlurMath.Lerp(n010, n110, x), y), SlurMath.Lerp( SlurMath.Lerp(n001, n101, x), SlurMath.Lerp(n011, n111, x), y), z)); }
/// <inheritdoc /> protected sealed override double ValueAtLinearUnsafe(Vec3d point) { point = ToGridSpace(point); double u = SlurMath.Fract(point.X, out int i0); double v = SlurMath.Fract(point.Y, out int j0); double w = SlurMath.Fract(point.Z, out int k0); j0 *= CountX; k0 *= CountXY; int i1 = i0 + 1; int j1 = j0 + CountX; int k1 = k0 + CountXY; var vals = Values; return(SlurMath.Lerp( SlurMath.Lerp( SlurMath.Lerp(vals[i0 + j0 + k0], vals[i1 + j0 + k0], u), SlurMath.Lerp(vals[i0 + j1 + k0], vals[i1 + j1 + k0], u), v), SlurMath.Lerp( SlurMath.Lerp(vals[i0 + j0 + k1], vals[i1 + j0 + k1], u), SlurMath.Lerp(vals[i0 + j1 + k1], vals[i1 + j1 + k1], u), v), w)); }
/// <inheritdoc/> /// <summary> /// /// </summary> /// <param name="point"></param> /// <returns></returns> protected sealed override double ValueAtLinearUnchecked(Vec2d point) { point = ToGridSpace(point); double u = SlurMath.Fract(point.X, out int i0); double v = SlurMath.Fract(point.Y, out int j0); j0 *= CountX; int i1 = i0 + 1; int j1 = j0 + CountX; var vals = Values; return(SlurMath.Lerp( SlurMath.Lerp(vals[i0 + j0], vals[i1 + j0], u), SlurMath.Lerp(vals[i0 + j1], vals[i1 + j1], u), v)); }
/// <inheritdoc /> protected sealed override Vec2d ValueAtLinear(Vec2d point) { point = ToGridSpace(point); double u = SlurMath.Fract(point.X, out int i0); double v = SlurMath.Fract(point.Y, out int j0); int i1 = WrapX(i0 + 1); int j1 = WrapY(j0 + 1) * CountX; i0 = WrapX(i0); j0 = WrapY(j0) * CountX; var vals = Values; return(Vec2d.Lerp( Vec2d.Lerp(vals[i0 + j0], vals[i1 + j0], u), Vec2d.Lerp(vals[i0 + j1], vals[i1 + j1], u), v)); }
/// <summary> /// Returns a grid point at the given point. /// Assumes the point is within the bounds of the grid. /// </summary> /// <param name="point"></param> /// <param name="result"></param> public void GridPointAtUnsafe(Vec2d point, GridPoint2d result) { point = ToGridSpace(point); result.SetWeights( SlurMath.Fract(point.X, out int i0), SlurMath.Fract(point.Y, out int j0) ); j0 *= _nx; int i1 = i0 + 1; int j1 = j0 + _nx; var corners = result.Corners; corners[0] = i0 + j0; corners[1] = i1 + j0; corners[2] = i0 + j1; corners[3] = i1 + j1; }
/// <summary> /// TODO move into SlurUnity /// </summary> /// <param name="colors"></param> /// <param name="factor"></param> /// <returns></returns> public static Color Lerp(IReadOnlyList <Color> colors, float factor) { int last = colors.Count - 1; int i; // object SlurMathf = null; factor = SlurMath.Fract(factor * last, out i); //Fract(factor * last, out i); if (i < 0) { return(colors[0]); } else if (i >= last) { return(colors[last]); } return(Color.LerpUnclamped(colors[i], colors[i + 1], factor)); }
/// <summary> /// Returns a grid point at the given point. /// </summary> /// <param name="point"></param> /// <param name="result"></param> public void GridPointAt(Vec2d point, GridPoint2d result) { point = ToGridSpace(point); result.SetWeights( SlurMath.Fract(point.X, out int i0), SlurMath.Fract(point.Y, out int j0) ); int i1 = WrapX(i0 + 1); int j1 = WrapY(j0 + 1) * _nx; i0 = WrapX(i0); j0 = WrapY(j0) * _nx; var corners = result.Corners; corners[0] = i0 + j0; corners[1] = i1 + j0; corners[2] = i0 + j1; corners[3] = i1 + j1; }