示例#1
0
文件: Noise.cpp 项目: Clever-Boy/XLE
    // 2D simplex noise
    float SimplexNoise(Float2 input)
    {
        float xin = input[0], yin = input[1];
        InitPerm();

        float n0, n1, n2; // Noise contributions from the three corners
        // Skew the input space to determine which simplex cell we're in
        float s = (xin+yin)*F2; // Hairy factor for 2D
        int i = fastfloor(xin+s);
        int j = fastfloor(yin+s);

        float t = (i+j)*G2;
        float X0 = i-t; // Unskew the cell origin back to (x,y) space
        float Y0 = j-t;
        float x0 = xin-X0; // The x,y distances from the cell origin
        float y0 = yin-Y0;
        // For the 2D case, the simplex shape is an equilateral triangle.
        // Determine which simplex we are in.
        int i1, j1; // Offsets for second (middle) corner of simplex in (i,j) coords
        if(x0>y0)   { i1=1; j1=0; } // lower triangle, XY order: (0,0)->(1,0)->(1,1)
        else        { i1=0; j1=1; }      // upper triangle, YX order: (0,0)->(0,1)->(1,1)

        // A step of (1,0) in (i,j) means a step of (1-c,-c) in (x,y), and
        // a step of (0,1) in (i,j) means a step of (-c,1-c) in (x,y), where
        // c = (3-sqrt(3))/6
        float x1 = x0 - i1 + G2; // Offsets for middle corner in (x,y) unskewed coords
        float y1 = y0 - j1 + G2;
        float x2 = x0 - 1.f + 2.f * G2; // Offsets for last corner in (x,y) unskewed coords
        float y2 = y0 - 1.f + 2.f * G2;

        // Work out the hashed gradient indices of the three simplex corners
        int ii = i & 255;
        int jj = j & 255;
        int gi0 = permMod12[ii+perm[jj]];
        int gi1 = permMod12[ii+i1+perm[jj+j1]];
        int gi2 = permMod12[ii+1+perm[jj+1]];

        // Calculate the contribution from the three corners
        float t0 = 0.5f - x0*x0-y0*y0;
        if(t0<0) n0 = 0.f;
        else {
          t0 *= t0;
          n0 = t0 * t0 * dot(grad3[gi0], x0, y0);  // (x,y) of grad3 used for 2D gradient
        }
        float t1 = 0.5f - x1*x1-y1*y1;
        if(t1<0) n1 = 0.f;
        else {
          t1 *= t1;
          n1 = t1 * t1 * dot(grad3[gi1], x1, y1);
        }
        float t2 = 0.5f - x2*x2-y2*y2;
        if(t2<0) n2 = 0.f;
        else {
          t2 *= t2;
          n2 = t2 * t2 * dot(grad3[gi2], x2, y2);
        }
        // Add contributions from each corner to get the final noise value.
        // The result is scaled to return values in the interval [-1,1].
        return 70.f * (n0 + n1 + n2);
    }
