Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to develop OpenGL ES (GLES) 2.0 applications on Linux?

I would like to develop OpenGL ES 2.0 apps on my Ubuntu machine. I could not find any libraries/emulators that support GLES 2.0 yet. Any suggestions?

like image 218
l.thee.a Avatar asked Sep 28 '10 02:09

l.thee.a


3 Answers

GLFW, Mesa, Ubuntu 16.04 AMD64

This was not easy to setup on Ubuntu 14.04, but now it just works.

sudo apt-get install libglfw3-dev libgles2-mesa-dev
gcc glfw_triangle.c -lGLESv2 -lglfw

Output:

glfw_triangle.c

#include <stdio.h>
#include <stdlib.h>

#define GLFW_INCLUDE_ES2
#include <GLFW/glfw3.h>

static const GLuint WIDTH = 800;
static const GLuint HEIGHT = 600;
static const GLchar* vertex_shader_source =
    "#version 100\n"
    "attribute vec3 position;\n"
    "void main() {\n"
    "   gl_Position = vec4(position, 1.0);\n"
    "}\n";
static const GLchar* fragment_shader_source =
    "#version 100\n"
    "void main() {\n"
    "   gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);\n"
    "}\n";
static const GLfloat vertices[] = {
     0.0f,  0.5f, 0.0f,
     0.5f, -0.5f, 0.0f,
    -0.5f, -0.5f, 0.0f,
};

GLint common_get_shader_program(const char *vertex_shader_source, const char *fragment_shader_source) {
    enum Consts {INFOLOG_LEN = 512};
    GLchar infoLog[INFOLOG_LEN];
    GLint fragment_shader;
    GLint shader_program;
    GLint success;
    GLint vertex_shader;

    /* Vertex shader */
    vertex_shader = glCreateShader(GL_VERTEX_SHADER);
    glShaderSource(vertex_shader, 1, &vertex_shader_source, NULL);
    glCompileShader(vertex_shader);
    glGetShaderiv(vertex_shader, GL_COMPILE_STATUS, &success);
    if (!success) {
        glGetShaderInfoLog(vertex_shader, INFOLOG_LEN, NULL, infoLog);
        printf("ERROR::SHADER::VERTEX::COMPILATION_FAILED\n%s\n", infoLog);
    }

    /* Fragment shader */
    fragment_shader = glCreateShader(GL_FRAGMENT_SHADER);
    glShaderSource(fragment_shader, 1, &fragment_shader_source, NULL);
    glCompileShader(fragment_shader);
    glGetShaderiv(fragment_shader, GL_COMPILE_STATUS, &success);
    if (!success) {
        glGetShaderInfoLog(fragment_shader, INFOLOG_LEN, NULL, infoLog);
        printf("ERROR::SHADER::FRAGMENT::COMPILATION_FAILED\n%s\n", infoLog);
    }

    /* Link shaders */
    shader_program = glCreateProgram();
    glAttachShader(shader_program, vertex_shader);
    glAttachShader(shader_program, fragment_shader);
    glLinkProgram(shader_program);
    glGetProgramiv(shader_program, GL_LINK_STATUS, &success);
    if (!success) {
        glGetProgramInfoLog(shader_program, INFOLOG_LEN, NULL, infoLog);
        printf("ERROR::SHADER::PROGRAM::LINKING_FAILED\n%s\n", infoLog);
    }

    glDeleteShader(vertex_shader);
    glDeleteShader(fragment_shader);
    return shader_program;
}

