Hello, and welcome to my exploration of the OpenGL API. OpenGL is a specification for a software library that gives developers hardware-independent access to the computing power of the GPU, a key component in rendering high-performance real-time graphics. In the following series of articles, I will attempt to explain the various technical advances and design decisions that, over time, have led a small triangle rasterizer to become the complex system it is today.
This series is intended for aspiring graphics programmers, already familiar with the mathematics of 3D graphics and the syntax of C. I will be spending no time here on either of those subjects, and a limited amount of time on API-agnostic graphics concepts. The star of the show is OpenGL itself, and how to use the API to its fullest potential.
Below, I will try my best to maintain a table of contents with links to every post. Maybe I'll write something to do this for me.
Table of Contents
Alright! To begin, here are some fundamentals to OpenGL.
OpenGL is a Specification, not a Library
The statement that OpenGL is not an actual piece of software often confuses newcomers. It is extraordinarily important to realize that the OpenGL Specification defines a set of functions and what they do, but does not provide a particular implementation – much like the C++ Standard Template Library. Operating systems and hardware vendors are left to implement the API themselves in the form of drivers. Naturally, this leads to some discrepancies between implementations. To complicate matters, vendors can include their own proprietary extensions within drivers, increasing the fragmentation of functionality. Many of the common extension problems were solved with the Core Profile, which significantly changed the specification. As a result, it has become much easier to write robust, multiplatform code in recent years. However, it is still important to be mindful of driver discrepancies and extensions, especially for more specialized or recent OpenGL functionality.
OpenGL Operates on a Global Context
The OpenGL API is a set of C-style functions that all perform operations on a global state bound to a single thread. The context can be bound to different threads, though at a performance cost worth avoiding. As a result, all interactions with OpenGL should be confined to one thread. This complicates multi-threaded rendering, but I will discuss that later.
Also important to remember is the fragility of global state. A good – though inefficient – rule of thumb is to unset all state set and to unbind every resource bound when one is done using it (I will interchangeably refer to both of these operations as state changes). This ensures that the state is clean and not prone to unwanted behavior. However, with a careful tracing of the code path, many state changes can be deemed redundant and removed.
OpenGL is Asynchronous
Communication does not come easy for the CPU and GPU. Memory on the GPU must be locked for the CPU to access it, and commands need to be buffered to send to the GPU in bulk. Since both of these may seem like inconveniences for the developer, OpenGL chose to manage locking and command buffering internally and asynchronously. As a great man once wrote, "This has made a lot of people very angry and been widely regarded as a bad move." Most often, it is not a problem; but the resulting lack of control results in frustration in more performant use-cases, which we will look at later.
OpenGL Does Not Create its Own Context
OpenGL was designed to operate on an internal context, but there is no particular specification to create or manage this context. This responsibility was left to the platform developers. Since each platform has radically different windowing systems, setting up an OpenGL context can be a huge pain. Fortunately, cross-platform solutions to this problem exist, and are great for getting a context up and running. However, these APIs often lack OS-feature support on non-Windows platforms, which makes the OSX user in me sad.
Hopefully this has made OpenGL a little less nebulous of a topic, and with the next article, I can dive right into the nuts and bolts.