示例#2
0
/* Initialize the filling state. */
static int
tile_fill_init(tile_fill_state_t * ptfs, const gx_device_color * pdevc,
               gx_device * dev, bool set_mask_phase)
{
    gx_color_tile *m_tile = pdevc->mask.m_tile;
    int px, py;

    ptfs->pdevc = pdevc;
    if (m_tile == 0) {          /* no clipping */
        ptfs->pcdev = dev;
        ptfs->phase = pdevc->phase;
        return 0;
    }
    ptfs->pcdev = (gx_device *) & ptfs->cdev;
    ptfs->tmask = &m_tile->tmask;
    ptfs->phase.x = pdevc->mask.m_phase.x;
    ptfs->phase.y = pdevc->mask.m_phase.y;
    /*
     * For non-simple tiles, the phase will be reset on each pass of the
     * tile_by_steps loop, but for simple tiles, we must set it now.
     */
    if (set_mask_phase && m_tile->is_simple) {
        px = imod(-(int)fastfloor(m_tile->step_matrix.tx - ptfs->phase.x + 0.5),
                  m_tile->tmask.rep_width);
        py = imod(-(int)fastfloor(m_tile->step_matrix.ty - ptfs->phase.y + 0.5),
                  m_tile->tmask.rep_height);
    } else
        px = py = 0;
    return tile_clip_initialize(&ptfs->cdev, ptfs->tmask, dev, px, py, NULL);
}
示例#3
0
// -------------------------------------------------------------------------- //
//
void Test_Mathutils::testFastFloor()
{
    double value = -9998823.1;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = -23.1;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = -2.99999;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = -1.876543;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = -0.00000000000000003;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = 0.0;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = 0.1345;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = 2345.76543;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
    value = 3445676.66543;
    CPPUNIT_ASSERT_DOUBLES_EQUAL( std::floor(value),
                                  fastfloor(value), EPS);
}
示例#4
0
int
gx_trans_pattern_fill_rect(int xmin, int ymin, int xmax, int ymax, gx_color_tile *ptile,
                               gx_pattern_trans_t *fill_trans_buffer, 
                               gs_int_point phase)
{

    tile_fill_trans_state_t state;
    int code;

    if (ptile == 0)             /* null pattern */
        return 0;

    /* Fit fill */
    if ( (xmin | ymin) < 0 ) {
        if ( xmin < 0 )
	    xmin = 0;
        if ( ymin < 0 )
            ymin = 0;
    }

    state.phase.x = phase.x;
    state.phase.y = phase.y;

    if (ptile->is_simple && ptile->cdev == NULL) {
        /* A simple case.  Tile is not clist and simple. */
        int px =
            imod(-(int)fastfloor(ptile->step_matrix.tx - phase.x + 0.5),
                  ptile->ttrans->width);
        int py =
            imod(-(int)fastfloor(ptile->step_matrix.ty - phase.y + 0.5),
                 ptile->ttrans->height);
        
        tile_rect_trans_simple(xmin, ymin, xmax, ymax, px, py, ptile,
            fill_trans_buffer);
    } else {
        if (ptile->cdev == NULL) {
            /* No clist for the pattern, but a complex case
               This portion transforms the bounding box by the step matrix
               and does partial rect fills with tiles that fall into this
               transformed bbox */
            code = tile_by_steps_trans(&state, xmin, ymin, xmax-xmin, ymax-ymin,
                fill_trans_buffer, ptile);
        } else {
            /* clist for the tile.  Currently this is not implemented
               for the case when the tile has transparency.  This is
               on the to do list.  Right now, all tiles with transparency
               are rendered into the pattern cache or into the clist
               */
            return_error(gs_error_unregistered);
        }
    }
return(0);
}
示例#5
0
文件: simplex.c 项目: thorlund/demo
float simplexRawNoise2( const float x, const float y ) {
  float n0, n1, n2;

  float F2 = 0.5 * (sqrtf(3.0) - 1.0);
  float s = (x + y) * F2;
  int i = fastfloor( x + s );
  int j = fastfloor( y + s );

  float G2 = (3.0 - sqrtf(3.0)) / 6.0;
  float t = (i + j) * G2;
  float X0 = i-t;
  float Y0 = j-t;
  float x0 = x-X0;
  float y0 = y-Y0;

  int i1, j1;
  if(x0>y0) {i1=1; j1=0;}
  else {i1=0; j1=1;}

  float x1 = x0 - i1 + G2;
  float y1 = y0 - j1 + G2;
  float x2 = x0 - 1.0 + 2.0 * G2;
  float y2 = y0 - 1.0 + 2.0 * G2;

  int ii = i & 255;
  int jj = j & 255;
  int gi0 = perm[ii+perm[jj]] % 12;
  int gi1 = perm[ii+i1+perm[jj+j1]] % 12;
  int gi2 = perm[ii+1+perm[jj+1]] % 12;

  float t0 = 0.5 - x0*x0-y0*y0;
  if(t0<0) n0 = 0.0;
  else {
  t0 *= t0;
  n0 = t0 * t0 * dot2(grad3[gi0], x0, y0);
  }

  float t1 = 0.5 - x1*x1-y1*y1;
  if(t1<0) n1 = 0.0;
  else {
  t1 *= t1;
  n1 = t1 * t1 * dot2(grad3[gi1], x1, y1);
  }

  float t2 = 0.5 - x2*x2-y2*y2;
  if(t2<0) n2 = 0.0;
  else {
  t2 *= t2;
  n2 = t2 * t2 * dot2(grad3[gi2], x2, y2);
  }

  return 70.0 * (n0 + n1 + n2);
}
示例#6
0
gl_pos_t compute_stratum_height(stratum *st, global_pos *glpos) {
  // static variables:
  static stratum *pr_st = NULL;
  static global_chunk_pos pr_glcpos = { .x = -1, .y = -1, .z = -1 };
  // low- and high-frequency distortion:
  static float lfdx = 0; static float lfdy = 0;
  // low- and high-frequency noise:
  static float lfn = 0;
  // base thickness:
  static float base = 0;

  // normal variables:
  float fx;
  float fy;
  global_chunk_pos glcpos;

  // compute our chunk position:
  glpos__glcpos(glpos, &glcpos);

  if (pr_st != st || pr_glcpos.x != glcpos.x || pr_glcpos.y != glcpos.y) {
    // need to recompute low-frequency info:
    fx = (float) (glpos->x);
    fy = (float) (glpos->y);
    stratum_lf_distortion(st, fx, fy, &lfdx, &lfdy);
    stratum_lf_noise(st, fx+lfdx, fy+lfdy, &lfn);
    stratum_base_thickness(st, fx+lfdx, fy+lfdy, &base);
  }
  // set static variables:
  copy_glcpos(&glcpos, &pr_glcpos);
  pr_st = st;
  return (gl_pos_t) fastfloor(base + lfn);
}
示例#7
0
/**
* 1D Perlin simplex noise
*
*  Takes around 74ns on an AMD APU.
*
* @param[in] x float coordinate
*
* @return Noise value in the range[-1; 1], value of 0 on all integer coordinates.
*/
float SimplexNoise::noise(float x) {
	float n0, n1;   // Noise contributions from the two "corners"

					// No need to skew the input space in 1D

					// Corners coordinates (nearest integer values):
	int32_t i0 = fastfloor(x);
	int32_t i1 = i0 + 1;
	// Distances to corners (between 0 and 1):
	float x0 = x - i0;
	float x1 = x0 - 1.0f;

	// Calculate the contribution from the first corner
	float t0 = 1.0f - x0*x0;
	//  if(t0 < 0.0f) t0 = 0.0f; // not possible
	t0 *= t0;
	n0 = t0 * t0 * grad(hash(i0), x0);

	// Calculate the contribution from the second corner
	float t1 = 1.0f - x1*x1;
	//  if(t1 < 0.0f) t1 = 0.0f; // not possible
	t1 *= t1;
	n1 = t1 * t1 * grad(hash(i1), x1);

	// The maximum value of this noise is 8*(3/4)^4 = 2.53125
	// A factor of 0.395 scales to fit exactly within [-1,1]
	return 0.395f * (n0 + n1);
}
// ----------------------------------------------------------------------------
//
int ScalarDistributionData::get_bin(const double value) const {

    if (value < lowest_)
    {
        return 0;
    }

    if (highest_ < value)
    {
        return nbins_ - 1;
    }

    return static_cast<int>(fastfloor(((value-lowest_)*one_over_binsize_)));
}
// Simplex noise code:
// From an original algorythm by Ken Perlin.
// Returns a value in the range of about [-0.347 .. 0.347]
float LEDStripSimplexNoise::SimplexNoise(float x, float y, float z)
{
    // Skew input space to relative coordinate in simplex cell
    s = (x + y + z) * onethird;
    i = fastfloor(x+s);
    j = fastfloor(y+s);
    k = fastfloor(z+s);

    // Unskew cell origin back to (x, y , z) space
    s = (i + j + k) * onesixth;
    u = x - i + s;
    v = y - j + s;
    w = z - k + s;;

    A[0] = A[1] = A[2] = 0;

    // For 3D case, the simplex shape is a slightly irregular tetrahedron.
    // Determine which simplex we're in
int hi = u >= w ? u >= v ? 0 : 1 : v >= w ? 1 : 2;
int lo = u < w ? u < v ? 0 : 1 : v < w ? 1 : 2;

    return k_fn(hi) + k_fn(3 - hi - lo) + k_fn(lo) + k_fn(0);
}
示例#10
0
// 4D raw Simplex noise
double raw_noise_4d( const double x, const double y, const double z, const double w ) {
    // The skewing and unskewing factors are hairy again for the 4D case
    double F4 = (sqrtf(5.0)-1.0)/4.0;
    double G4 = (5.0-sqrtf(5.0))/20.0;
    double n0, n1, n2, n3, n4; // Noise contributions from the five corners

    // Skew the (x,y,z,w) space to determine which cell of 24 simplices we're in
    double s = (x + y + z + w) * F4; // Factor for 4D skewing
    int i = fastfloor(x + s);
    int j = fastfloor(y + s);
    int k = fastfloor(z + s);
    int l = fastfloor(w + s);
    double t = (i + j + k + l) * G4; // Factor for 4D unskewing
    double X0 = i - t; // Unskew the cell origin back to (x,y,z,w) space
    double Y0 = j - t;
    double Z0 = k - t;
    double W0 = l - t;

    double x0 = x - X0; // The x,y,z,w distances from the cell origin
    double y0 = y - Y0;
    double z0 = z - Z0;
    double w0 = w - W0;

    // For the 4D case, the simplex is a 4D shape I won't even try to describe.
    // To find out which of the 24 possible simplices we're in, we need to
    // determine the magnitude ordering of x0, y0, z0 and w0.
    // The method below is a good way of finding the ordering of x,y,z,w and
    // then find the correct traversal order for the simplex we're in.
    // First, six pair-wise comparisons are performed between each possible pair
    // of the four coordinates, and the results are used to add up binary bits
    // for an integer index.
    int c1 = (x0 > y0) ? 32 : 0;
    int c2 = (x0 > z0) ? 16 : 0;
    int c3 = (y0 > z0) ? 8 : 0;
    int c4 = (x0 > w0) ? 4 : 0;
    int c5 = (y0 > w0) ? 2 : 0;
    int c6 = (z0 > w0) ? 1 : 0;
    int c = c1 + c2 + c3 + c4 + c5 + c6;

    int i1, j1, k1, l1; // The integer offsets for the second simplex corner
    int i2, j2, k2, l2; // The integer offsets for the third simplex corner
    int i3, j3, k3, l3; // The integer offsets for the fourth simplex corner

    // simplex[c] is a 4-vector with the numbers 0, 1, 2 and 3 in some order.
    // Many values of c will never occur, since e.g. x>y>z>w makes x<z, y<w and x<w
    // impossible. Only the 24 indices which have non-zero entries make any sense.
    // We use a thresholding to set the coordinates in turn from the largest magnitude.
    // The number 3 in the "simplex" array is at the position of the largest coordinate.
    i1 = simplex[c][0]>=3 ? 1 : 0;
    j1 = simplex[c][1]>=3 ? 1 : 0;
    k1 = simplex[c][2]>=3 ? 1 : 0;
    l1 = simplex[c][3]>=3 ? 1 : 0;
    // The number 2 in the "simplex" array is at the second largest coordinate.
    i2 = simplex[c][0]>=2 ? 1 : 0;
    j2 = simplex[c][1]>=2 ? 1 : 0;
    k2 = simplex[c][2]>=2 ? 1 : 0;
    l2 = simplex[c][3]>=2 ? 1 : 0;
    // The number 1 in the "simplex" array is at the second smallest coordinate.
    i3 = simplex[c][0]>=1 ? 1 : 0;
    j3 = simplex[c][1]>=1 ? 1 : 0;
    k3 = simplex[c][2]>=1 ? 1 : 0;
    l3 = simplex[c][3]>=1 ? 1 : 0;
    // The fifth corner has all coordinate offsets = 1, so no need to look that up.

    double x1 = x0 - i1 + G4; // Offsets for second corner in (x,y,z,w) coords
    double y1 = y0 - j1 + G4;
    double z1 = z0 - k1 + G4;
    double w1 = w0 - l1 + G4;
    double x2 = x0 - i2 + 2.0*G4; // Offsets for third corner in (x,y,z,w) coords
    double y2 = y0 - j2 + 2.0*G4;
    double z2 = z0 - k2 + 2.0*G4;
    double w2 = w0 - l2 + 2.0*G4;
    double x3 = x0 - i3 + 3.0*G4; // Offsets for fourth corner in (x,y,z,w) coords
    double y3 = y0 - j3 + 3.0*G4;
    double z3 = z0 - k3 + 3.0*G4;
    double w3 = w0 - l3 + 3.0*G4;
    double x4 = x0 - 1.0 + 4.0*G4; // Offsets for last corner in (x,y,z,w) coords
    double y4 = y0 - 1.0 + 4.0*G4;
    double z4 = z0 - 1.0 + 4.0*G4;
    double w4 = w0 - 1.0 + 4.0*G4;

    // Work out the hashed gradient indices of the five simplex corners
    int ii = i & 255;
    int jj = j & 255;
    int kk = k & 255;
    int ll = l & 255;
    int gi0 = perm[ii+perm[jj+perm[kk+perm[ll]]]] % 32;
    int gi1 = perm[ii+i1+perm[jj+j1+perm[kk+k1+perm[ll+l1]]]] % 32;
    int gi2 = perm[ii+i2+perm[jj+j2+perm[kk+k2+perm[ll+l2]]]] % 32;
    int gi3 = perm[ii+i3+perm[jj+j3+perm[kk+k3+perm[ll+l3]]]] % 32;
    int gi4 = perm[ii+1+perm[jj+1+perm[kk+1+perm[ll+1]]]] % 32;

    // Calculate the contribution from the five corners
    double t0 = 0.6 - x0*x0 - y0*y0 - z0*z0 - w0*w0;
    if(t0<0) n0 = 0.0;
    else {
        t0 *= t0;
        n0 = t0 * t0 * dot(grad4[gi0], x0, y0, z0, w0);
    }

    double t1 = 0.6 - x1*x1 - y1*y1 - z1*z1 - w1*w1;
    if(t1<0) n1 = 0.0;
    else {
        t1 *= t1;
        n1 = t1 * t1 * dot(grad4[gi1], x1, y1, z1, w1);
    }

    double t2 = 0.6 - x2*x2 - y2*y2 - z2*z2 - w2*w2;
    if(t2<0) n2 = 0.0;
    else {
        t2 *= t2;
        n2 = t2 * t2 * dot(grad4[gi2], x2, y2, z2, w2);
    }

    double t3 = 0.6 - x3*x3 - y3*y3 - z3*z3 - w3*w3;
    if(t3<0) n3 = 0.0;
    else {
        t3 *= t3;
        n3 = t3 * t3 * dot(grad4[gi3], x3, y3, z3, w3);
    }

    double t4 = 0.6 - x4*x4 - y4*y4 - z4*z4 - w4*w4;
    if(t4<0) n4 = 0.0;
    else {
        t4 *= t4;
        n4 = t4 * t4 * dot(grad4[gi4], x4, y4, z4, w4);
    }

    // Sum up and scale the result to cover the range [-1,1]
    return 27.0 * (n0 + n1 + n2 + n3 + n4);
}
示例#11
0
// 2D raw Simplex noise
double raw_noise_2d( const double x, const double y ) {
    // Noise contributions from the three corners
    double n0, n1, n2;

    // Skew the input space to determine which simplex cell we're in
    double F2 = 0.5 * (sqrtf(3.0) - 1.0);
    // Hairy factor for 2D
    double s = (x + y) * F2;
    int i = fastfloor( x + s );
    int j = fastfloor( y + s );

    double G2 = (3.0 - sqrtf(3.0)) / 6.0;
    double t = (i + j) * G2;
    // Unskew the cell origin back to (x,y) space
    double X0 = i-t;
    double Y0 = j-t;
    // The x,y distances from the cell origin
    double x0 = x-X0;
    double y0 = y-Y0;

    // For the 2D case, the simplex shape is an equilateral triangle.
    // Determine which simplex we are in.
    int i1, j1; // Offsets for second (middle) corner of simplex in (i,j) coords
    if(x0>y0) {i1=1; j1=0;} // lower triangle, XY order: (0,0)->(1,0)->(1,1)
    else {i1=0; j1=1;} // upper triangle, YX order: (0,0)->(0,1)->(1,1)

    // A step of (1,0) in (i,j) means a step of (1-c,-c) in (x,y), and
    // a step of (0,1) in (i,j) means a step of (-c,1-c) in (x,y), where
    // c = (3-sqrt(3))/6
    double x1 = x0 - i1 + G2; // Offsets for middle corner in (x,y) unskewed coords
    double y1 = y0 - j1 + G2;
    double x2 = x0 - 1.0 + 2.0 * G2; // Offsets for last corner in (x,y) unskewed coords
    double y2 = y0 - 1.0 + 2.0 * G2;

    // Work out the hashed gradient indices of the three simplex corners
    int ii = i & 255;
    int jj = j & 255;
    int gi0 = perm[ii+perm[jj]] % 12;
    int gi1 = perm[ii+i1+perm[jj+j1]] % 12;
    int gi2 = perm[ii+1+perm[jj+1]] % 12;

    // Calculate the contribution from the three corners
    double t0 = 0.5 - x0*x0-y0*y0;
    if(t0<0) n0 = 0.0;
    else {
        t0 *= t0;
        n0 = t0 * t0 * dot(grad3[gi0], x0, y0); // (x,y) of grad3 used for 2D gradient
    }

    double t1 = 0.5 - x1*x1-y1*y1;
    if(t1<0) n1 = 0.0;
    else {
        t1 *= t1;
        n1 = t1 * t1 * dot(grad3[gi1], x1, y1);
    }

    double t2 = 0.5 - x2*x2-y2*y2;
    if(t2<0) n2 = 0.0;
    else {
        t2 *= t2;
        n2 = t2 * t2 * dot(grad3[gi2], x2, y2);
    }

    // Add contributions from each corner to get the final noise value.
    // The result is scaled to return values in the interval [-1,1].
    return 70.0 * (n0 + n1 + n2);
}
示例#12
0
double_t classic3::operator()(double_t x, double_t y, double_t z) const
{
	// Find unit grid cell containing point
	int32_t X = fastfloor(x);
	int32_t Y = fastfloor(y);
	int32_t Z = fastfloor(z);

	// Get relative xyz coordinates of point within that cell
	x = x - X;
	y = y - Y;
	z = z - Z;

	// Wrap the integer cells at 255 (smaller integer period can be introduced here)
	X = X & 255;
	Y = Y & 255;
	Z = Z & 255;

	// Calculate a set of eight hashed gradient indices
	int32_t gi000 = perm[X+perm[Y+perm[Z]]] % 12;
	int32_t gi001 = perm[X+perm[Y+perm[Z+1]]] % 12;
	int32_t gi010 = perm[X+perm[Y+1+perm[Z]]] % 12;
	int32_t gi011 = perm[X+perm[Y+1+perm[Z+1]]] % 12;
	int32_t gi100 = perm[X+1+perm[Y+perm[Z]]] % 12;
	int32_t gi101 = perm[X+1+perm[Y+perm[Z+1]]] % 12;
	int32_t gi110 = perm[X+1+perm[Y+1+perm[Z]]] % 12;
	int32_t gi111 = perm[X+1+perm[Y+1+perm[Z+1]]] % 12;
	// The gradients of each corner are now:
	// g000 = grad3[gi000];
	// g001 = grad3[gi001];
	// g010 = grad3[gi010];
	// g011 = grad3[gi011];
	// g100 = grad3[gi100];
	// g101 = grad3[gi101];
	// g110 = grad3[gi110];
	// g111 = grad3[gi111];
	// Calculate noise contributions from each of the eight corners
	double_t n000= dot(grad3[gi000], x, y, z);
	double_t n100= dot(grad3[gi100], x-1, y, z);
	double_t n010= dot(grad3[gi010], x, y-1, z);
	double_t n110= dot(grad3[gi110], x-1, y-1, z);
	double_t n001= dot(grad3[gi001], x, y, z-1);
	double_t n101= dot(grad3[gi101], x-1, y, z-1);
	double_t n011= dot(grad3[gi011], x, y-1, z-1);
	double_t n111= dot(grad3[gi111], x-1, y-1, z-1);
	// Compute the fade curve value for each of x, y, z
	double_t u = fade(x);
	double_t v = fade(y);
	double_t w = fade(z);
	// Interpolate along x the contributions from each of the corners
	double_t nx00 = mix(n000, n100, u);
	double_t nx01 = mix(n001, n101, u);
	double_t nx10 = mix(n010, n110, u);
	double_t nx11 = mix(n011, n111, u);
	// Interpolate the four results along y
	double_t nxy0 = mix(nx00, nx10, v);
	double_t nxy1 = mix(nx01, nx11, v);
	// Interpolate the two last results along z
	double_t nxyz = mix(nxy0, nxy1, w);

	return nxyz;
}
示例#13
0
文件: noise.c 项目: linehan/barnacle
/* 
 * Return a simplex noise value given coordinates x, y
 */
