Quantcast
Channel: Mali Developer Center
Viewing all articles
Browse latest Browse all 125

OpenGL ES 2.0 简单示例

$
0
0

 

这一简单示例演示如何通过使用 OpenGL ES 2.0 API 和可编程着色器,以及 SDK 中提供的简单帮助器框架将简单三角形渲染至屏幕。 本示例的完整源代码在 OpenGL ES SDK for Linux on ARM 和 OpenGL ES 2.0 SDK for Android 中提供。 本页不涵盖 EGL 的初始化,因此建议在这一部分中使用 SDK。

定义三角形顶点数据:

const float triangleVertices[] =
{
     0.0f,  0.5f, 0.0f,
    -0.5f, -0.5f, 0.0f,
     0.5f, -0.5f, 0.0f,
};

以及三角形颜色值:

const float triangleColors[] =
{
    1.0, 0.0, 0.0, 1.0,
    0.0, 1.0, 0.0, 1.0,
    0.0, 1.0, 0.0, 1.0,
};

 

至应用程序的入口点将设置平台并初始化 EGL。

int main(void)
{
    /* Intialize the Platform object for platform specific functions. */
    Platform *platform = Platform::getInstance();

    /* Initialize windowing system. */
    platform->createWindow(WINDOW_W, WINDOW_H);

    /* Initialize EGL. */
    EGLRuntime::initializeEGL(EGLRuntime::OPENGLES2);
    EGL_CHECK(eglMakeCurrent(EGLRuntime::display, EGLRuntime::surface, EGLRuntime::surface, EGLRuntime::context));

    /* Initialize OpenGL ES graphics subsystem. */
    setupGraphics(WINDOW_W, WINDOW_H);

    bool end = false;
    /* The rendering loop to draw the scene. */
    while(!end)
    {
        /* If something has happened to the window, end the sample. */
        if(platform->checkWindow() != Platform::WINDOW_IDLE)
        {
            end = true;
        }
        /* Render a single frame */
        renderFrame();

        /* 
         * Push the EGL surface color buffer to the native window.
         * Causes the rendered graphics to be displayed on screen.
         */
        eglSwapBuffers(EGLRuntime::display, EGLRuntime::surface);
    }

    /* Shut down EGL. */
    EGLRuntime::terminateEGL();

    /* Shut down windowing system. */
    platform->destroyWindow();

    /* Shut down the Platform object*/
    delete platform;

    return 0;
}

这一工作的大部分在 setupGraphics  和 renderFrame 中进行。

此函数从 main 中调用,窗口大小则作为输入传递。 该函数将加载顶点和片段着色器,进行编译,并将它们链接至将在应用程序的其余部分中使用的程序。

bool setupGraphics(int width, int height)
{
    /* Full paths to the shader files */
    string vertexShaderPath = "Triangle_triangle.vert"; 
    string fragmentShaderPath = "Triangle_triangle.frag";

    GLuint vertexShaderID = 0;
    GLuint fragmentShaderID = 0;

    /* Initialize OpenGL ES. */
    GL_CHECK(glEnable(GL_BLEND));
    /* Should do: src * (src alpha) + dest * (1-src alpha). */
    GL_CHECK(glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA));

    /* Process shaders. */
    Shader::processShader(&vertexShaderID, vertexShaderPath.c_str(), GL_VERTEX_SHADER);
    Shader::processShader(&fragmentShaderID, fragmentShaderPath.c_str(), GL_FRAGMENT_SHADER);

    programID = GL_CHECK(glCreateProgram());
    if (programID == 0)
    {
        //Could not create Program error
        return false;
    }

    GL_CHECK(glAttachShader(programID, vertexShaderID));
    GL_CHECK(glAttachShader(programID, fragmentShaderID));
    GL_CHECK(glLinkProgram(programID));
    GL_CHECK(glUseProgram(programID));

    /* Positions. */
    GL_CHECK(iLocPosition = glGetAttribLocation(programID, "a_v4Position"));
    /* Fill colors. */
    GL_CHECK(iLocFillColor = glGetAttribLocation(programID, "a_v4FillColor"));

    GL_CHECK(glViewport(0, 0, width, height));

    /* Set clear screen color. */
    GL_CHECK(glClearColor(0.0f, 0.0f, 1.0f, 1.0f));

    return true;
}

这会在每个循环中调用一次,并将顶点和颜色数据发送到 GPU,以便在下一次调用  eglSwapBuffers 时进行渲染。

void renderFrame(void)
{
   GL_CHECK(glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT));
   GL_CHECK(glUseProgram(programID));

    /* Pass the triangle vertex positions to the shader */
    GL_CHECK(glVertexAttribPointer(iLocPosition, 3, GL_FLOAT, GL_FALSE, 0, triangleVertices));

    GL_CHECK(glEnableVertexAttribArray(iLocPosition));

    if(iLocFillColor != -1)
    {
        /* Pass the vertex colours to the shader */
        GL_CHECK(glVertexAttribPointer(iLocFillColor, 4, GL_FLOAT, GL_FALSE, 0, triangleColors));
        GL_CHECK(glEnableVertexAttribArray(iLocFillColor));
    }

    GL_CHECK(glDrawArrays(GL_TRIANGLES, 0, 3));
}

顶点着色器和片段着色器比较琐碎:

顶点:

attribute vec4 a_v4Position;
attribute vec4 a_v4FillColor;

varying vec4 v_v4FillColor;

void main()
{
    v_v4FillColor = a_v4FillColor;
    gl_Position = a_v4Position;
}

片段:

precision mediump float;

varying vec4 v_v4FillColor;

void main()
{
        gl_FragColor = v_v4FillColor;
}

 

OpenGL ES SDK


Viewing all articles
Browse latest Browse all 125

Trending Articles