Skip to content

erlangsters/opengl-x.y-generator

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

10 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

OpenGL binding generator for the BEAM

Erlangsters Repository Supported Erlang/OTP Versions Current Version License Build Status

The OpenGL binding generator for the Erlang and Elixir programming language. Generated bindings work exclusively with the EGL binding (and have an internal dependency on it).

The generated bindings are hosted in those repositories for convenience.

You will need to pair up one of those bindings with the EGL binding (for a OpenGL context and surface) and perhaps the GLFW binding (to provide a window).

Written by the Erlangsters community and released under the MIT license.

Getting started

The generator is able to generate a binding for OpenGL version 3.3, 4.1 and 4.6, and all OpenGL ES versions.

With little effort, it's technically easy to make it generate a binding for other versions but this restriction exists for a reason: only a subset of the available versions are relevant in today's world.

To generate a binding, run this command after it's compiled with rebar3 escriptize.

./_build/default/bin/bin_opengl <api> <version>

Where <api> can be either gl or gles, and version is x.z.

It reads the gl-specs.xml and binding-specs.conf to generate gl.h, gl.erl and gl.c, which can then be included in your project. Note that in-source documentation is also generated.

For obvious reason, the API cannot be kept entirely the same and adjustments had to be made. However, it follows a rigorous set of mapping rules which are documented in the sections below.

Binding specifications

The good thing about OpenGL APIs is that they're set in stone (at least at the time of writing, in 2025) and won't change since the development has shifted to Vulkan. It makes generating bindings for it simpler.

The strategy is to start with the official OpenGL APIs specification in the XML format (as provided by the Khronos Group).

Snippet of the XML specifications.

<command>
    <proto>void <name>glProgramUniform4ui64vNV</name></proto>
    <param class="program"><ptype>GLuint</ptype> <name>program</name></param>
    <param><ptype>GLint</ptype> <name>location</name></param>
    <param><ptype>GLsizei</ptype> <name>count</name></param>
    <param kind="Vector4" len="count*4">const <ptype>GLuint64EXT</ptype> *<name>value</name></param>
</command>

Instead of relying on heuristic detection and guesswork to translate OpenGL functions into their BEAM-equivalent forms, the generator uses manually written 'binding specifications' to explicitly define the correct mapping.

Snippet of the binding specifications.

{"glHint", [ % XXX: update once final.
  {name, "hint"},
  {params, [
    {"Target", {gl_enum, "HintTarget"}},
    {"Mode", {gl_enum, "HintMode"}}
  ]},
  {return, "ok"}
]}

With both pieces of data combined, the generator is able to write pretty OpenGL bindings that adhere to the specification.

Thread safety

The generated bindings will only work with the specified EGL binding. This is because OpenGL commands execute in a context and the API is not thread-safe. Therefore, it relies on the EGL binding which re-arrange their execution to map what your application is doing. xxx

Simply assume that a BEAM process is equal to a OS thread in your application and all thread-related specifics apply in your code the exact same way. xxx

Refer to the documentation of the EGL binding for more information.

API mapping (informal)

To be written.

API mapping (formal)

To be written.