コード例 #1
0
ファイル: Cylinder.cpp プロジェクト: A7med-Shoukry/g3d
void Cylinder::getRandomSurfacePoint(Vector3& p, Vector3& N) const {
    float h = height();
    float r = radius();

    // Create a random point on a standard cylinder and then rotate to the global frame.

    // Relative areas (factor of 2PI already taken out)
    float capRelArea  = square(r) / 2.0f;
    float sideRelArea = r * h;

    float r1 = uniformRandom(0, capRelArea * 2 + sideRelArea);

    if (r1 < capRelArea * 2) {

        // Select a point uniformly at random on a disk
        // @cite http://mathworld.wolfram.com/DiskPointPicking.html
        float a = uniformRandom(0, (float)twoPi());
        float r2 = sqrt(uniformRandom(0, 1)) * r;
        p.x = cos(a) * r2;
        p.z = sin(a) * r2;

        N.x = 0;
        N.z = 0;
        if (r1 < capRelArea) {
            // Top
            p.y = h / 2.0f;
            N.y = 1;
        } else {
            // Bottom
            p.y = -h / 2.0f;
            N.y = -1;
        }
    } else {
        // Side
        float a = uniformRandom(0, (float)twoPi());
        N.x = cos(a);
        N.y = 0;
        N.z = sin(a);
        p.x = N.x * r;
        p.z = N.y * r;
        p.y = uniformRandom(-h / 2.0f, h / 2.0f);
    }

    // Transform to world space
    CoordinateFrame cframe;
    getReferenceFrame(cframe);
    
    p = cframe.pointToWorldSpace(p);
    N = cframe.normalToWorldSpace(N);
}
コード例 #2
0
ファイル: Cylinder.cpp プロジェクト: A7med-Shoukry/g3d
Vector3 Cylinder::randomInteriorPoint() const {
    float h = height();
    float r = radius();

    // Create a random point in a standard cylinder and then rotate to the global frame.

    // Select a point uniformly at random on a disk
    // @cite http://mathworld.wolfram.com/DiskPointPicking.html
    float a = uniformRandom(0, (float)twoPi());
    float r2 = sqrt(uniformRandom(0, 1)) * r;

    Vector3 p(  cos(a) * r2,
                uniformRandom(-h / 2.0f, h / 2.0f),
                sin(a) * r2);

    // Transform to world space
    CoordinateFrame cframe;
    getReferenceFrame(cframe);
    
    return cframe.pointToWorldSpace(p);
}
コード例 #3
0
ファイル: Capsule.cpp プロジェクト: h4s0n/Sandshroud
void Capsule::getRandomSurfacePoint(Vector3& p, Vector3& N) const {
    float h = height();
    float r = radius();

    // Create a random point on a standard capsule and then rotate to the global frame.

    // Relative areas
    float capRelArea  = sqrt(r) / 2.0f;
    float sideRelArea = r * h;

    float r1 = uniformRandom(0, capRelArea * 2 + sideRelArea);

    if (r1 < capRelArea * 2) {

        // Select a point uniformly at random on a sphere
        N = Sphere(Vector3::zero(), 1).randomSurfacePoint();
        p = N * r;
        p.y += sign(p.y) * h / 2.0f;
    } else {
        // Side
        float a = uniformRandom(0, (float)twoPi());
        N.x = cos(a);
        N.y = 0;
        N.z = sin(a);
        p.x = N.x * r;
        p.z = N.y * r;
        p.y = uniformRandom(-h / 2.0f, h / 2.0f);
    }

    // Transform to world space
    CoordinateFrame cframe;
    getReferenceFrame(cframe);
    
    p = cframe.pointToWorldSpace(p);
    N = cframe.normalToWorldSpace(N);
}
コード例 #4
0
ファイル: Capsule.cpp プロジェクト: h4s0n/Sandshroud
Vector3 Capsule::randomInteriorPoint() const {
    float h = height();
    float r = radius();

    // Create a random point in a standard capsule and then rotate to the global frame.

    Vector3 p;

    float hemiVolume = pi() * (r*r*r) * 4 / 6.0;
    float cylVolume = pi() * square(r) * h;
    
    float r1 = uniformRandom(0, 2.0 * hemiVolume + cylVolume);

    if (r1 < 2.0 * hemiVolume) {

        p = Sphere(Vector3::zero(), r).randomInteriorPoint();

        p.y += sign(p.y) * h / 2.0f;

    } else {

        // Select a point uniformly at random on a disk
        float a = uniformRandom(0, (float)twoPi());
        float r2 = sqrt(uniformRandom(0, 1)) * r;

        p = Vector3(cos(a) * r2,
                    uniformRandom(-h / 2.0f, h / 2.0f),
                    sin(a) * r2);
    }

    // Transform to world space
    CoordinateFrame cframe;
    getReferenceFrame(cframe);
    
    return cframe.pointToWorldSpace(p);
}
コード例 #5
0
ファイル: MeshAlg.cpp プロジェクト: Demigodess/Darkcore
void MeshAlg::generateGrid(
    Array<Vector3>&     vertex,
    Array<Vector2>&     texCoord,
    Array<int>&         index,
    int                 wCells,
    int                 hCells,
    const Vector2&      textureScale,
    bool                spaceCentered,
    bool                twoSided,
    const CoordinateFrame& xform,
    const Image1::Ref&  height) {

    vertex.fastClear();
    texCoord.fastClear();
    index.fastClear();

    // Generate vertices
    for (int z = 0; z <= hCells; ++z) {
        for (int x = 0; x <= wCells; ++x) {
            Vector3 v(x / (float)wCells, 0, z / (float)hCells);

            Vector2 t = v.xz() * textureScale;

            texCoord.append(t);

            if (height.notNull()) {
                v.y = height->nearest(v.x * (height->width() - 1), v.z * (height->height() - 1)).value;
            }
            if (spaceCentered) {
                v -= Vector3(0.5f, 0, 0.5f);
            }
            v = xform.pointToWorldSpace(v);
            vertex.append(v);
        }
    }

    // Generate indices
    for (int z = 0; z < hCells; ++z) {
        for (int x = 0; x < wCells; ++x) {
            int A = x + z * (wCells + 1);
            int B = A + 1;
            int C = A + (wCells + 1);
            int D = C + 1;

            //  A       B
            //   *-----*
            //   | \   |
            //   |   \ |
            //   *-----*
            //  C       D

            index.append(A, D, B);
            index.append(A, C, D);
        }
    }

    if (twoSided) {
        // The index array needs to have reversed winding for the bottom
        // and offset by the original number of vertices
        Array<int> ti = index;
        ti.reverse();
        for (int i = 0; i < ti.size(); ++i) {
            ti[i] += vertex.size();
        }
        index.append(ti);

        // Duplicate the arrays
        vertex.append(Array<Vector3>(vertex));
        texCoord.append(Array<Vector2>(texCoord));
    }
}