Wednesday, October 25, 2017

OpenGL Tutorial - Part 2 of 3

Welcome back to my three part OpenGL tutorial.  In the last part, we briefly introduced the idea of OpenGL, but in this part of the tutorial, we will guide the reader through the process of setting up a development environment so that they can write code and run programs in OpenGL.

Without any further ado, here are the steps.

1. Download Glut

The core OpenGL headers and libraries come from glut/freeglut.  Use the link below to download freeglut from the MSVC section (this was listed in a link with text "Download freeglut 3.0.0 for MSVC" as of this writing.)  Go ahead and keep the zip around for later reference.

2. Download Glew

Short for OpenGL Extension Wrangler Library.  This contains a lot of extended features that you may not need until you become more advanced with working in OpenGL.  You can obtain this from the link here:


3. Setup directories and copy files

Set up a directory so that you can copy/move the downloaded files from steps 1 and 2.  This can be mostly anywhere, but you may want to keep it simple.  For example, lets use:
  • Central root location for everything: E:\opengl
  • Place for code and projects to go: E:\opengl\projects
  • Put your library files (i.e. freeglut; other dependencies) in here: E:\opengl\lib
After creating the file structure above, unzip the downloads from steps 1 and 2 and paste their folders into E:\opengl\lib.  So your file tree should look something like:

E:\OPENGL
├───lib
│   ├───freeglut-3.0.0
│   └───glew-2.1.0
└───projects

Note that you can output cool text trees like this using the tree command in a terminal window on both Windows and Unix systems.

4. Create C++ Project

In this tutorial, we're going to create a simple OpenGL project to demonstrate some of its 3D capabilities.  This demo will just be a cube that bounces around inside of a 3D box, utilizing some simple math of calculating angles of the bounce off each wall, as well as the simple physics of constant animating velocity and rotation.

Fire up Visual Studio (in this guide, version 2015 is used) and create a new project through the dialog in File > New > Project.  In here, search for Visual C++ in the templates section on the left, and then select Empty Project from the middle.  Give the project a name, like DemoOpenGL, and also click on Browse to place the project in your projects directory from the previous step.

Now your file structure should appear similar to this:

E:\OPENGL
├───lib
│   ├───freeglut-3.0.0
│   └───glew-2.1.0
└───projects
    └───DemoOpenGL

4.1. Add First Source

First, we'll need to add at least one source file.  Right click on the DemoOpenGL project node in the Solution Explorer and navigate to Add > New Item.  Find Visual++ from the left, and select C++ file in the middle.  Name the file main.cpp and click the Add button.

Doing this enables some project settings for the next step so that we can configure properly.


5. Configuring your project

This step is an important one for anyone developing in OpenGL.  It is probably the most complicated one, and so its important to understand what's going on and become comfortable creating new projects with ease.

There's three things we basically need:

1. To see the OpenGL "include" header files.
2. To resolve external references via linked libraries
3. Runtime dlls

While you're doing this, be aware that there are two configurations: 32-bit and a 64-bit.  While headers are platform-independent, the dll's and libs are not, and hence, we will provide forked instructions for both platforms.

To make sure your build configurations have both a 32-bit and 64-bit setting, check out the box just to the right of where it says "Debug" on Visual Studio (up at the top, left of the middle).  Currently, it should by default say x86.  If you already have a setting in there for x64, then you should be fine.  The x86 is a 32-bit version while the x64 is the 64-bit version.  If not, then you can go inside to create a new build configuration (this should be simple).

5.1. Including headers

Inside Visual Studio, get to the project properties.  To do this, right click on your DemoOpenGL project node in the Solution Explorer and navigate to Properties.  Make sure the Configuration drop-down at the top-left is selected to "All Configurations".

Headers are platform independent, so be sure to set these settings under "All Platforms" in the drop down at the top-middle.

Navigate to C/C++ > General.  On the right, look for Additional Include Directories.  Click in the box beside it, and there should be a little down-arrow at the far right.  Click on that and then click on <Edit...>.  This brings up a dialog window where you can specify the location of directories to "include" so that C++ knows where to look in its attempts to resolve external references.