int main(void) {
    GLuint shader_program, vbo;
    GLint pos;
    GLFWwindow* window;

    glfwInit();
    glfwWindowHint(GLFW_CLIENT_API, GLFW_OPENGL_ES_API);
    glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 2);
    glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0);
    window = glfwCreateWindow(WIDTH, HEIGHT, __FILE__, NULL, NULL);
    glfwMakeContextCurrent(window);

    printf("GL_VERSION  : %s\n", glGetString(GL_VERSION) );
    printf("GL_RENDERER : %s\n", glGetString(GL_RENDERER) );

    shader_program = common_get_shader_program(vertex_shader_source, fragment_shader_source);
    pos = glGetAttribLocation(shader_program, "position");

    glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
    glViewport(0, 0, WIDTH, HEIGHT);

    glGenBuffers(1, &vbo);
    glBindBuffer(GL_ARRAY_BUFFER, vbo);
    glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
    glVertexAttribPointer(pos, 3, GL_FLOAT, GL_FALSE, 0, (GLvoid*)0);
    glEnableVertexAttribArray(pos);
    glBindBuffer(GL_ARRAY_BUFFER, 0);

    while (!glfwWindowShouldClose(window)) {
        glfwPollEvents();
        glClear(GL_COLOR_BUFFER_BIT);
        glUseProgram(shader_program);
        glDrawArrays(GL_TRIANGLES, 0, 3);
        glfwSwapBuffers(window);
    }
    glDeleteBuffers(1, &vbo);
    glfwTerminate();
    return EXIT_SUCCESS;
}

The key line lines of code are:

#define GLFW_INCLUDE_ES2
#include <GLFW/glfw3.h>

GLFW_INCLUDE_ES2 is documented at: http://www.glfw.org/docs/latest/build_guide.html#build_macros and a quick look at the source shows that it forwards to GLES:

 #elif defined(GLFW_INCLUDE_ES2)
  #include <GLES2/gl2.h>
  #if defined(GLFW_INCLUDE_GLEXT)
   #include <GLES2/gl2ext.h>
  #endif

This source seems to be written in the common subset of GLES and OpenGL (like much of GLES), and also compiles with -lGL if we remove the #define GLFW_INCLUDE_ES2.

If we add things which are not in GLES like immediate rendering glBegin, link fails as expected.

See also: https://askubuntu.com/questions/244133/how-do-i-get-egl-and-opengles-libraries-for-ubuntu-running-on-virtualbox

Credits: genpfult made the code much more correct.

ARM Mali OpenGL ES SDK

  • download from: http://malideveloper.arm.com/resources/sdks/opengl-es-sdk-for-linux/
  • open the documentation HTML on a browser
  • follow the "Quick Start Guide", it's simple

Contains several interesting open source examples + windowing system boilerplate (X11 + EGL).

The build system supports easy cross compilation for ARM / Mali SoCs, but I haven't tested that yet.

The key component included seems to be the "OpenGL ES Emulator" http://malideveloper.arm.com/resources/tools/opengl-es-emulator/ which "maps OpenGL ES 3.2 API calls to the OpenGL API". But that does not ship with source, only precompiled.

Uses a custom enterprisey EULA that appears to be permissive, but yeah, ask your lawyer.

Tested on SDK v2.4.4.


Mesa supports it. If you want to restrict yourself to OpenGL ES only then you'll need to build it into a separate directory and then add the appropriate include and library directories.

like image 7
Ignacio Vazquez-Abrams Avatar answered Oct 21 '22 17:10

Ignacio Vazquez-Abrams


Update:

You can (still) use PowerVR SDK and now it supports Vulkan as well. Updated links:

  • PowerVR SDK page: https://www.imgtec.com/developers/powervr-sdk-tools/powervr-sdk/
  • Installers download page: https://www.imgtec.com/developers/powervr-sdk-tools/installers/
  • Github repo: https://github.com/powervr-graphics/Native_SDK

At the time of my original answer, PowerVR SDK was the most complete solution (Mesa gained full OpenGL ES 2.0 support with its 3.1 release according to its Wikipedia page).

Now, Mesa and Mali SDK can also be a choice. For detailed info on those, please refer to this detailed answer by Ciro Santilli 冠状病毒审查六四事件法轮功

Original Answer:

You can use POWERVR SDK to emulate Opengl es on your PC. You can download the SDK here. The archive provides the necessary steps to install the emulation libraries as a documentation file and includes tutorials and demo applications with source codes.

like image 5
Bertan Gundogdu Avatar answered Oct 21 '22 16:10

Bertan Gundogdu