double simplex_noise(double yin, double xin)
{
        double skew;          // Input space (x,y) skewed to simplex space (i,j)
        double unskew;        // Simplex space (i,j) skewed to input space (x,y)
        double skew_factor;   // Transforms (x,y) to (i,j)
        double unskew_factor; // Transforms (i,j) to (x,y)
        double X0, Y0;        // Simplex cell origin in (x,y)
        double x0, y0;        // Distance of xin/yin from cell origin in (x,y)
        double x1, y1;        // Offsets of second corner in (x,y)
        double x2, y2;        // Offsets of third corner in (x,y)

        signed int i, j;      // Simplex space coordinates
        signed int i1, j1;    // Offsets for second corner of simplex.
        /* 
         * The unit simplex has 3 corners with offsets (0,0), (1,0), or (1,1).
         * The second corner can be either (1,0) or (0,1), depending on
         * which simplex contains (xin,yin), so we need to compute which
         * ordered pair to use, and store it, in order to calculate the
         * appropriate equivalent offsets in (x,y) that will be stored in
         * x1 and y1.
         *
         * To determine whether to use (0,1) or (1,0) for the offset of
         * the second corner, we need to determine which of the two simplices 
         * contains (xin,yin). 
         * 
         * We can see that if x0>y0, we are in the "lower" triangle, and if 
         * y0>x0, we are in the "upper" triangle: 
         *      ___
         *     |  /|   (Imagine a square)
         *    y| / |
         *     |/__|
         *       x
         */
        signed int ii, jj; // Gradient index variables
        signed int gi0, gi1, gi2; // Hashed gradient indices

        double t0, t1, t2; // Gradient contribution from each corner
        double n0, n1, n2; // Noise contribution from each corners

        /* Compute skew and unskew constants for 2D */
        skew   = 0.5*(sqrt(3.0)-1.0); // ((sqrt(n+1)-1)/n)
        unskew = (3.0-sqrt(3.0))/6.0; // ((n+1)-(sqrt(n+1)))/(n*(n+1))

        /* Transform (xin,yin) to simplex space (i,j) */
        skew_factor = (xin+yin)*skew;
        i = fastfloor(xin+skew_factor);
        j = fastfloor(yin+skew_factor);

        /* Transform origin of simplex cell containing (i,j) to (x,y) */
        unskew_factor = (i+j)*unskew;
        X0 = i-unskew_factor; 
        Y0 = j-unskew_factor;

        /* Compute distance between xin/yin and the cell origin */
        x0 = xin-X0;
        y0 = yin-Y0;

        /* Determine which simplex and thus which ordered pairs to use */
        if (x0 > y0) {  /* lower triangle, XY order: (0,0)->(1,0)->(1,1) */
                i1=1; 
                j1=0; 
        } else {        /* upper triangle, YX order: (0,0)->(0,1)->(1,1) */
                i1=0;                 
                j1=1;
        }

        /* Compute offsets of second corner in (x,y) */
        x1 = x0 - i1 + unskew;
        y1 = y0 - j1 + unskew;

        /* Compute offsets of third corner in (x,y) */
        x2 = x0 - 1.0 + 2.0 * unskew; 
        y2 = y0 - 1.0 + 2.0 * unskew;
        /* 
          Compute hashed gradient indices for the three corners
        */
        ii = i & 255;
        jj = j & 255;
        gi0 = PERM[ii+PERM[jj]] % 12;
        gi1 = PERM[ii+i1+PERM[jj+j1]] % 12;
        gi2 = PERM[ii+1+PERM[jj+1]] % 12;

        /* Compute gradient contribution from each corner */
        t0 = 0.5 - x0*x0-y0*y0;
        if (t0 < 0) 
                n0 = 0.0;
        else {
                t0 *= t0;
                n0 = t0 * t0 * dot(GRADIENT3[gi0], x0, y0);
        }
        t1 = 0.5 - x1*x1-y1*y1;
        if (t1 < 0) 
                n1 = 0.0;
        else {
                t1 *= t1;
                n1 = t1 * t1 * dot(GRADIENT3[gi1], x1, y1);
        }
        t2 = 0.5 - x2*x2-y2*y2;
        if (t2 < 0) 
                n2 = 0.0;
        else {
                t2 *= t2;
                n2 = t2 * t2 * dot(GRADIENT3[gi2], x2, y2);
        }

        /* Sum corners to arrive at final noise value, scale to 
         * interval [-1,1], and return */
        return (70.0 * (n0 + n1 + n2));
}
示例#14
0
float Simplex::_2D(std::initializer_list<float> coordinates, float scale) const
{
    thread_local float xc,yc;
    thread_local int ii,jj;
    thread_local int gi0,gi1,gi2;
    thread_local int skewedCubeOriginx,skewedCubeOriginy;
    thread_local int off1x,off1y;
    thread_local float n1,n2,n3;
    thread_local float c1,c2,c3;
    thread_local float sum;
    thread_local float unskewedCubeOriginx,unskewedCubeOriginy;
    thread_local float unskewedDistToOriginx,unskewedDistToOriginy;
    thread_local float d1x,d1y;
    thread_local float d2x,d2y;
    thread_local float d3x,d3y;

    std::initializer_list<float>::const_iterator it = coordinates.begin();

    xc = *(it  ) * scale;
    yc = *(++it) * scale;

    sum = (xc + yc) * SkewCoeff2D;
    skewedCubeOriginx = fastfloor(xc + sum);
    skewedCubeOriginy = fastfloor(yc + sum);

    sum = (skewedCubeOriginx + skewedCubeOriginy) * UnskewCoeff2D;
    unskewedCubeOriginx = skewedCubeOriginx - sum;
    unskewedCubeOriginy = skewedCubeOriginy - sum;

    unskewedDistToOriginx = xc - unskewedCubeOriginx;// Difference with 3d and 4d
    unskewedDistToOriginy = yc - unskewedCubeOriginy;

    if(unskewedDistToOriginx > unskewedDistToOriginy)
    {
        off1x = 1;
        off1y = 0;
    }
    else
    {
        off1x = 0;
        off1y = 1;
    }

    d1x = - unskewedDistToOriginx;
    d1y = - unskewedDistToOriginy;

    d2x = d1x + off1x - UnskewCoeff2D;
    d2y = d1y + off1y - UnskewCoeff2D;

    d3x = d1x + 1.f - 2.f * UnskewCoeff2D;
    d3y = d1y + 1.f - 2.f * UnskewCoeff2D;

    ii = skewedCubeOriginx & 255;
    jj = skewedCubeOriginy & 255;

    gi0 = perm[ii +         perm[jj         ]] & 7;
    gi1 = perm[ii + off1x + perm[jj + off1y ]] & 7;
    gi2 = perm[ii + 1 +     perm[jj + 1     ]] & 7;

    c1 = 0.5f - d1x * d1x - d1y * d1y;
    c2 = 0.5f - d2x * d2x - d2y * d2y;
    c3 = 0.5f - d3x * d3x - d3y * d3y;

    if(c1 < 0)
        n1 = 0;
    else
        n1 = c1*c1*c1*c1*(gradient2[gi0][0] * d1x + gradient2[gi0][1] * d1y);

    if(c2 < 0)
        n2 = 0;
    else
        n2 = c2*c2*c2*c2*(gradient2[gi1][0] * d2x + gradient2[gi1][1] * d2y);

    if(c3 < 0)
        n3 = 0;
    else
        n3 = c3*c3*c3*c3*(gradient2[gi2][0] * d3x + gradient2[gi2][1] * d3y);

    return (n1+n2+n3)*70.f;
}
示例#15
0
/*
 * This is somewhat a clone of the tile_by_steps function but one
 * that performs filling from and to pdf14dev (transparency) buffers.
 * At some point it may be desirable to do some optimization here.
 */