In that new little window that popped up, click on the New Line icon (looks like a folder).  This inserts a new line in the text area and you can click on the "..." button to browse to a location to include.  We want to do this twice and point to the include folders of each of our libraries:

 - e:\opengl\lib\freeglut-3.0.0\include
 - e:\opengl\lib\glew-2.1.0\include

Make sure you did this for "Additional Include Directories" and not "Additional #using Directories".

Click OK.


5.2. Including libraries

Next, we'll be doing something similar around libs instead of headers.  Inside the project properties dialog, browse to Configuration Properties > Linker > General and look for Additional Library Directories on the right.  Before you click, check that the Platform drop-down box is selected on the correct platform (Win32 is 32-bit and x64 is 64-bit).

With the correct platform, click the text box and then on the little arrow and then on <Edit...>.  Another similar window from the last step will launch.  Click the New Line icon and on the "..." button to browse to add the following folders:

[64 bit Version]
 - e:\opengl\lib\freeglut-3.0.0\lib\x64
 - e:\opengl\lib\glew-2.1.0\lib\Release\x64

[32 bit Version]
 - e:\opengl\lib\freeglut-3.0.0\lib
 - e:\opengl\lib\glew-2.1.0\lib\Release\Win32

Click Apply.

One more thing needs to be done in this section.  The above specified where libs could be found, but now we need to specify what libs to grab.  This part is platform independent, so change the Platform selector to All Platforms.

Go to Configuration Properties > Linker > Input and click in Additional Dependencies.  Bring up the dialog box with the <Edit...> link and type into the top empty text box the following libs:

freeglut.lib  (and press enter to get a new line)
glew32.lib

Click OK, and then OK again from the Property Pages.

5.3. Copy dll files

Last but not least, lets move our dll files over into our bin output folder.  This is also platform-dependent, so be sure to copy the correct files.

[64 bit]
Copy:
 - e:\opengl\lib\freeglut-3.0.0\bin\x64\freeglut.dll
 - e:\opengl\lib\glew-2.1.0\bin\Release\x64\glew32.dll (not a typo)

Paste into:
 - e:\opengl\projects\DemoOpenGL\x64\Debug

[32 bit]
Copy:
 - e:\opengl\lib\freeglut-3.0.0\bin\freeglut.dll
 - e:\opengl\lib\glew-2.1.0\bin\Release\Win32\glew32.dll

Paste into:
 - e:\opengl\projects\DemoOpenGL\Debug

6. Write code

Go ahead and paste this code into main.cpp, which I got from https://www.badprog.com/c-opengl-hello-world.  It should display a simple white square when run in the next step.

#include <GL/glut.h>
 
void displayMe(void)
{
    glClear(GL_COLOR_BUFFER_BIT);
    glBegin(GL_POLYGON);
    glVertex3f(0.0, 0.0, 0.0);
    glVertex3f(0.5, 0.0, 0.0);
    glVertex3f(0.5, 0.5, 0.0);
    glVertex3f(0.0, 0.5, 0.0);
    glEnd();
    glFlush();
}
 
int main(int argc, char** argv)
{
    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_SINGLE);
    glutInitWindowSize(300, 300);
    glutInitWindowPosition(100, 100);
    glutCreateWindow("Hello world :D");
    glutDisplayFunc(displayMe);
    glutMainLoop();
    return 0;
}


7. Compile/build/run

There shouldn't be any red-lined errors.  If there are red-underlined errors indicating that Visual Studio is unable to find a header file, then you may want to revisit step 5.1 to ensure the directories were set properly.

If there are linker errors, you may want to revisit step 5.2, which indicates that the libraries can't be found to resolve those references.

Lastly, if there is a problem running the application but not in building, you may get an error specifying that a required dll was not found.  For this, revisit step 5.3

When the above code is run, it should display a stationary white square on a black background.  Pretty simplistic "hello world" program of sorts.  In the next step, we will work around something a little less basic to give the reader a little more hands-on experience.

Road Map:

Part 1 - Introduction
Part 2 - Setting up OpenGL in Visual Studio
Part 3 - Implementing The Boundary Bouncing Cube

No comments:

Post a Comment