织梦CMS - 轻松建站从此开始!

罗索

OPENGL-ES 球体顶点坐标计算

落鹤生 发布于 2012-03-13 11:35 点击:次 
//创建球体模型的顶点坐标 bool OGLESFiveSpheres::CreateGeometry() { unsigned int i; /* g_ui32RimNo多少个同心圆 g_uiRimSize每个同心圆上的点数 */ /* Createsthesphereverticesandtexturecoordinates */ m_ui32VertexNo=(g_ui32RimNo- 2 )*g_uiRimSize+ 2 ; m_pV
TAG:

//创建球体模型的顶点坐标 
bool OGLESFiveSpheres::CreateGeometry() 

    unsigned int i; 
 
    /* 
        g_ui32RimNo 多少个同心圆 
        g_uiRimSize 每个同心圆上的点数 
    */ 
    /* 
        Creates the sphere vertices and texture coordinates 
    */ 
    m_ui32VertexNo = (g_ui32RimNo - 2) * g_uiRimSize + 2
    m_pVertex = new SVertex[m_ui32VertexNo]; 
 
    if(!m_pVertex) 
    { 
        PVRShellSet(prefExitMessage, "Error: Out of memory."); 
        return false
    } 
 
    // Bottom vertex 
    m_pVertex[0].fPos.x = 0
    m_pVertex[0].fPos.y = -0.5f * g_ui32SphereScale; 
    m_pVertex[0].fPos.z = 0
    m_pVertex[0].fU = 0.5f; 
    m_pVertex[0].fV = 0.5f; 
 
    // 7 rims of 16 vertices each 
    float fYAngleInc = PVRT_PI / (float) (g_ui32RimNo - 1); 
    float fYAngle = fYAngleInc; 
    int i32Index = 1
 
    for(i = 0; i < (g_ui32RimNo - 2); ++i) 
    { 
        float fPosY = (float) cos(fYAngle) * -0.5f; 
        fYAngle += fYAngleInc; 
 
        for(int j = 0; j < g_uiRimSize; ++j) 
        { 
            float fAngle = (float)j * 2.0f * PVRT_PI / (float)g_uiRimSize; 
            float fSize = (float) cos(asin(fPosY*2)) * 0.50f; 
            m_pVertex[GetVertexIndex(i+1,j)].fPos.x = (float)PVRTFCOS(fAngle) * (fSize*g_ui32SphereScale); 
            m_pVertex[GetVertexIndex(i+1,j)].fPos.y = fPosY * g_ui32SphereScale; 
            m_pVertex[GetVertexIndex(i+1,j)].fPos.z = (float)PVRTFSIN(fAngle) * (fSize*g_ui32SphereScale); 
            m_pVertex[GetVertexIndex(i+1,j)].fU = m_pVertex[GetVertexIndex(i+1,j)].fPos.x + 0.5f; 
            m_pVertex[GetVertexIndex(i+1,j)].fV = m_pVertex[GetVertexIndex(i+1,j)].fPos.z + 0.5f; 
            ++i32Index; 
        } 
    } 
 
    // Top vertex 
    m_pVertex[i32Index].fPos.x = 0
    m_pVertex[i32Index].fPos.y = 0.5f * g_ui32SphereScale; 
    m_pVertex[i32Index].fPos.z = 0
    m_pVertex[i32Index].fU = 0.5f; 
    m_pVertex[i32Index].fV = 0.5f; 
 
    /* 
        Creates the sphere normals. 
    */ 
    for(i = 0; i < (g_ui32RimNo - 2) * g_uiRimSize + 2; ++i) 
    { 
        PVRTVec3 vNormal; 
        vNormal.x = m_pVertex[i].fPos.x; 
        vNormal.y = m_pVertex[i].fPos.y; 
        vNormal.z = m_pVertex[i].fPos.z; 
 
        vNormal.normalize(); 
 
        m_pVertex[i].fNormal.x = vNormal.x; 
        m_pVertex[i].fNormal.y = vNormal.y; 
        m_pVertex[i].fNormal.z = vNormal.z; 
    } 
 
    return true

 

说明:假如球体有180个同心圆(g_ui32RimNo = 180)当然包含最上面一个点和最下面一个点,南极北极。

那么每个同心圆之间的角度差都是1°。即角度增量为:

float fYAngleInc = PVRT_PI / (float) (g_ui32RimNo - 1); //B角

同一个同心圆上面所有点的Y坐标都是一致的。

float fPosY = (float) cos(fYAngle) * -0.5f; 

角度Q的计算:

 float fAngle = (float)j * 2.0f * PVRT_PI / (float)g_uiRimSize; //图中有点错误,Q画成了与X负轴夹角,应该是正轴夹角。

同心圆半径R1的计算:

float fSize = (float) cos(asin(fPosY*2)) * 0.50f; 

fPosY*2 =   (float) cos(fYAngle) * -0.5f * 2 =  (float) cos(fYAngle)  = sin(π/2 - fYAngle)

其实R1也可以这样计算: (float) sin(fYAngle) * 0.50f; 

X坐标计算:

R1 * cosQ

Z坐标计算:

R1 * sinQ

(cr0_3)
本站文章除注明转载外,均为本站原创或编译欢迎任何形式的转载,但请务必注明出处,尊重他人劳动,同学习共成长。转载请注明:文章转载自:罗索实验室 [http://www.rosoo.net/a/201203/15814.html]
本文出处:百度博客 作者:cr0_3 原文
顶一下
(0)
0%
踩一下
(0)
0%
------分隔线----------------------------
发表评论
请自觉遵守互联网相关的政策法规,严禁发布色情、暴力、反动的言论。
评价:
表情:
用户名: 验证码:点击我更换图片
栏目列表
将本文分享到微信
织梦二维码生成器
推荐内容