OpenGL: let’s break it down

Ok, so now that we’ve got makefiles down, let’s talk about the structure of the actual program. I know this is the scary bit, but we’ll get through this together. The image above is my basic graphics program. It produces a single, blank white window. There’s no text in the title bar and the only way to interact with it is to press ‘q’ to exit.

Now, to the breakdown. First, let’s take a look at the headers. I like to keep my standard OpenGL headers in their own header file called glglobal.h. Here’s what that looks like:

#if defined (WIN32)

#if defined(_APPLE_)
#include <OpenGL/gl.h>
#include <OpenGL/glu.h>
#include <GLUT/glut.h>
#include <GL/gl.h>
#include <GL/glu.h>
#include <GL/glut.h>

#include "Utils.h"

That’s the whole thing. Except for the last line, this is universal and can be used on any computer since it checks the OS. We’ll take a quick look at Utils.h but I’m not going to go in depth on the implementation. You can feel free to implement these yourself, they’re very helpful.

#ifndef DESUTILS_H
#define DESUTILS_H

// This will sleep for ms milliseconds.  It calls nanosleep().
void delay(int ms);

extern void setWorldWin(GLdouble left,GLdouble right,
	GLdouble bottom,GLdouble top);

extern void setViewPort(GLint left,GLint right,GLint bottom,GLint top);


The delay function is just a wrapper for nanosleep because I don’t like converting from milliseconds to nanoseconds. I’ll confess I don’t remember why I wrote setWorldWin. It’s not in the basic program above and looking at the implementation didn’t reveal any specific purpose. SetViewPort exists for the sheer purpose of simplifying entry of the window dimensions. glViewport takes arguments for bottom left coordinates x,y and then the width and height of the window. But that irritates me. The beauty of programming is you can write a wrapper function for just about anything.

Onward! Next up, the initialization function.

