1 \input texinfo @c -*-texinfo-*-
8 @set UPDATED 1 February 2013
11 This manual is for Figl (version @value{VERSION}, updated
14 Copyright 2013 Andy Wingo and others.
17 Figl is free software: you can redistribute and/or modify it and its
18 documentation under the terms of the GNU Lesser General Public License
19 as published by the Free Software Foundation, either version 3 of the
20 License, or (at your option) any later version.
22 Figl is distributed in the hope that it will be useful, but WITHOUT
23 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
24 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General
25 Public License for more details.
27 You should have received a copy of the GNU Lesser General Public
28 License along with this program. If not, see
29 @uref{http://www.gnu.org/licenses/}.
32 Portions of this document were generated from the upstream OpenGL
33 documentation. The work as a whole is redistributable under the
34 license above. Sections containing generated documentation are
35 prefixed with a specific copyright header.
38 @dircategory The Algorithmic Language Scheme
40 * Figl: (figl.info). An OpenGL interface for Guile.
45 @subtitle version @value{VERSION}, updated @value{UPDATED}
49 @vskip 0pt plus 1filll
60 * Introduction:: The what, why, and how of Figl.
62 * GL:: A Scheme interface to OpenGL.
63 * GLU:: The GL Utility library.
64 * GLX:: Using OpenGL with the X Window System.
65 * GLUT:: The GL Utility Toolkit.
67 * FAQ:: Figl answers questions.
82 Figl is the Foreign Interface to GL: an OpenGL binding for Guile.
84 OpenGL is a family of APIs and layers. The following chapters discuss
85 the parts of OpenGL and how they are bound by Figl.
87 But before that, some notes on the Figl binding as a whole.
90 * About Figl:: The structure of the binding.
97 Figl is a @dfn{foreign} interface to OpenGL because it uses the
98 dynamic @dfn{foreign function interface} provided by Guile 2.0,
99 providing access to OpenGL without any C code at all. In fact, much
100 of Figl (and this manual) is automatically generated from upstream API
101 specifications and documentation.
103 We have tried to do a very complete job at wrapping OpenGL, and
104 additionally have tried to provide a nice Scheme interface as well.
105 Our strategy has been to separate the binding into low-level and
108 The low-level bindings correspond exactly with the GL specification,
109 and are well-documented. However, these interfaces are not so nice to
110 use from Scheme; output arguments have to be allocated by the caller,
111 and there is only the most basic level of type checking, and no sanity
112 checking at all. For example, you can pass a bytevector of image data
113 to the low-level @code{glTexImage2D} procedure, but no check is made
114 that the dimensions you specify actually correspond to the size of the
115 bytevector. This function could end up reading past the end of the
116 bytevector. Worse things can happen with procedures that write to
117 arrays, like @code{glGetTexImage}.
119 The high-level bindings are currently a work in progress, and are
120 being manually written. They intend to be a complete interface to the
121 GL, without the need to use the low-level bindings. However, the
122 low-level bindings will always be available for you to use if needed,
123 and have the advantage that their behavior is better documented and
124 specified by OpenGL itself.
126 Low-level bindings are accessed by loading the @code{(figl
127 @var{module} low-level)}, for example via:
130 (use-modules (figl gl low-level))
133 The high-level modules are named like @code{(figl @var{module})}, for
134 example @code{(figl gl)}.
142 * About OpenGL:: Know the past to understand the present.
143 * GL Contexts:: Finding a square of pixels.
144 * Rendering:: How to paint.
145 * Low-Level GL:: Primitive interface to OpenGL.
146 * GL Enumerations:: Enumerated values.
147 * GL Extensions:: Beyond core OpenGL.
152 @section About OpenGL
154 OpenGL is a standard API for drawing three-dimensional graphics. From
155 its origin in Silicon Graphics's workstations the early 1990s, today
156 it has become ubiquitous, with implementations on mobile phones,
157 televisions, tablets, desktops, and even web browsers.
159 OpenGL has been able to achieve such widespread adoption not just
160 because it co-evolved with powerful graphics hardware, but also
161 because it was conceived of as an interface specification and not a
162 piece of source code. In fact, these days it is a family of APIs,
163 available in several flavors and versions:
167 This series of specifications started with the original releases in
168 1992, and ended with OpenGL 1.5 in 2003. This era corresponds to a
169 time when graphics cards were less powerful and more special-purpose,
170 with dedicated hardware to handle such details as fog and lighting.
171 As such the OpenGL 1.x API reflects the capabilities of these special
175 By the early 2000s, graphics hardware had become much more
176 general-purpose and needed a more general-purpose API. The so-called
177 @dfn{fixed-function rendering pipeline} of the earlier years was
178 replaced with a @dfn{programmable rendering pipeline}, in which
179 effects that would have required special hardware were instead
180 performed by custom programs running on the graphics card. OpenGL
181 added support for allocating @dfn{buffer objects} on the graphics
182 card, and for @dfn{shader programs}, which did the actual rendering.
183 In time, this buffer-focused API came to be the preferred form of
187 OpenGL ES was a ``cut-down'' version of OpenGL 2.x, designed to be
188 small enough to appeal to embedded device vendors. OpenGL ES 1.x
189 removed some of the legacy functionality from OpenGL, while adding
190 interfaces to use fixed-point math, for devices without floating-point
191 units. OpenGL ES 2.x went farther still, removing the fixed-function
192 pipeline entirely. OpenGL ES 2.x is common on current smart phone
195 @item OpenGL 3.x and above
196 The OpenGL 3.x series followed the lead of OpenGL ES, first
197 deprecating (in 3.0) and then removing (in 3.1) the fixed-function
198 pipeline. OpenGL 3.0 was released in 2008, but the free Mesa
199 impementation only began supporting it in 2012, so it is currently
200 (@value{UPDATED}) less common.
203 Figl wraps the OpenGL 2.1 API. It's a ubiquitous subset of the OpenGL
204 implementations that are actually deployed in the wild; its legacy API
205 looks back to OpenGL 1.x, while the buffer-oriented API is compatible
212 All this talk about drawing is very well and good, but how do you
213 actually get a canvas? Interestingly enough, this is outside the
214 purview of the OpenGL specification. There are specific ways to get
215 an @dfn{OpenGL context} for each different windowing system that is
216 out there. OpenGL is all crayons and no paper.
218 For the X window system, there is a standard API for creating a GL
219 context given a window (or a drawable), @dfn{GLX}. @xref{GLX}, for
220 more information on its binding in Guile.
222 Bseides creating contexts from native windows or drawables, each
223 backend also supports functions to make a context @dfn{current}. The
224 OpenGL API is stateful; you can think of each call as taking an
225 implicit @dfn{current context} parameter, which holds the current
226 state of the GL and is operated on by the function in question.
227 Contexts are thread-specific, and one context should not be active on
228 more than one thread at a time.
230 All calls to OpenGL functions must be made while a context is active;
231 otherwise the result is undefined. Hopefully while you are getting
232 used to this rule, your driver is nice enough not to crash on you if
233 you call a function outside a GL context, but it's not even required
234 to do that. Backend-specific functions may or may not require a
235 context to be current; for example, Windows requires a context to be
236 current, wheras GLX does not.
238 There have been a few attempts at abstracting away the need for
239 calling API specific to a given windowing system, notably GLUT and
240 EGL. GLUT is the older of the two, and though it is practically
241 unchanged since the mid-1990s, it is still widely used on desktops.
242 @xref{GLUT}, for more on GLUT.
244 EGL is technically part of OpenGL ES, and was designed with the modern
245 OpenGL API and mobile hardware in mind, though it also works on the
246 desktop. Figl does not yet have an EGL binding.
252 To draw with OpenGL, you obtain a drawing context (@pxref{GL
253 Contexts}) and send @dfn{the GL} some geometry. (You can think of the
254 GL as a layer over your graphics card.) You can give the GL points,
255 lines, and triangles in three-dimensional space. You configure your
256 GL to render a certain part of space, and it takes your geometry,
257 rasterizes it, and writes it to the screen (when you tell it to).
259 That's the basic idea. You can customize most parts of this
260 @dfn{rendering pipeline}, by specifying attributes of your geometry
261 with the OpenGL API, and by programmatically operating on the geometry
262 and the pixels with programs called @dfn{shaders}.
264 GL is an @dfn{immediate-mode} graphics API, which is to say that it
265 doesn't keep around a scene graph of objects. Instead, at every frame
266 you as the OpenGL user have to tell the GL what is in the world, and
267 how to paint it. It's a fairly low-level interface, but a powerful
269 @uref{http://www.opengl.org/wiki/Rendering_Pipeline_Overview}, for
272 In the old days of OpenGL 1.0, it was common to call a function to
273 paint each individual vertex. You'll still see this style in some old
274 tutorials. This quickly gets expensive if you have a lot of vertexes,
275 though. This style, known as @dfn{Legacy OpenGL}, was deprecated and
276 even removed from some versions of OpenGL. See
277 @uref{http://www.opengl.org/wiki/Legacy_OpenGL}, for more on the older
280 Instead, the newer thing to do is to send the geometry to the GL in a
281 big array buffer, and have the GL draw geometry from the buffer. The
282 newer functions like @code{glGenBuffers} allocate buffers, returning
283 an integer that @dfn{names} a buffer managed by the GL. You as a user
284 can update the contents of the buffer, but when drawing you reference
285 the buffer by name. This has the advantage of reducing the chatter
286 and data transfer between you and the GL, though it can be less
289 So which API should you use? Use what you feel like using, if you
290 have a choice. Legacy OpenGL isn't going away any time soon on the
291 desktop. Sometimes you don't have a choice, though; for example, when
292 targeting a device that only supports OpenGL ES 2.x, legacy OpenGL is
295 But if you want some advice, we suggest that you use the newer APIs.
296 Not only will your code be future-proof and more efficient on the GL
297 level, reducing the number of API calls improves performance, and it
298 can reduce the amount of heap allocation in your program. All
299 floating-point numbers are currently allocated on the heap in Guile,
300 and doing less floating-point math in tight loops can only be a good
305 @section Low-Level GL
306 @include low-level-gl.texi
309 @node GL Enumerations
310 @section GL Enumerations
311 @include low-level-gl-enums.texi
315 @section GL Extensions
318 The future is already here -- it's just not very evenly distributed.
323 Before interfaces end up in core OpenGL, the are usually present as
324 vendor-specific or candidate extensions. Indeed, the making of an
325 OpenGL standard these days seems to be a matter of simply collecting a
326 set of mature extensions and making them coherent.
328 Figl doesn't currently provide specific interfaces for extensions.
329 Perhaps it should, but that's a lot of work that we haven't had time
330 to do. Contributions are welcome.
332 In the meantime, if you know enough about GL to know that you need an
333 extension, you can define one yourself -- after all, Figl is all a
334 bunch of Scheme code anyway.
336 For example, let's say you decide that you need to render to a
337 framebuffer object. You go to @uref{http://www.opengl.org/registry/}
338 and pick out an extension, say
339 @uref{http://www.opengl.org/registry/specs/ARB/framebuffer_object.txt}.
341 This extension defines a procedure, @code{GLboolean
342 glIsRenderBuffer(GLuint)}. So you define it:
345 (use-modules (figl gl runtime) (figl gl types))
346 (define-gl-procedure (glIsRenderBuffer (buf GLuint) -> GLboolean)
347 "Render buffer predicate. Other docs here.")
350 And that's that. It's a low-level binding, but what did you expect?
352 Note that you'll still need to check for the availability of this
353 extension at runtime with @code{(glGetString GL_EXTENSIONS)}.
360 * Low-Level GLU:: Primitive interface to ``glu'' functionality.
364 @section Low-Level GLU
365 @include low-level-glu.texi
372 * Low-Level GLX:: Primitive interface to ``glX'' functionality.
373 * GLX Enumerations:: GLX enumerated values.
378 @section Low-Level GLX
379 @include low-level-glx.texi
382 @node GLX Enumerations
383 @section GLX Enumerations
384 @include low-level-glx-enums.texi
390 TODO: Write GLUT documentation.
396 TODO: Write about things readers will want to know (instead of
397 commenting them in the source :)
401 @unnumbered Function Index