static int
tile_by_steps_trans(tile_fill_trans_state_t * ptfs, int x0, int y0, int w0, int h0,
              gx_pattern_trans_t *fill_trans_buffer, const gx_color_tile * ptile)
{
    int x1 = x0 + w0, y1 = y0 + h0;
    int i0, i1, j0, j1, i, j;
    gs_matrix step_matrix;      /* translated by phase */
    gx_pattern_trans_t *ptrans_pat = ptile->ttrans;

    ptfs->x0 = x0, ptfs->w0 = w0;
    ptfs->y0 = y0, ptfs->h0 = h0;
    step_matrix = ptile->step_matrix;
    step_matrix.tx -= ptfs->phase.x;
    step_matrix.ty -= ptfs->phase.y;
    {
        gs_rect bbox;           /* bounding box in device space */
        gs_rect ibbox;          /* bounding box in stepping space */
        double bbw = ptile->bbox.q.x - ptile->bbox.p.x;
        double bbh = ptile->bbox.q.y - ptile->bbox.p.y;
        double u0, v0, u1, v1;

        bbox.p.x = x0, bbox.p.y = y0;
        bbox.q.x = x1, bbox.q.y = y1;
        gs_bbox_transform_inverse(&bbox, &step_matrix, &ibbox);
        if_debug10('T',
          "[T]x,y=(%d,%d) w,h=(%d,%d) => (%g,%g),(%g,%g), offset=(%g,%g)\n",
                   x0, y0, w0, h0,
                   ibbox.p.x, ibbox.p.y, ibbox.q.x, ibbox.q.y,
                   step_matrix.tx, step_matrix.ty);
        /*
         * If the pattern is partly transparent and XStep/YStep is smaller
         * than the device space BBox, we need to ensure that we cover
         * each pixel of the rectangle being filled with *every* pattern
         * that overlaps it, not just *some* pattern copy.
         */
        u0 = ibbox.p.x - max(ptile->bbox.p.x, 0) - 0.000001;
        v0 = ibbox.p.y - max(ptile->bbox.p.y, 0) - 0.000001;
        u1 = ibbox.q.x - min(ptile->bbox.q.x, 0) + 0.000001;
        v1 = ibbox.q.y - min(ptile->bbox.q.y, 0) + 0.000001;
        if (!ptile->is_simple)
            u0 -= bbw, v0 -= bbh, u1 += bbw, v1 += bbh;
        i0 = (int)fastfloor(u0);
        j0 = (int)fastfloor(v0);
        i1 = (int)ceil(u1);
        j1 = (int)ceil(v1);
    }
    if_debug4('T', "[T]i=(%d,%d) j=(%d,%d)\n", i0, i1, j0, j1);
    for (i = i0; i < i1; i++)
        for (j = j0; j < j1; j++) {
            int x = (int)fastfloor(step_matrix.xx * i +
                          step_matrix.yx * j + step_matrix.tx);
            int y = (int)fastfloor(step_matrix.xy * i +
                          step_matrix.yy * j + step_matrix.ty);
            int w = ptrans_pat->width;
            int h = ptrans_pat->height;
            int xoff, yoff;
            int px, py;

            if_debug4('T', "[T]i=%d j=%d x,y=(%d,%d)", i, j, x, y);
            if (x < x0)
                xoff = x0 - x, x = x0, w -= xoff;
            else
                xoff = 0;
            if (y < y0)
                yoff = y0 - y, y = y0, h -= yoff;
            else
                yoff = 0;
            if (x + w > x1)
                w = x1 - x;
            if (y + h > y1)
                h = y1 - y;
            if_debug6('T', "=>(%d,%d) w,h=(%d,%d) x/yoff=(%d,%d)\n",
                      x, y, w, h, xoff, yoff);
            if (w > 0 && h > 0) {

                px = imod(xoff - x, ptile->ttrans->width);
                py = imod(yoff - y, ptile->ttrans->height);

                /* Set the offsets for colored pattern fills */
                ptfs->xoff = xoff;
                ptfs->yoff = yoff;

                /* We only go through blending during tiling, if
                   there was overlap as defined by the step matrix
                   and the bounding box */

                ptile->ttrans->pat_trans_fill(x, y, x+w, y+h, px, py, ptile,
                        fill_trans_buffer);
            }
        }
    return 0;
}
示例#16
0
float NzWorley2D::Get()
{
    xc = x * m_scale;
    yc = y * m_scale;

    x0 = fastfloor(xc);
    y0 = fastfloor(yc);

    fractx = xc - static_cast<float>(x0);
    fracty = yc - static_cast<float>(y0);

    featurePoints.clear();
    //Dummy points : FIX ME : Remove them
    featurePoints[100.f] = NzVector2f(0.f,0.f);
    featurePoints[101.f] = NzVector2f(0.f,0.f);
    featurePoints[102.f] = NzVector2f(0.f,0.f);
    featurePoints[103.f] = NzVector2f(0.f,0.f);

    SquareTest(x0,y0,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(fractx < it->first)
        SquareTest(x0 - 1,y0,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(1.f - fractx < it->first)
        SquareTest(x0 + 1,y0,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(fracty < it->first)
        SquareTest(x0,y0 - 1,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(1.f - fracty < it->first)
        SquareTest(x0,y0 + 1,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(fractx < it->first &&
       fracty < it->first)
       SquareTest(x0 - 1, y0 - 1,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(1.f - fractx < it->first &&
       fracty < it->first)
       SquareTest(x0 + 1, y0 - 1,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(fractx < it->first &&
       1.f - fracty < it->first)
       SquareTest(x0 - 1, y0 + 1,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    if(1.f - fractx < it->first &&
       1.f - fracty < it->first)
       SquareTest(x0 + 1, y0 + 1,xc,yc);

    it = featurePoints.begin();
    std::advance(it,m_function);

    //Remove dummy points
    featurePoints.erase(--(featurePoints.end()));
    featurePoints.erase(--(featurePoints.end()));
    featurePoints.erase(--(featurePoints.end()));
    featurePoints.erase(--(featurePoints.end()));

    return it->first * scale[m_function];
}
示例#17
0
int
gx_trans_pattern_fill_rect(int xmin, int ymin, int xmax, int ymax,
                           gx_color_tile *ptile,
                           gx_pattern_trans_t *fill_trans_buffer,
                           gs_int_point phase, gx_device *dev,
                           const gx_device_color * pdevc)
{

    tile_fill_trans_state_t state_trans;
    tile_fill_state_t state_clist_trans;
    int code;

    if (ptile == 0)             /* null pattern */
        return 0;

    /* Fit fill */
    if ( (xmin | ymin) < 0 ) {
        if ( xmin < 0 )
            xmin = 0;
        if ( ymin < 0 )
            ymin = 0;
    }

    /* Initialize the fill state */
    state_trans.phase.x = phase.x;
    state_trans.phase.y = phase.y;

    if (ptile->is_simple && ptile->cdev == NULL) {
        /* A simple case.  Tile is not clist and simple. */
        int px =
            imod(-(int)fastfloor(ptile->step_matrix.tx - phase.x + 0.5),
                  ptile->ttrans->width);
        int py =
            imod(-(int)fastfloor(ptile->step_matrix.ty - phase.y + 0.5),
                 ptile->ttrans->height);

        tile_rect_trans_simple(xmin, ymin, xmax, ymax, px, py, ptile,
            fill_trans_buffer);
    } else {
        if (ptile->cdev == NULL) {
            /* No clist for the pattern, but a complex case
               This portion transforms the bounding box by the step matrix
               and does partial rect fills with tiles that fall into this
               transformed bbox */
            code = tile_by_steps_trans(&state_trans, xmin, ymin, xmax-xmin,
                                        ymax-ymin, fill_trans_buffer, ptile);
        } else {
            /* clist for the trans tile.  This uses the pdf14 device as a target
               and should blend directly into the buffer.  Note that the
               pattern can not have a push pdf14 device or a pop pdf14 device
               compositor action.  Those are removed during the compositor
               clist writing operation where we check for the case of a pattern
               with a transparency */
            gx_device_clist *cdev = ptile->cdev;
            gx_device_clist_reader *crdev = (gx_device_clist_reader *)cdev;
            gx_strip_bitmap tbits;

            code = tile_fill_init(&state_clist_trans, pdevc, dev, false);

            state_clist_trans.phase.x = phase.x;
            state_clist_trans.phase.y = phase.y;
            crdev->yplane.depth = 0;
            crdev->yplane.shift = 0;
            crdev->yplane.index = -1;
            crdev->pages = NULL;
            crdev->num_pages = 1;
            state_clist_trans.orig_dev = dev;
            state_clist_trans.pdevc = pdevc;
            tbits = ptile->tbits;
            tbits.size.x = crdev->width;
            tbits.size.y = crdev->height;
            code = tile_by_steps(&state_clist_trans, xmin, ymin, xmax,
                                 ymax, ptile, &tbits, tile_pattern_clist);
        }
    }
    return(0);
}
示例#18
0
float NzSimplex4D::GetValue(float x, float y, float z, float w, float resolution)
{
    x *= resolution;
    y *= resolution;
    z *= resolution;
    w *= resolution;

    sum = (x + y + z + w) * SkewCoeff4D;
    skewedCubeOrigin.x = fastfloor(x + sum);
    skewedCubeOrigin.y = fastfloor(y + sum);
    skewedCubeOrigin.z = fastfloor(z + sum);
    skewedCubeOrigin.w = fastfloor(w + sum);

    sum = (skewedCubeOrigin.x + skewedCubeOrigin.y + skewedCubeOrigin.z + skewedCubeOrigin.w) * UnskewCoeff4D;
    unskewedCubeOrigin.x = skewedCubeOrigin.x - sum;
    unskewedCubeOrigin.y = skewedCubeOrigin.y - sum;
    unskewedCubeOrigin.z = skewedCubeOrigin.z - sum;
    unskewedCubeOrigin.w = skewedCubeOrigin.w - sum;

    unskewedDistToOrigin.x = x - unskewedCubeOrigin.x;
    unskewedDistToOrigin.y = y - unskewedCubeOrigin.y;
    unskewedDistToOrigin.z = z - unskewedCubeOrigin.z;
    unskewedDistToOrigin.w = w - unskewedCubeOrigin.w;

    c1 = (unskewedDistToOrigin.x > unskewedDistToOrigin.y) ? 32 : 0;
    c2 = (unskewedDistToOrigin.x > unskewedDistToOrigin.z) ? 16 : 0;
    c3 = (unskewedDistToOrigin.y > unskewedDistToOrigin.z) ? 8  : 0;
    c4 = (unskewedDistToOrigin.x > unskewedDistToOrigin.w) ? 4  : 0;
    c5 = (unskewedDistToOrigin.y > unskewedDistToOrigin.w) ? 2  : 0;
    c6 = (unskewedDistToOrigin.z > unskewedDistToOrigin.w) ? 1  : 0;
    c = c1 + c2 + c3 + c4 + c5 + c6;

    off1.x = lookupTable4D[c][0] >= 3 ? 1 : 0;
    off1.y = lookupTable4D[c][1] >= 3 ? 1 : 0;
    off1.z = lookupTable4D[c][2] >= 3 ? 1 : 0;
    off1.w = lookupTable4D[c][3] >= 3 ? 1 : 0;

    off2.x = lookupTable4D[c][0] >= 2 ? 1 : 0;
    off2.y = lookupTable4D[c][1] >= 2 ? 1 : 0;
    off2.z = lookupTable4D[c][2] >= 2 ? 1 : 0;
    off2.w = lookupTable4D[c][3] >= 2 ? 1 : 0;

    off3.x = lookupTable4D[c][0] >= 1 ? 1 : 0;
    off3.y = lookupTable4D[c][1] >= 1 ? 1 : 0;
    off3.z = lookupTable4D[c][2] >= 1 ? 1 : 0;
    off3.w = lookupTable4D[c][3] >= 1 ? 1 : 0;

    d1 = unskewedDistToOrigin;

    d2.x = d1.x - off1.x + UnskewCoeff4D;
    d2.y = d1.y - off1.y + UnskewCoeff4D;
    d2.z = d1.z - off1.z + UnskewCoeff4D;
    d2.w = d1.w - off1.w + UnskewCoeff4D;

    d3.x = d1.x - off2.x + 2.f*UnskewCoeff4D;
    d3.y = d1.y - off2.y + 2.f*UnskewCoeff4D;
    d3.z = d1.z - off2.z + 2.f*UnskewCoeff4D;
    d3.w = d1.w - off2.w + 2.f*UnskewCoeff4D;

    d4.x = d1.x - off3.x + 3.f*UnskewCoeff4D;
    d4.y = d1.y - off3.y + 3.f*UnskewCoeff4D;
    d4.z = d1.z - off3.z + 3.f*UnskewCoeff4D;
    d4.w = d1.w - off3.w + 3.f*UnskewCoeff4D;

    d5.x = d1.x - 1.f + 4*UnskewCoeff4D;
    d5.y = d1.y - 1.f + 4*UnskewCoeff4D;
    d5.z = d1.z - 1.f + 4*UnskewCoeff4D;
    d5.w = d1.w - 1.f + 4*UnskewCoeff4D;

    ii = skewedCubeOrigin.x & 255;
    jj = skewedCubeOrigin.y & 255;
    kk = skewedCubeOrigin.z & 255;
    ll = skewedCubeOrigin.w & 255;

    gi0 = perm[ii +          perm[jj +          perm[kk +          perm[ll]]]] & 31;
    gi1 = perm[ii + off1.x + perm[jj + off1.y + perm[kk + off1.z + perm[ll + off1.w]]]] & 31;
    gi2 = perm[ii + off2.x + perm[jj + off2.y + perm[kk + off2.z + perm[ll + off2.w]]]] & 31;
    gi3 = perm[ii + off3.x + perm[jj + off3.y + perm[kk + off3.z + perm[ll + off3.w]]]] & 31;
    gi4 = perm[ii + 1 +      perm[jj + 1 +      perm[kk + 1 +      perm[ll + 1]]]] % 32;

    c1 = 0.6f - d1.x*d1.x - d1.y*d1.y - d1.z*d1.z - d1.w*d1.w;
    c2 = 0.6f - d2.x*d2.x - d2.y*d2.y - d2.z*d2.z - d2.w*d2.w;
    c3 = 0.6f - d3.x*d3.x - d3.y*d3.y - d3.z*d3.z - d3.w*d3.w;
    c4 = 0.6f - d4.x*d4.x - d4.y*d4.y - d4.z*d4.z - d4.w*d4.w;
    c5 = 0.6f - d5.x*d5.x - d5.y*d5.y - d5.z*d5.z - d5.w*d5.w;

    if(c1 < 0)
        n1 = 0;
    else
        n1 = c1*c1*c1*c1*(gradient4[gi0][0]*d1.x + gradient4[gi0][1]*d1.y + gradient4[gi0][2]*d1.z + gradient4[gi0][3]*d1.w);

    if(c2 < 0)
        n2 = 0;
    else
        n2 = c2*c2*c2*c2*(gradient4[gi1][0]*d2.x + gradient4[gi1][1]*d2.y + gradient4[gi1][2]*d2.z + gradient4[gi1][3]*d2.w);

    if(c3 < 0)
        n3 = 0;
    else
        n3 = c3*c3*c3*c3*(gradient4[gi2][0]*d3.x + gradient4[gi2][1]*d3.y + gradient4[gi2][2]*d3.z + gradient4[gi2][3]*d3.w);

    if(c4 < 0)
        n4 = 0;
    else
        n4 = c4*c4*c4*c4*(gradient4[gi3][0]*d4.x + gradient4[gi3][1]*d4.y + gradient4[gi3][2]*d4.z + gradient4[gi3][3]*d4.w);

    if(c5 < 0)
        n5 = 0;
    else
        n5 = c5*c5*c5*c5*(gradient4[gi4][0]*d5.x + gradient4[gi4][1]*d5.y + gradient4[gi4][2]*d5.z + gradient4[gi4][3]*d5.w);

    return (n1+n2+n3+n4+n5)*27.f;
}
示例#19
0
/* This does the case of tiling with simple tiles.  Since it is not commented anywhere note
   that simple means that the tile size is the same as the step matrix size and the cross
   terms in the step matrix are 0.  Hence a simple case of tile replication. This needs to be optimized.  */
void
tile_rect_trans_simple(int xmin, int ymin, int xmax, int ymax, int px, int py, const gx_color_tile *ptile,
            gx_pattern_trans_t *fill_trans_buffer)
{
    int kk, jj, ii, h, w, buff_y_offset, buff_x_offset;
    unsigned char *ptr_out, *ptr_in, *buff_out, *buff_in, *ptr_out_temp;
    unsigned char *row_ptr;
    int in_row_offset;
    int tile_width = ptile->ttrans->width;
    int tile_height = ptile->ttrans->height;
    int dx, dy;
    int left_rem_end, left_width, num_full_tiles, right_tile_width;

    buff_y_offset = ymin - fill_trans_buffer->rect.p.y;
    buff_x_offset = xmin - fill_trans_buffer->rect.p.x;

    buff_out = fill_trans_buffer->transbytes +
        buff_y_offset * fill_trans_buffer->rowstride +
        buff_x_offset;

    buff_in = ptile->ttrans->transbytes;

    h = ymax - ymin;
    w = xmax - xmin;

    if (h <= 0 || w <= 0) return;

    dx = (xmin + px) % tile_width;
    dy = (ymin + py) % tile_height;

    /* To speed this up, the inner loop on the width is implemented with
       mem copys where we have a left remainder, full tiles and a right remainder.
       Depending upon the rect that we are filling we may have only one of these
       three portions, or two or all three.  We compute the parts now outside the loops. */

    /* Left remainder part */

    left_rem_end = min(dx+w,tile_width);
    left_width = left_rem_end - dx;

    /* Now the middle part */

    num_full_tiles = (int)fastfloor((float) (w - left_width)/ (float) tile_width);

    /* Now the right part */

    right_tile_width = w - num_full_tiles*tile_width - left_width;


    for (kk = 0; kk < fill_trans_buffer->n_chan; kk++){

        ptr_out = buff_out + kk * fill_trans_buffer->planestride;
        ptr_in = buff_in + kk * ptile->ttrans->planestride;

        for (jj = 0; jj < h; jj++){

            in_row_offset = (jj + dy) % ptile->ttrans->height;
            row_ptr = ptr_in + in_row_offset * ptile->ttrans->rowstride;

             /* This is the case when we have no blending. */

            ptr_out_temp = ptr_out;

            /* Left part */

            memcpy( ptr_out_temp, row_ptr + dx, left_width);
            ptr_out_temp += left_width;

            /* Now the full tiles */

            for ( ii = 0; ii < num_full_tiles; ii++){

                memcpy( ptr_out_temp, row_ptr, tile_width);
                ptr_out_temp += tile_width;

            }

            /* Now the remainder */

            memcpy( ptr_out_temp, row_ptr, right_tile_width);

            ptr_out += fill_trans_buffer->rowstride;

        }

    }

    /* If the group we are filling has a shape plane fill that now */
    /* Note:  Since this was a virgin group push we can just blast it with 255 */

    if (fill_trans_buffer->has_shape) {

        ptr_out = buff_out + fill_trans_buffer->n_chan * fill_trans_buffer->planestride;

        for (jj = 0; jj < h; jj++){

            memset(ptr_out, 255, w);
            ptr_out += fill_trans_buffer->rowstride;

        }

    }

}
示例#20
0
文件: Noise.cpp 项目: Clever-Boy/XLE
  // 4D simplex noise, better simplex rank ordering method 2012-03-09
  float SimplexNoise(Float4 input) 
  {
      float x = input[0], y = input[1], z = input[2], w = input[3];

      InitPerm();

    float n0, n1, n2, n3, n4; // Noise contributions from the five corners
    // Skew the (x,y,z,w) space to determine which cell of 24 simplices we're in
    float s = (x + y + z + w) * F4; // Factor for 4D skewing
    int i = fastfloor(x + s);
    int j = fastfloor(y + s);
    int k = fastfloor(z + s);
    int l = fastfloor(w + s);
    float t = (i + j + k + l) * G4; // Factor for 4D unskewing
    float X0 = i - t; // Unskew the cell origin back to (x,y,z,w) space
    float Y0 = j - t;
    float Z0 = k - t;
    float W0 = l - t;
    float x0 = x - X0;  // The x,y,z,w distances from the cell origin
    float y0 = y - Y0;
    float z0 = z - Z0;
    float w0 = w - W0;
    // For the 4D case, the simplex is a 4D shape I won't even try to describe.
    // To find out which of the 24 possible simplices we're in, we need to
    // determine the magnitude ordering of x0, y0, z0 and w0.
    // Six pair-wise comparisons are performed between each possible pair
    // of the four coordinates, and the results are used to rank the numbers.
    int rankx = 0;
    int ranky = 0;
    int rankz = 0;
    int rankw = 0;
    if(x0 > y0) rankx++; else ranky++;
    if(x0 > z0) rankx++; else rankz++;
    if(x0 > w0) rankx++; else rankw++;
    if(y0 > z0) ranky++; else rankz++;
    if(y0 > w0) ranky++; else rankw++;
    if(z0 > w0) rankz++; else rankw++;
    int i1, j1, k1, l1; // The integer offsets for the second simplex corner
    int i2, j2, k2, l2; // The integer offsets for the third simplex corner
    int i3, j3, k3, l3; // The integer offsets for the fourth simplex corner
    // simplex[c] is a 4-vector with the numbers 0, 1, 2 and 3 in some order.
    // Many values of c will never occur, since e.g. x>y>z>w makes x<z, y<w and x<w
    // impossible. Only the 24 indices which have non-zero entries make any sense.
    // We use a thresholding to set the coordinates in turn from the largest magnitude.
    // Rank 3 denotes the largest coordinate.
    i1 = rankx >= 3 ? 1 : 0;
    j1 = ranky >= 3 ? 1 : 0;
    k1 = rankz >= 3 ? 1 : 0;
    l1 = rankw >= 3 ? 1 : 0;
    // Rank 2 denotes the second largest coordinate.
    i2 = rankx >= 2 ? 1 : 0;
    j2 = ranky >= 2 ? 1 : 0;
    k2 = rankz >= 2 ? 1 : 0;
    l2 = rankw >= 2 ? 1 : 0;
    // Rank 1 denotes the second smallest coordinate.
    i3 = rankx >= 1 ? 1 : 0;
    j3 = ranky >= 1 ? 1 : 0;
    k3 = rankz >= 1 ? 1 : 0;
    l3 = rankw >= 1 ? 1 : 0;
    // The fifth corner has all coordinate offsets = 1, so no need to compute that.
    float x1 = x0 - i1 + G4; // Offsets for second corner in (x,y,z,w) coords
    float y1 = y0 - j1 + G4;
    float z1 = z0 - k1 + G4;
    float w1 = w0 - l1 + G4;
    float x2 = x0 - i2 + 2.0f*G4; // Offsets for third corner in (x,y,z,w) coords
    float y2 = y0 - j2 + 2.0f*G4;
    float z2 = z0 - k2 + 2.0f*G4;
    float w2 = w0 - l2 + 2.0f*G4;
    float x3 = x0 - i3 + 3.0f*G4; // Offsets for fourth corner in (x,y,z,w) coords
    float y3 = y0 - j3 + 3.0f*G4;
    float z3 = z0 - k3 + 3.0f*G4;
    float w3 = w0 - l3 + 3.0f*G4;
    float x4 = x0 - 1.0f + 4.0f*G4; // Offsets for last corner in (x,y,z,w) coords
    float y4 = y0 - 1.0f + 4.0f*G4;
    float z4 = z0 - 1.0f + 4.0f*G4;
    float w4 = w0 - 1.0f + 4.0f*G4;
    // Work out the hashed gradient indices of the five simplex corners
    int ii = i & 255;
    int jj = j & 255;
    int kk = k & 255;
    int ll = l & 255;
    int gi0 = perm[ii+perm[jj+perm[kk+perm[ll]]]] % 32;
    int gi1 = perm[ii+i1+perm[jj+j1+perm[kk+k1+perm[ll+l1]]]] % 32;
    int gi2 = perm[ii+i2+perm[jj+j2+perm[kk+k2+perm[ll+l2]]]] % 32;
    int gi3 = perm[ii+i3+perm[jj+j3+perm[kk+k3+perm[ll+l3]]]] % 32;
    int gi4 = perm[ii+1+perm[jj+1+perm[kk+1+perm[ll+1]]]] % 32;
    // Calculate the contribution from the five corners
    float t0 = 0.6f - x0*x0 - y0*y0 - z0*z0 - w0*w0;
    if(t0<0) n0 = 0.0f;
    else {
      t0 *= t0;
      n0 = t0 * t0 * dot(grad4[gi0], x0, y0, z0, w0);
    }
   float t1 = 0.6f - x1*x1 - y1*y1 - z1*z1 - w1*w1;
    if(t1<0) n1 = 0.0f;
    else {
      t1 *= t1;
      n1 = t1 * t1 * dot(grad4[gi1], x1, y1, z1, w1);
    }
   float t2 = 0.6f - x2*x2 - y2*y2 - z2*z2 - w2*w2;
    if(t2<0) n2 = 0.0f;
    else {
      t2 *= t2;
      n2 = t2 * t2 * dot(grad4[gi2], x2, y2, z2, w2);
    }
   float t3 = 0.6f - x3*x3 - y3*y3 - z3*z3 - w3*w3;
    if(t3<0) n3 = 0.0f;
    else {
      t3 *= t3;
      n3 = t3 * t3 * dot(grad4[gi3], x3, y3, z3, w3);
    }
   float t4 = 0.6f - x4*x4 - y4*y4 - z4*z4 - w4*w4;
    if(t4<0) n4 = 0.0f;
    else {
      t4 *= t4;
      n4 = t4 * t4 * dot(grad4[gi4], x4, y4, z4, w4);
    }
    // Sum up and scale the result to cover the range [-1,1]
    return 27.0f * (n0 + n1 + n2 + n3 + n4);
  }
示例#21
0
/**
* 2D Perlin simplex noise
*
*  Takes around 150ns on an AMD APU.
*
* @param[in] x float coordinate
* @param[in] y float coordinate
*
* @return Noise value in the range[-1; 1], value of 0 on all integer coordinates.
*/
float SimplexNoise::noise(float x, float y) {
	float n0, n1, n2;   // Noise contributions from the three corners

						// Skewing/Unskewing factors for 2D
	const float F2 = 0.366025403f;  // F2 = (sqrt(3) - 1) / 2
	const float G2 = 0.211324865f;  // G2 = (3 - sqrt(3)) / 6   = F2 / (1 + 2 * K)

									// Skew the input space to determine which simplex cell we're in
	float s = (x + y) * F2;  // Hairy factor for 2D
	float xs = x + s;
	float ys = y + s;
	int32_t i = fastfloor(xs);
	int32_t j = fastfloor(ys);

	// Unskew the cell origin back to (x,y) space
	float t = static_cast<float>(i + j) * G2;
	float X0 = i - t;
	float Y0 = j - t;
	float x0 = x - X0;  // The x,y distances from the cell origin
	float y0 = y - Y0;

	// For the 2D case, the simplex shape is an equilateral triangle.
	// Determine which simplex we are in.
	int32_t i1, j1;  // Offsets for second (middle) corner of simplex in (i,j) coords
	if (x0 > y0) {   // lower triangle, XY order: (0,0)->(1,0)->(1,1)
		i1 = 1;
		j1 = 0;
	}
	else {   // upper triangle, YX order: (0,0)->(0,1)->(1,1)
		i1 = 0;
		j1 = 1;
	}

	// A step of (1,0) in (i,j) means a step of (1-c,-c) in (x,y), and
	// a step of (0,1) in (i,j) means a step of (-c,1-c) in (x,y), where
	// c = (3-sqrt(3))/6

	float x1 = x0 - i1 + G2;            // Offsets for middle corner in (x,y) unskewed coords
	float y1 = y0 - j1 + G2;
	float x2 = x0 - 1.0f + 2.0f * G2;   // Offsets for last corner in (x,y) unskewed coords
	float y2 = y0 - 1.0f + 2.0f * G2;

	// Calculate the contribution from the first corner
	float t0 = 0.5f - x0*x0 - y0*y0;
	if (t0 < 0.0f) {
		n0 = 0.0f;
	}
	else {
		t0 *= t0;
		n0 = t0 * t0 * grad(hash(i + hash(j)), x0, y0);
	}

	// Calculate the contribution from the second corner
	float t1 = 0.5f - x1*x1 - y1*y1;
	if (t1 < 0.0f) {
		n1 = 0.0f;
	}
	else {
		t1 *= t1;
		n1 = t1 * t1 * grad(hash(i + i1 + hash(j + j1)), x1, y1);
	}

	// Calculate the contribution from the third corner
	float t2 = 0.5f - x2*x2 - y2*y2;
	if (t2 < 0.0f) {
		n2 = 0.0f;
	}
	else {
		t2 *= t2;
		n2 = t2 * t2 * grad(hash(i + 1 + hash(j + 1)), x2, y2);
	}

	// Add contributions from each corner to get the final noise value.
	// The result is scaled to return values in the interval [-1,1].
	return 45.23065f * (n0 + n1 + n2);
}
示例#22
0
/*
 * Fill with non-standard X and Y stepping.
 * ptile is pdevc->colors.pattern.{m,p}_tile.
 * tbits_or_tmask is whichever of tbits and tmask is supplying
 * the tile size.
 * This implementation could be sped up considerably!
 */
static int
tile_by_steps(tile_fill_state_t * ptfs, int x0, int y0, int w0, int h0,
              const gx_color_tile * ptile,
              const gx_strip_bitmap * tbits_or_tmask,
              int (*fill_proc) (const tile_fill_state_t * ptfs,
                                int x, int y, int w, int h))
{
    int x1 = x0 + w0, y1 = y0 + h0;
    int i0, i1, j0, j1, i, j;
    gs_matrix step_matrix;      /* translated by phase */
    int code;

    ptfs->x0 = x0, ptfs->w0 = w0;
    ptfs->y0 = y0, ptfs->h0 = h0;
    step_matrix = ptile->step_matrix;
    step_matrix.tx -= ptfs->phase.x;
    step_matrix.ty -= ptfs->phase.y;
    {
        gs_rect bbox;           /* bounding box in device space */
        gs_rect ibbox;          /* bounding box in stepping space */
        double bbw = ptile->bbox.q.x - ptile->bbox.p.x;
        double bbh = ptile->bbox.q.y - ptile->bbox.p.y;
        double u0, v0, u1, v1;

        bbox.p.x = x0, bbox.p.y = y0;
        bbox.q.x = x1, bbox.q.y = y1;
        gs_bbox_transform_inverse(&bbox, &step_matrix, &ibbox);
        if_debug10('T',
          "[T]x,y=(%d,%d) w,h=(%d,%d) => (%g,%g),(%g,%g), offset=(%g,%g)\n",
                   x0, y0, w0, h0,
                   ibbox.p.x, ibbox.p.y, ibbox.q.x, ibbox.q.y,
                   step_matrix.tx, step_matrix.ty);
        /*
         * If the pattern is partly transparent and XStep/YStep is smaller
         * than the device space BBox, we need to ensure that we cover
         * each pixel of the rectangle being filled with *every* pattern
         * that overlaps it, not just *some* pattern copy.
         */
        u0 = ibbox.p.x - max(ptile->bbox.p.x, 0) - 0.000001;
        v0 = ibbox.p.y - max(ptile->bbox.p.y, 0) - 0.000001;
        u1 = ibbox.q.x - min(ptile->bbox.q.x, 0) + 0.000001;
        v1 = ibbox.q.y - min(ptile->bbox.q.y, 0) + 0.000001;
        if (!ptile->is_simple)
            u0 -= bbw, v0 -= bbh, u1 += bbw, v1 += bbh;
        i0 = (int)fastfloor(u0);
        j0 = (int)fastfloor(v0);
        i1 = (int)ceil(u1);
        j1 = (int)ceil(v1);
    }
    if_debug4('T', "[T]i=(%d,%d) j=(%d,%d)\n", i0, i1, j0, j1);
    for (i = i0; i < i1; i++)
        for (j = j0; j < j1; j++) {
            int x = (int)fastfloor(step_matrix.xx * i +
                          step_matrix.yx * j + step_matrix.tx);
            int y = (int)fastfloor(step_matrix.xy * i +
                          step_matrix.yy * j + step_matrix.ty);
            int w = tbits_or_tmask->size.x;
            int h = tbits_or_tmask->size.y;
            int xoff, yoff;

            if_debug4('T', "[T]i=%d j=%d x,y=(%d,%d)", i, j, x, y);
            if (x < x0)
                xoff = x0 - x, x = x0, w -= xoff;
            else
                xoff = 0;
            if (y < y0)
                yoff = y0 - y, y = y0, h -= yoff;
            else
                yoff = 0;
            if (x + w > x1)
                w = x1 - x;
            if (y + h > y1)
                h = y1 - y;
            if_debug6('T', "=>(%d,%d) w,h=(%d,%d) x/yoff=(%d,%d)\n",
                      x, y, w, h, xoff, yoff);
            if (w > 0 && h > 0) {
                if (ptfs->pcdev == (gx_device *) & ptfs->cdev)
                    tile_clip_set_phase(&ptfs->cdev,
                                imod(xoff - x, ptfs->tmask->rep_width),
                                imod(yoff - y, ptfs->tmask->rep_height));
                /* Set the offsets for colored pattern fills */
                ptfs->xoff = xoff;
                ptfs->yoff = yoff;
                code = (*fill_proc) (ptfs, x, y, w, h);
                if (code < 0)
                    return code;
            }
        }
    return 0;
}
示例#23
0
int
gx_dc_pattern_fill_rectangle(const gx_device_color * pdevc, int x, int y,
                             int w, int h, gx_device * dev,
                             gs_logical_operation_t lop,
                             const gx_rop_source_t * source)
{
    gx_color_tile *ptile = pdevc->colors.pattern.p_tile;
    const gx_rop_source_t *rop_source = source;
    gx_rop_source_t no_source;
    gx_strip_bitmap *bits;
    tile_fill_state_t state;
    int code;

    if (ptile == 0)             /* null pattern */
        return 0;
    if (rop_source == NULL)
        set_rop_no_source(rop_source, no_source, dev);
    bits = &ptile->tbits;

    state.cdev.finalize = 0;

    code = tile_fill_init(&state, pdevc, dev, false);
    if (code < 0)
        return code;
    if (ptile->is_simple && ptile->cdev == NULL) {
        int px =
            imod(-(int)fastfloor(ptile->step_matrix.tx - state.phase.x + 0.5),
                 bits->rep_width);
        int py =
            imod(-(int)fastfloor(ptile->step_matrix.ty - state.phase.y + 0.5),
                 bits->rep_height);

        if (state.pcdev != dev)
            tile_clip_set_phase(&state.cdev, px, py);
        /* RJW: Can we get away with calling the simpler version? Not
         * if we are working in planar mode because the default
         * strip_tile_rectangle doesn't understand bits being in planar
         * mode at the moment.
         */
        if (source == NULL && lop_no_S_is_T(lop) && state.num_planes == -1)
            code = (*dev_proc(state.pcdev, strip_tile_rectangle))
                (state.pcdev, bits, x, y, w, h,
                 gx_no_color_index, gx_no_color_index, px, py);
        else if (rop_source->planar_height == 0)
            code = (*dev_proc(state.pcdev, strip_copy_rop))
                        (state.pcdev,
                         rop_source->sdata, rop_source->sourcex,
                         rop_source->sraster, rop_source->id,
                         (rop_source->use_scolors ? rop_source->scolors : NULL),
                         bits, NULL, x, y, w, h, px, py, lop);
        else
            code = (*dev_proc(state.pcdev, strip_copy_rop2))
                        (state.pcdev,
                         rop_source->sdata, rop_source->sourcex,
                         rop_source->sraster, rop_source->id,
                         (rop_source->use_scolors ? rop_source->scolors : NULL),
                         bits, NULL, x, y, w, h, px, py, lop,
                         rop_source->planar_height);
    } else {
        state.lop = lop;
        state.source = source;
        state.orig_dev = dev;
        if (ptile->cdev == NULL) {
            code = tile_by_steps(&state, x, y, w, h, ptile,
                                 &ptile->tbits, tile_colored_fill);
        } else {
            gx_device_clist *cdev = ptile->cdev;
            gx_device_clist_reader *crdev = (gx_device_clist_reader *)cdev;
            gx_strip_bitmap tbits;

            crdev->yplane.depth = 0; /* Don't know what to set here. */
            crdev->yplane.shift = 0;
            crdev->yplane.index = -1;
            crdev->pages = NULL;
            crdev->num_pages = 1;
            state.orig_dev = dev;
            tbits = ptile->tbits;
            tbits.size.x = crdev->width;
            tbits.size.y = crdev->height;
            code = tile_by_steps(&state, x, y, w, h, ptile,
                                 &tbits, tile_pattern_clist);
        }
    }
    if(state.cdev.finalize)
        state.cdev.finalize((gx_device *)&state.cdev);
    return code;
}
示例#24
0
float Simplex::_4D(std::initializer_list<float> coordinates, float scale) const
{
    thread_local float xc,yc,zc,wc;
    thread_local float x,y,z,w;
    thread_local int ii,jj,kk,ll;
    thread_local int gi0,gi1,gi2,gi3,gi4;
    thread_local int skewedCubeOriginx,skewedCubeOriginy,skewedCubeOriginz,skewedCubeOriginw;

    thread_local int off1x,off1y,off1z,off1w;
    thread_local int off2x,off2y,off2z,off2w;
    thread_local int off3x,off3y,off3z,off3w;

    thread_local int c;
    thread_local float n1,n2,n3,n4,n5;
    thread_local float c1,c2,c3,c4,c5,c6;

    thread_local float sum;
    thread_local float unskewedCubeOriginx,unskewedCubeOriginy,unskewedCubeOriginz,unskewedCubeOriginw;
    thread_local float unskewedDistToOriginx,unskewedDistToOriginy,unskewedDistToOriginz,unskewedDistToOriginw;
    thread_local float d1x,d2x,d3x,d4x,d5x;
    thread_local float d1y,d2y,d3y,d4y,d5y;
    thread_local float d1z,d2z,d3z,d4z,d5z;
    thread_local float d1w,d2w,d3w,d4w,d5w;

    std::initializer_list<float>::const_iterator it = coordinates.begin();

    x = *(it  );
    y = *(++it);
    z = *(++it);
    w = *(++it);

    xc = x * scale;
    yc = y * scale;
    zc = z * scale;
    wc = w * scale;

    sum = (xc + yc + zc + wc) * SkewCoeff4D;
    skewedCubeOriginx = fastfloor(xc + sum);
    skewedCubeOriginy = fastfloor(yc + sum);
    skewedCubeOriginz = fastfloor(zc + sum);
    skewedCubeOriginw = fastfloor(wc + sum);

    sum = (skewedCubeOriginx + skewedCubeOriginy + skewedCubeOriginz + skewedCubeOriginw) * UnskewCoeff4D;
    unskewedCubeOriginx = skewedCubeOriginx - sum;
    unskewedCubeOriginy = skewedCubeOriginy - sum;
    unskewedCubeOriginz = skewedCubeOriginz - sum;
    unskewedCubeOriginw = skewedCubeOriginw - sum;

    unskewedDistToOriginx = xc - unskewedCubeOriginx;
    unskewedDistToOriginy = yc - unskewedCubeOriginy;
    unskewedDistToOriginz = zc - unskewedCubeOriginz;
    unskewedDistToOriginw = wc - unskewedCubeOriginw;

    c1 = (unskewedDistToOriginx > unskewedDistToOriginy) ? 32 : 0;
    c2 = (unskewedDistToOriginx > unskewedDistToOriginz) ? 16 : 0;
    c3 = (unskewedDistToOriginy > unskewedDistToOriginz) ? 8  : 0;
    c4 = (unskewedDistToOriginx > unskewedDistToOriginw) ? 4  : 0;
    c5 = (unskewedDistToOriginy > unskewedDistToOriginw) ? 2  : 0;
    c6 = (unskewedDistToOriginz > unskewedDistToOriginw) ? 1  : 0;
    c = c1 + c2 + c3 + c4 + c5 + c6;

    off1x = lookupTable4D[c][0] >= 3 ? 1 : 0;
    off1y = lookupTable4D[c][1] >= 3 ? 1 : 0;
    off1z = lookupTable4D[c][2] >= 3 ? 1 : 0;
    off1w = lookupTable4D[c][3] >= 3 ? 1 : 0;

    off2x = lookupTable4D[c][0] >= 2 ? 1 : 0;
    off2y = lookupTable4D[c][1] >= 2 ? 1 : 0;
    off2z = lookupTable4D[c][2] >= 2 ? 1 : 0;
    off2w = lookupTable4D[c][3] >= 2 ? 1 : 0;

    off3x = lookupTable4D[c][0] >= 1 ? 1 : 0;
    off3y = lookupTable4D[c][1] >= 1 ? 1 : 0;
    off3z = lookupTable4D[c][2] >= 1 ? 1 : 0;
    off3w = lookupTable4D[c][3] >= 1 ? 1 : 0;

    d1x = unskewedDistToOriginx;
    d1y = unskewedDistToOriginy;
    d1z = unskewedDistToOriginz;
    d1w = unskewedDistToOriginw;

    d2x = d1x - off1x + UnskewCoeff4D;
    d2y = d1y - off1y + UnskewCoeff4D;
    d2z = d1z - off1z + UnskewCoeff4D;
    d2w = d1w - off1w + UnskewCoeff4D;

    d3x = d1x - off2x + 2.f*UnskewCoeff4D;
    d3y = d1y - off2y + 2.f*UnskewCoeff4D;
    d3z = d1z - off2z + 2.f*UnskewCoeff4D;
    d3w = d1w - off2w + 2.f*UnskewCoeff4D;

    d4x = d1x - off3x + 3.f*UnskewCoeff4D;
    d4y = d1y - off3y + 3.f*UnskewCoeff4D;
    d4z = d1z - off3z + 3.f*UnskewCoeff4D;
    d4w = d1w - off3w + 3.f*UnskewCoeff4D;

    d5x = d1x - 1.f + 4*UnskewCoeff4D;
    d5y = d1y - 1.f + 4*UnskewCoeff4D;
    d5z = d1z - 1.f + 4*UnskewCoeff4D;
    d5w = d1w - 1.f + 4*UnskewCoeff4D;

    ii = skewedCubeOriginx & 255;
    jj = skewedCubeOriginy & 255;
    kk = skewedCubeOriginz & 255;
    ll = skewedCubeOriginw & 255;

    gi0 = perm[ii +         perm[jj +         perm[kk +         perm[ll        ]]]] & 31;
    gi1 = perm[ii + off1x + perm[jj + off1y + perm[kk + off1z + perm[ll + off1w]]]] & 31;
    gi2 = perm[ii + off2x + perm[jj + off2y + perm[kk + off2z + perm[ll + off2w]]]] & 31;
    gi3 = perm[ii + off3x + perm[jj + off3y + perm[kk + off3z + perm[ll + off3w]]]] & 31;
    gi4 = perm[ii + 1 +     perm[jj + 1 +     perm[kk + 1 +     perm[ll + 1    ]]]] % 32;

    c1 = 0.6f - d1x*d1x - d1y*d1y - d1z*d1z - d1w*d1w;
    c2 = 0.6f - d2x*d2x - d2y*d2y - d2z*d2z - d2w*d2w;
    c3 = 0.6f - d3x*d3x - d3y*d3y - d3z*d3z - d3w*d3w;
    c4 = 0.6f - d4x*d4x - d4y*d4y - d4z*d4z - d4w*d4w;
    c5 = 0.6f - d5x*d5x - d5y*d5y - d5z*d5z - d5w*d5w;

    if(c1 < 0)
        n1 = 0;
    else
        n1 = c1*c1*c1*c1*(gradient4[gi0][0]*d1x + gradient4[gi0][1]*d1y + gradient4[gi0][2]*d1z + gradient4[gi0][3]*d1w);

    if(c2 < 0)
        n2 = 0;
    else
        n2 = c2*c2*c2*c2*(gradient4[gi1][0]*d2x + gradient4[gi1][1]*d2y + gradient4[gi1][2]*d2z + gradient4[gi1][3]*d2w);

    if(c3 < 0)
        n3 = 0;
    else
        n3 = c3*c3*c3*c3*(gradient4[gi2][0]*d3x + gradient4[gi2][1]*d3y + gradient4[gi2][2]*d3z + gradient4[gi2][3]*d3w);

    if(c4 < 0)
        n4 = 0;
    else
        n4 = c4*c4*c4*c4*(gradient4[gi3][0]*d4x + gradient4[gi3][1]*d4y + gradient4[gi3][2]*d4z + gradient4[gi3][3]*d4w);

    if(c5 < 0)
        n5 = 0;
    else
        n5 = c5*c5*c5*c5*(gradient4[gi4][0]*d5x + gradient4[gi4][1]*d5y + gradient4[gi4][2]*d5z + gradient4[gi4][3]*d5w);

    return (n1+n2+n3+n4+n5)*27.f;
}
示例#25
0
/* Our source tile runs (conceptually) from (0,0) to
 * (ptile->ttrans->width, ptile->ttrans->height). In practise, only a limited
 * section of this (ptile->rect) may actually be used. */
void
tile_rect_trans_simple(int xmin, int ymin, int xmax, int ymax,
                       int px, int py, const gx_color_tile *ptile,
                       gx_pattern_trans_t *fill_trans_buffer)
{
    int kk, jj, ii, h, w;
    int buff_out_y_offset, buff_out_x_offset;
    unsigned char *ptr_out, *ptr_in, *buff_out, *buff_in, *ptr_out_temp;
    unsigned char *row_ptr;
    int in_row_offset;
    int dx, dy;
    int left_rem_end, left_width, num_full_tiles, right_tile_width;
    int left_copy_rem_end, left_copy_width, left_copy_offset, left_copy_start;
    int mid_copy_width, right_copy_width;
    int tile_width  = ptile->ttrans->width;
    int tile_height = ptile->ttrans->height;

    /* Update the bbox in the topmost stack entry to reflect the fact that we
     * have drawn into it. FIXME: This makes the groups too large! */
    if (fill_trans_buffer->dirty->p.x > xmin)
        fill_trans_buffer->dirty->p.x = xmin;
    if (fill_trans_buffer->dirty->p.y > ymin)
        fill_trans_buffer->dirty->p.y = ymin;
    if (fill_trans_buffer->dirty->q.x < xmax)
        fill_trans_buffer->dirty->q.x = xmax;
    if (fill_trans_buffer->dirty->q.y < ymax)
        fill_trans_buffer->dirty->q.y = ymax;
    buff_out_y_offset = ymin - fill_trans_buffer->rect.p.y;
    buff_out_x_offset = xmin - fill_trans_buffer->rect.p.x;

    buff_out = fill_trans_buffer->transbytes +
        buff_out_y_offset * fill_trans_buffer->rowstride +
        buff_out_x_offset;

    buff_in = ptile->ttrans->transbytes;

    h = ymax - ymin;
    w = xmax - xmin;

    if (h <= 0 || w <= 0) return;

    /* Calc dx, dy within the entire (conceptual) input tile. */
    dx = (xmin + px) % tile_width;
    dy = (ymin + py) % tile_height;

    /* To speed this up, the inner loop on the width is implemented with
     * memcpys where we have a left remainder, full tiles and a right
     * remainder. Depending upon the rect that we are filling we may have
     * only one of these three portions, or two or all three.  We compute
     * the parts now outside the loops. */

    /* Left remainder part */
    left_rem_end = min(dx+w,tile_width);
    left_width = left_rem_end - dx;
    left_copy_start = max(dx,ptile->ttrans->rect.p.x);
    left_copy_rem_end = min(dx+w,ptile->ttrans->rect.q.x);
    left_copy_width = left_copy_rem_end - left_copy_start;
    if (left_copy_width < 0)
        left_copy_width = 0;
    left_copy_offset = left_copy_start-ptile->ttrans->rect.p.x;

    /* Now the middle part */
    num_full_tiles = (int)fastfloor((float) (w - left_width)/ (float) tile_width);
    mid_copy_width = ptile->ttrans->rect.q.x - ptile->ttrans->rect.p.x;

    /* Now the right part */
    right_tile_width = w - num_full_tiles*tile_width - left_width;
    right_copy_width = right_tile_width - ptile->ttrans->rect.p.x;
    if (right_copy_width > ptile->ttrans->rect.q.x)
        right_copy_width = ptile->ttrans->rect.q.x;
    right_copy_width -= ptile->ttrans->rect.p.x;
    if (right_copy_width < 0)
        right_copy_width = 0;

    for (kk = 0; kk < fill_trans_buffer->n_chan; kk++) {

        ptr_out = buff_out + kk * fill_trans_buffer->planestride;
        ptr_in  = buff_in  + kk * ptile->ttrans->planestride;

        for (jj = 0; jj < h; jj++, ptr_out += fill_trans_buffer->rowstride) {

            in_row_offset = ((jj + dy) % ptile->ttrans->height);
            if (in_row_offset >= ptile->ttrans->rect.q.y)
                continue;
            in_row_offset -= ptile->ttrans->rect.p.y;
            if (in_row_offset < 0)
                continue;
            row_ptr = ptr_in + in_row_offset * ptile->ttrans->rowstride;

             /* This is the case when we have no blending. */
            ptr_out_temp = ptr_out;

            /* Left part */
            memcpy( ptr_out_temp, row_ptr + left_copy_offset, left_copy_width);
            ptr_out_temp += left_width;

            /* Now the full tiles */

            for ( ii = 0; ii < num_full_tiles; ii++){
                memcpy( ptr_out_temp, row_ptr, mid_copy_width);
                ptr_out_temp += tile_width;
            }

            /* Now the remainder */
            memcpy( ptr_out_temp, row_ptr, right_copy_width);
        }
    }

    /* If the group we are filling has a shape plane fill that now */
    /* Note:  Since this was a virgin group push we can just blast it with
     * 255 */
    if (fill_trans_buffer->has_shape) {
        ptr_out = buff_out + fill_trans_buffer->n_chan * fill_trans_buffer->planestride;
        for (jj = 0; jj < h; jj++,ptr_out += fill_trans_buffer->rowstride) {
            memset(ptr_out, 255, w);
        }
    }
}
示例#26
0
	float Worley::Get(float x, float y, float scale) const
	{
		std::map<float, Vector2f> featurePoints;

		float xc, yc;
		int x0, y0;
		float fractx, fracty;

		xc = x * scale;
		yc = y * scale;

		x0 = fastfloor(xc);
		y0 = fastfloor(yc);

		fractx = xc - static_cast<float>(x0);
		fracty = yc - static_cast<float>(y0);

		featurePoints.clear();

		SquareTest(x0,y0,xc,yc,featurePoints);

		std::size_t functionIndex = static_cast<std::size_t>(m_function);

		auto it = featurePoints.begin();
		std::advance(it, functionIndex);

		if(fractx < it->first)
			SquareTest(x0 - 1,y0,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		if(1.f - fractx < it->first)
			SquareTest(x0 + 1,y0,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		if(fracty < it->first)
			SquareTest(x0,y0 - 1,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		if (1.f - fracty < it->first)
			SquareTest(x0,y0 + 1,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		if (fractx < it->first && fracty < it->first)
			SquareTest(x0 - 1, y0 - 1,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		if (1.f - fractx < it->first && fracty < it->first)
		   SquareTest(x0 + 1, y0 - 1,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		if (fractx < it->first && 1.f - fracty < it->first)
		   SquareTest(x0 - 1, y0 + 1,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		if(1.f - fractx < it->first && 1.f - fracty < it->first)
		   SquareTest(x0 + 1, y0 + 1,xc,yc,featurePoints);

		it = featurePoints.begin();
		std::advance(it, functionIndex);

		return it->first * m_functionScales[functionIndex];
	}
示例#27
0
	float Perlin3D::GetValue(float x, float y, float z, float resolution)
	{
		x /= resolution;
		y /= resolution;
		z /= resolution;

		x0 = fastfloor(x);
		y0 = fastfloor(y);
		z0 = fastfloor(z);

		ii = x0 & 255;
		jj = y0 & 255;
		kk = z0 & 255;

		gi0 = perm[ii +	 perm[jj +	 perm[kk]]] & 15;
		gi1 = perm[ii + 1 + perm[jj +	 perm[kk]]] & 15;
		gi2 = perm[ii +	 perm[jj + 1 + perm[kk]]] & 15;
		gi3 = perm[ii + 1 + perm[jj + 1 + perm[kk]]] & 15;

		gi4 = perm[ii +	 perm[jj +	 perm[kk + 1]]] & 15;
		gi5 = perm[ii + 1 + perm[jj +	 perm[kk + 1]]] & 15;
		gi6 = perm[ii +	 perm[jj + 1 + perm[kk + 1]]] & 15;
		gi7 = perm[ii + 1 + perm[jj + 1 + perm[kk + 1]]] & 15;

		temp.x = x-x0;
		temp.y = y-y0;
		temp.z = z-z0;

		Cx = temp.x * temp.x * temp.x * (temp.x * (temp.x * 6 - 15) + 10);
		Cy = temp.y * temp.y * temp.y * (temp.y * (temp.y * 6 - 15) + 10);
		Cz = temp.z * temp.z * temp.z * (temp.z * (temp.z * 6 - 15) + 10);

		s[0] = gradient3[gi0][0]*temp.x + gradient3[gi0][1]*temp.y + gradient3[gi0][2]*temp.z;

		temp.x = x-(x0+1);
		t[0] = gradient3[gi1][0]*temp.x + gradient3[gi1][1]*temp.y + gradient3[gi1][2]*temp.z;

		temp.y = y-(y0+1);
		v[0] = gradient3[gi3][0]*temp.x + gradient3[gi3][1]*temp.y + gradient3[gi3][2]*temp.z;

		temp.x = x-x0;
		u[0] = gradient3[gi2][0]*temp.x + gradient3[gi2][1]*temp.y + gradient3[gi2][2]*temp.z;

		temp.y = y-y0;
		temp.z = z-(z0+1);
		s[1] = gradient3[gi4][0]*temp.x + gradient3[gi4][1]*temp.y + gradient3[gi4][2]*temp.z;

		temp.x = x-(x0+1);
		t[1] = gradient3[gi5][0]*temp.x + gradient3[gi5][1]*temp.y + gradient3[gi5][2]*temp.z;

		temp.y = y-(y0+1);
		v[1] = gradient3[gi7][0]*temp.x + gradient3[gi7][1]*temp.y + gradient3[gi7][2]*temp.z;

		temp.x = x-x0;
		u[1] = gradient3[gi6][0]*temp.x + gradient3[gi6][1]*temp.y + gradient3[gi6][2]*temp.z;

		Li1 = s[0] + Cx*(t[0]-s[0]);
		Li2 = u[0] + Cx*(v[0]-u[0]);
		Li3 = s[1] + Cx*(t[1]-s[1]);
		Li4 = u[1] + Cx*(v[1]-u[1]);

		Li5 = Li1 + Cy*(Li2-Li1);
		Li6 = Li3 + Cy*(Li4-Li3);

		return Li5 + Cz*(Li6-Li5);
	}
示例#28
0
float simplexNoise3d(float x, float y, float z)
{
    float n0, n1, n2, n3; // Noise contributions from the four corners

    // Skew the input space to determine which simplex cell we're in
    float F3 = 1.f / 3.f;
    float s = (x + y + z) * F3; // Very nice and simple skew factor for 3D
    int i = fastfloor(x + s);
    int j = fastfloor(y + s);
    int k = fastfloor(z + s);

    float G3 = 1.f / 6.f; // Very nice and simple unskew factor, too
    float t = (i + j + k) * G3;
    float X0 = i - t; // Unskew the cell origin back to (x,y,z) space
    float Y0 = j - t;
    float Z0 = k - t;
    float x0 = x - X0; // The x,y,z distances from the cell origin
    float y0 = y - Y0;
    float z0 = z - Z0;

    // For the 3D case, the simplex shape is a slightly irregular tetrahedron.
    // Determine which simplex we are in.
    int i1, j1, k1; // Offsets for second corner of simplex in (i,j,k) coords
    int i2, j2, k2; // Offsets for third corner of simplex in (i,j,k) coords

    if(x0 >= y0)
	{
        if(y0 >= z0)
		{
			// X Y Z order
			i1 = 1;
			j1 = 0;
			k1 = 0;
			i2 = 1;
			j2 = 1;
			k2 = 0;
		}
        else if(x0 >= z0)
		{
			// X Z Y order
			i1 = 1;
			j1 = 0;
			k1 = 0;
			i2 = 1;
			j2 = 0;
			k2 = 1;
		}
        else
		{
			// Z X Y order
			i1 = 0;
			j1 = 0;
			k1 = 1;
			i2 = 1;
			j2 = 0;
			k2 = 1;
		}
    }
    else 
	{
        if(y0 < z0) 
		{ 
			// Z Y X order
			i1 = 0; 
			j1 = 0; 
			k1 = 1; 
			i2 = 0; 
			j2 = 1; 
			k2 = 1; 
		} 
        else if(x0 < z0) 
		{
			// Y Z X order
			i1 = 0; 
			j1 = 1; 
			k1 = 0; 
			i2 = 0; 
			j2 = 1; 
			k2 = 1; 
		} 
        else 
		{ 
			// Y X Z order
			i1 = 0;
			j1 = 1;
			k1 = 0;
			i2 = 1; 
			j2 = 1; 
			k2 = 0; 
		} 
    }

    float x1 = x0 - i1 + G3; // Offsets for second corner in (x,y,z) coords
    float y1 = y0 - j1 + G3;
    float z1 = z0 - k1 + G3;
    float x2 = x0 - i2 + 2.f*G3; // Offsets for third corner in (x,y,z) coords
    float y2 = y0 - j2 + 2.f*G3;
    float z2 = z0 - k2 + 2.f*G3;
    float x3 = x0 - 1.f + 3.f*G3; // Offsets for last corner in (x,y,z) coords
    float y3 = y0 - 1.f + 3.f*G3;
    float z3 = z0 - 1.f + 3.f*G3;

    // Work out the hashed gradient indices of the four simplex corners
    int ii = i & 255;
    int jj = j & 255;
    int kk = k & 255;

    int gi0 = perm[ii +      perm[jj +      perm[kk     ]]] % 12;
    int gi1 = perm[ii + i1 + perm[jj + j1 + perm[kk + k1]]] % 12;
    int gi2 = perm[ii + i2 + perm[jj + j2 + perm[kk + k2]]] % 12;
    int gi3 = perm[ii + 1  + perm[jj +  1 + perm[kk +  1]]] % 12;

    // Calculate the contribution from the four corners
    float t0 = 0.6f - x0 * x0 - y0 * y0 - z0 * z0;
    if(t0 < 0)
	{
		n0 = 0.f;
	}
    else 
	{
        t0 *= t0;
        n0 = t0 * t0 * dot(grad3[gi0], x0, y0, z0);
    }

    float t1 = 0.6f - x1 * x1 - y1 * y1 - z1 * z1;
    if(t1 < 0)
	{
		n1 = 0.f;
	}
    else 
	{
        t1 *= t1;
        n1 = t1 * t1 * dot(grad3[gi1], x1, y1, z1);
    }

    float t2 = 0.6f - x2 * x2 - y2 * y2 - z2 * z2;
    if(t2 < 0) 
	{
		n2 = 0.f;
	}
    else 
	{
        t2 *= t2;
        n2 = t2 * t2 * dot(grad3[gi2], x2, y2, z2);
    }

    float t3 = 0.6f - x3 * x3 - y3 * y3 - z3 * z3;
    if(t3 < 0)
	{
		n3 = 0.0;
	}
    else 
	{
        t3 *= t3;
        n3 = t3 * t3 * dot(grad3[gi3], x3, y3, z3);
    }

    // Add contributions from each corner to get the final noise value.
    // The result is scaled to stay just inside [-1,1]
    return 32.f * (n0 + n1 + n2 + n3);
}
示例#29
0
// 3D raw Simplex noise
double noise( const double x, const double y, const double z ) {
	double n0, n1, n2, n3; // Noise contributions from the four corners

	// Skew the input space to determine which simplex cell we're in
	const double F3 = 1.0/3.0;
	double s = (x+y+z)*F3; // Very nice and simple skew factor for 3D
	int i = fastfloor(x+s);
	int j = fastfloor(y+s);
	int k = fastfloor(z+s);

	const double G3 = 1.0/6.0; // Very nice and simple unskew factor, too
	double t = (i+j+k)*G3;
	double X0 = i-t; // Unskew the cell origin back to (x,y,z) space
	double Y0 = j-t;
	double Z0 = k-t;
	double x0 = x-X0; // The x,y,z distances from the cell origin
	double y0 = y-Y0;
	double z0 = z-Z0;

	// For the 3D case, the simplex shape is a slightly irregular tetrahedron.
	// Determine which simplex we are in.
	int i1, j1, k1; // Offsets for second corner of simplex in (i,j,k) coords
	int i2, j2, k2; // Offsets for third corner of simplex in (i,j,k) coords

	if(x0>=y0) {
	if(y0>=z0)
	{ i1=1; j1=0; k1=0; i2=1; j2=1; k2=0; } // X Y Z order
	else if(x0>=z0) { i1=1; j1=0; k1=0; i2=1; j2=0; k2=1; } // X Z Y order
	else { i1=0; j1=0; k1=1; i2=1; j2=0; k2=1; } // Z X Y order
	}
	else { // x0<y0
	if(y0<z0) { i1=0; j1=0; k1=1; i2=0; j2=1; k2=1; } // Z Y X order
	else if(x0<z0) { i1=0; j1=1; k1=0; i2=0; j2=1; k2=1; } // Y Z X order
	else { i1=0; j1=1; k1=0; i2=1; j2=1; k2=0; } // Y X Z order
	}

	// A step of (1,0,0) in (i,j,k) means a step of (1-c,-c,-c) in (x,y,z),
	// a step of (0,1,0) in (i,j,k) means a step of (-c,1-c,-c) in (x,y,z), and
	// a step of (0,0,1) in (i,j,k) means a step of (-c,-c,1-c) in (x,y,z), where
	// c = 1/6.
	double x1 = x0 - i1 + G3; // Offsets for second corner in (x,y,z) coords
	double y1 = y0 - j1 + G3;
	double z1 = z0 - k1 + G3;
	double x2 = x0 - i2 + 2.0*G3; // Offsets for third corner in (x,y,z) coords
	double y2 = y0 - j2 + 2.0*G3;
	double z2 = z0 - k2 + 2.0*G3;
	double x3 = x0 - 1.0 + 3.0*G3; // Offsets for last corner in (x,y,z) coords
	double y3 = y0 - 1.0 + 3.0*G3;
	double z3 = z0 - 1.0 + 3.0*G3;

	// Work out the hashed gradient indices of the four simplex corners
	int ii = i & 255;
	int jj = j & 255;
	int kk = k & 255;
	int gi0 = mod12[perm[ii+perm[jj+perm[kk]]]];
	int gi1 = mod12[perm[ii+i1+perm[jj+j1+perm[kk+k1]]]];
	int gi2 = mod12[perm[ii+i2+perm[jj+j2+perm[kk+k2]]]];
	int gi3 = mod12[perm[ii+1+perm[jj+1+perm[kk+1]]]];

	// Calculate the contribution from the four corners
	double t0 = 0.6 - x0*x0 - y0*y0 - z0*z0;
	if(t0<0) n0 = 0.0;
	else {
	t0 *= t0;
	n0 = t0 * t0 * dot(grad3[gi0], x0, y0, z0);
	}

	double t1 = 0.6 - x1*x1 - y1*y1 - z1*z1;
	if(t1<0) n1 = 0.0;
	else {
	t1 *= t1;
	n1 = t1 * t1 * dot(grad3[gi1], x1, y1, z1);
	}

	double t2 = 0.6 - x2*x2 - y2*y2 - z2*z2;
	if(t2<0) n2 = 0.0;
	else {
	t2 *= t2;
	n2 = t2 * t2 * dot(grad3[gi2], x2, y2, z2);
	}

	double t3 = 0.6 - x3*x3 - y3*y3 - z3*z3;
	if(t3<0) n3 = 0.0;
	else {
	t3 *= t3;
	n3 = t3 * t3 * dot(grad3[gi3], x3, y3, z3);
	}

	// Add contributions from each corner to get the final noise value.
	// The result is scaled to stay just inside [-1,1]
	return 32.0*(n0 + n1 + n2 + n3);
}
示例#30
0
float Simplex::_3D(std::initializer_list<float> coordinates, float scale) const
{
    thread_local float xc, yc, zc;
    thread_local float x,y,z;
    thread_local int ii,jj,kk;
    thread_local int gi0,gi1,gi2,gi3;
    thread_local int skewedCubeOriginx,skewedCubeOriginy,skewedCubeOriginz;

    thread_local int off1x,off1y,off1z;
    thread_local int off2x,off2y,off2z;
    thread_local float n1,n2,n3,n4;
    thread_local float c1,c2,c3,c4;

    thread_local float sum;
    thread_local float unskewedCubeOriginx,unskewedCubeOriginy,unskewedCubeOriginz;
    thread_local float unskewedDistToOriginx,unskewedDistToOriginy,unskewedDistToOriginz;
    thread_local float d1x,d1y,d1z;
    thread_local float d2x,d2y,d2z;
    thread_local float d3x,d3y,d3z;
    thread_local float d4x,d4y,d4z;

    std::initializer_list<float>::const_iterator it = coordinates.begin();

    x = *(it  );
    y = *(++it);
    z = *(++it);

    xc = x * scale;
    yc = y * scale;
    zc = z * scale;

    sum = (xc + yc + zc) * SkewCoeff3D;
    skewedCubeOriginx = fastfloor(xc + sum);
    skewedCubeOriginy = fastfloor(yc + sum);
    skewedCubeOriginz = fastfloor(zc + sum);

    sum = (skewedCubeOriginx + skewedCubeOriginy + skewedCubeOriginz) * UnskewCoeff3D;
    unskewedCubeOriginx = skewedCubeOriginx - sum;
    unskewedCubeOriginy = skewedCubeOriginy - sum;
    unskewedCubeOriginz = skewedCubeOriginz - sum;

    unskewedDistToOriginx = xc - unskewedCubeOriginx;
    unskewedDistToOriginy = yc - unskewedCubeOriginy;
    unskewedDistToOriginz = zc - unskewedCubeOriginz;

    if(unskewedDistToOriginx >= unskewedDistToOriginy)
    {
        if(unskewedDistToOriginy >= unskewedDistToOriginz)
        {
            off1x = 1;
            off1y = 0;
            off1z = 0;
            off2x = 1;
            off2y = 1;
            off2z = 0;
        }
        else if(unskewedDistToOriginx >= unskewedDistToOriginz)
        {
            off1x = 1;
            off1y = 0;
            off1z = 0;
            off2x = 1;
            off2y = 0;
            off2z = 1;
        }
        else
        {
            off1x = 0;
            off1y = 0;
            off1z = 1;
            off2x = 1;
            off2y = 0;
            off2z = 1;
        }
    }
    else
    {
        if(unskewedDistToOriginy < unskewedDistToOriginz)
        {
            off1x = 0;
            off1y = 0;
            off1z = 1;
            off2x = 0;
            off2y = 1;
            off2z = 1;
        }
        else if(unskewedDistToOriginx < unskewedDistToOriginz)
        {
            off1x = 0;
            off1y = 1;
            off1z = 0;
            off2x = 0;
            off2y = 1;
            off2z = 1;
        }
        else
        {
            off1x = 0;
            off1y = 1;
            off1z = 0;
            off2x = 1;
            off2y = 1;
            off2z = 0;
        }
    }

    d1x = unskewedDistToOriginx;
    d1y = unskewedDistToOriginy;
    d1z = unskewedDistToOriginz;

    d2x = d1x - off1x + UnskewCoeff3D;
    d2y = d1y - off1y + UnskewCoeff3D;
    d2z = d1z - off1z + UnskewCoeff3D;

    d3x = d1x - off2x + 2.f*UnskewCoeff3D;
    d3y = d1y - off2y + 2.f*UnskewCoeff3D;
    d3z = d1z - off2z + 2.f*UnskewCoeff3D;

    d4x = d1x - 1.f + 3.f*UnskewCoeff3D;
    d4y = d1y - 1.f + 3.f*UnskewCoeff3D;
    d4z = d1z - 1.f + 3.f*UnskewCoeff3D;

    ii = skewedCubeOriginx & 255;
    jj = skewedCubeOriginy & 255;
    kk = skewedCubeOriginz & 255;

    gi0 = perm[ii +         perm[jj +         perm[kk         ]]] % 12;
    gi1 = perm[ii + off1x + perm[jj + off1y + perm[kk + off1z ]]] % 12;
    gi2 = perm[ii + off2x + perm[jj + off2y + perm[kk + off2z ]]] % 12;
    gi3 = perm[ii + 1 +     perm[jj + 1 +     perm[kk + 1     ]]] % 12;

    c1 = 0.6f - d1x * d1x - d1y * d1y - d1z * d1z;
    c2 = 0.6f - d2x * d2x - d2y * d2y - d2z * d2z;
    c3 = 0.6f - d3x * d3x - d3y * d3y - d3z * d3z;
    c4 = 0.6f - d4x * d4x - d4y * d4y - d4z * d4z;

    if(c1 < 0)
        n1 = 0;
    else
        n1 = c1*c1*c1*c1*(gradient3[gi0][0] * d1x + gradient3[gi0][1] * d1y + gradient3[gi0][2] * d1z);

    if(c2 < 0)
        n2 = 0;
    else
        n2 = c2*c2*c2*c2*(gradient3[gi1][0] * d2x + gradient3[gi1][1] * d2y + gradient3[gi1][2] * d2z);

    if(c3 < 0)
        n3 = 0;
    else
        n3 = c3*c3*c3*c3*(gradient3[gi2][0] * d3x + gradient3[gi2][1] * d3y + gradient3[gi2][2] * d3z);

    if(c4 < 0)
        n4 = 0;
    else
        n4 = c4*c4*c4*c4*(gradient3[gi3][0] * d4x + gradient3[gi3][1] * d4y + gradient3[gi3][2] * d4z);

    return (n1+n2+n3+n4)*32;
}