void myInit(){
	gluOrtho2D(0.0, (GLdouble) screenW, 0.0, (GLdouble) screenH);

This one sets up your window, let’s take a look,

  • glClearColor: this sets the background color of your window. the arguments it takes are red, green, blue, alpha. All values must be between 0 and 1. Alpha sets the opaque-ness of the background but I don’t really see any difference  between 0.0 alpha and 1.0 alpha. If you know how this works more in-depth, please leave me a comment because googling was minimally helpful.
  • glColor3f: this function sets the color of what you draw. Generally you’ll reset this as you go, but I’ve always found it helpful to set it at the beginning just in case. It has definitely happened to me where I couldn’t figure out what the problem with my drawing function was and it turned out to be that I’d forgotten to set the color.
  • glPointSize: you may have guessed it, but this function sets the point size. It takes a GLfloat and defaults to 1.0 if you don’t set it.
  • glMatrixMode: this sets the matrix stack future matrix operations will be applied to. You have 3 options for this one,
    • GL_COLOR
  • glLoadIdentity: this function replaces whatever the current matrix is with the identity matrix. we’re not going to worry about that too much right now
  • glOrtho2d: last, but not least, this function sets up a 2D orthographic viewing area. It takes four arguments, all of type GLdouble in the order left, right, bottom, top. they set up the horizontal and vertical clipping planes.

Ok, guys, stay with me. We’re going to skip to the main() function now.

int main(int argc, char** argv){
	glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB);

Most of the time, especially if you’re a relatively novice programmer, main() takes no arguments. Argc is the number of command line arguments, argv is an array of character pointers that is the list of arguments. argv[0] is always the program name. The glutInit function takes the address of argc and argv (which is already an address). This function initializes the glut (short for GLutilities) library. So let’s take a quick tour through the main function.

  • glutInitDisplayMode: takes one argument which is usually the bitwise OR of Glut display mode bit masks. You can read about the options here.
  • glutInitWindowSize: sets the size of the window. At the beginning of the program I set constants for screen width and height that are used here and in the gluOrtho2d function in the init function. I’ve found it’s dangerous to not set these as variables because if you update one set of values and not the other, you’ll get some very wonky results.
  • glutCreateWindow: creates the window, takes a string argument of what you want in the title bar. If you have any short instructions, such as “press q to exit” this is a good place for them
  • glutDisplayFunction: takes a function as an argument, this is the one that does the heavy lifting of actually calculating and displaying your program
  • glutKeyboardFuntion: sets up a handler for keyboard output. The handler in this function comes from my personal library and is as simple as
    • if(keyboard input is q or Q) { close window }
  • myInit: the function we ran through above that initializes all the junk
  • glutMainLoop: this function just runs the display function passed to glutDisplayFunction over and over

There we go! You made it through the hard bits! Perhaps you can understand why I keep this all in a template now. Finally let’s take a quick look at the display function stub.

void myDisplay(){


So this is it, the real deal. Any time you’re going to put something new on the screen, you want to call glClears so you’re not drawing endlessly over your old shapes. glFlush pushes the drawing or image you’ve created to the window buffer to be shown.

It’s as easy as that! (please, sense my sarcasm) If you have any questions about this post or there’s another graphics related topic you’d like me to cover, please leave a comment below

Happy coding!

The Setup

So here I was, thinking what would be useful for someone trying to learn graphics? A cheat sheet! and I set out to make a blog post about it. But it’s been awhile since I sat down and spent some quality time with openGL and it turns out, if you’re getting back into it like I am or if you’re just starting out, you probably need more of a blueprint. so that’s what we’re going to do first.

Before you even look at writing any C++ code, there’s some setup that needs to happen. My setup is fairly robust, built off a skeleton given out by my professor. I’m going to show you what I have but try to mention where it could be slimmed down.

First things first: file structure. I have a parent directory where all my graphics shenanigans lives called ‘glMathMagic’. That’s not terribly important but all the directories I’m about to talk about live in there. Inside glMathMagic, I have 4 directories and a few miscellaneous files. They go like this:

  • Directories:
    • src: this is where your main program files will go. I like to keep subfolders in here for each separate project so the makefiles don’t get all jumbled up. more on this later.
    • include: header files go in here
    • lib: library cpp files (aka corresponding to header files in include) go in here
    • bin: executables and any data files (.dat) go in here
  • Files
    • graphics.cfg: definitions for a bunch of macros for your makefiles. super important to have these defined somewhere and since there’s 2 makefiles you need, might as well keep this here in your upper directory to be referenced by both. more on this later.
    • template.cpp: I keep a skeleton graphics program that has all the window setup stuff in it to copy into src for new projects. don’t worry about this too much at the moment but I’ll share it later anyway
    • makefile: this is also sort of a skeleton backup in case I lose my other makefiles in a freak accident. not really important.

Let’s talk about makefiles. Maybe you love them. Maybe you’re terrified of them. I am both. This setup is for programming on the linux command line, which is important because makefiles are really just fancy bash scripting. We can get into that on a later date but for now all you need to know is I’m running Ubuntu. So here’s a quick rundown in case you’re super new: when you compile on the command line, you list the files you need. When you have lots of files in lots of folders, that gets really hard to keep track of. A makefile is basically a little script program you keep on hand to run all the necessary commands for you. I keep two of them, one in lib and one with each project in src.

Here’s what I have in the lib makefile:

include $(TOP)/graphics.cfg

		sadielib.cpp \

		$(VPATH)/sadielib.o \



all: $(UTILLIB)

# $(CXX) -MD creates a .d file and a .o file in the VPATH directory
$(LIBDEP):      $(VPATH)/%.d:   %.cpp
	-mkdir -p $(VPATH)
	$(CXX) -MD $(CXXFLAGS)  -o $(@:.d=.o) $<

$(OBJECTS): $(VPATH)/%.o: %.cpp
	$(CXX) $(CXXFLAGS) -o $@ $<


	rm -rf $(UTILLIB) $(VPATH)

include $(OBJECTS:.o=.d)

I’m not going to go in-depth with everything but there’s a few things you need to know.

  • stuff like $(VPATH) and $(CXXFLAGS) are defined in graphics.cfg in the parent folder
  • the basic setup of the main commands is
    target : [ dependency ]*
       [ tab  command  endl ]+
  • sadielib is my personal library of functions that are handy but not necessary, things I tend to use repeatedly. For example, the function to be able to press q to exit my graphics program is in there. Leave a comment down below if you’d like to hear more about my personal library. polyline is also a library I wrote but it’s wrappers for point and line classes.

Let’s move on to the makefile in src.

include $(TOP)/graphics.cfg

FILENAME = practice



# all the .o files need to be listed here.  Leave backslash off last list item



all: $(APP)

# $(CXX) -MD creates a .d file and a .o file in the VPATH directory
$(APPDEP):      $(VPATH)/%.d:   %.cpp
	-mkdir -p $(VPATH)
	$(CXX) -MD $(CXXFLAGS)  -o $(@:.d=.o) $<

$(OBJECTS): $(VPATH)/%.o: %.cpp
	$(CXX) $(CXXFLAGS) -o $@ $<

$(APP):  $(OBJECTS) $(LIBDIR)/libGraphicsUtils.a
	-mkdir -p $(BINDIR)
	-mkdir -p $(LIBDIR)
	make -C $(LIBDIR)
	$(LD) $(LDFLAGS) -o $@ $(OBJECTS) -l GraphicsUtils $(GLIBS) 

	rm -rf *.o *.d $(APP) $(VPATH)

# this generates errors on the first pass, but then these .d files
# get created for the second pass.  

include $(OBJECTS .o=.d) 

Ok so this one takes the archive that was built by the first makefile, libGraphicsUtils.a, and uses it to build your project file, FILENAME. In this example I have practice.cpp in src so I put FILENAME = practice.

You always want TOP to refer to that parent folder where graphics.cfg is. When I have subfolders in src and this makefile is in a subfolder, I change TOP = ../.. so it can still find everything.

Last, but not least, and probably most confusing, we’ll take a look at graphics.cfg.

# This is common for all graphics programs
# graphics library names

# first, figure out which OS we are working in (Macos = Darwin)
UNAME = $(shell uname)

ifeq ($(UNAME),Linux)
GLUT_LIB = glut
GLUI_LIB = glui

BINDIR = $(TOP)/bin
LIBDIR = $(TOP)/lib
INCLUDES = -I$(TOP)/include

#Compiler information
AR = ar
CC = gcc
CXX = g++
LD = g++
SYSLDFLAGS = -rdynamic
SHLDFLAGS = -s -export-dynamic -shared

ifeq ($(UNAME),Linux)
LIBAS += -ldl
FLAGS += -pthread


ifeq ($(UNAME),Linux)
GLIBS = -l$(GLUT_LIB) -l$(GLU_LIB) -l$(GL_LIB) -lm

ifeq ($(UNAME),Darwin)
GLIBS = -framework GLUT -framework Cocoa -framework OpenGL

VPATH = obj

# Define build rules


.SUFFIXES: .o .c .cpp .h

	$(CC) -c $(CFLAGS) -o $(VPATH)/$*.o $*.c

	$(CXX) -c $(CXXFLAGS) -o $(VPATH)/$*.o $*.cpp

So that’s all your definitions and shorthand you see up in the previous makefiles. you could put these in the makefiles, but as I mentioned before it’s just more streamlined to have them separately here.

Look at that, we’re all set up now! In my next post I’ll go into how to set up the program itself using C++ and OpenGL.

Happy Coding!