Followers 0

# OpenGL What makes OpenGL right handed?

## 63 posts in this topic

I often hear OpenGL referred to as using a right handed coordinate system, but I'm a little unclear as to the precise reason why this is so. Sure, the gluXXX helper functions operate in a right handed system, but what specifically about OpenGL makes it right handed?
0

##### Share on other sites
Negative Z points away from the camera origin( into the screen ) and Positive Y points up, Positive X points towards the right.
0

##### Share on other sites
It's because of the projection matrix. I believe it is because of the 3rd row, 3 column. I'm not sure since I haven't bothered with that matrix in years.
0

##### Share on other sites
Quote:
 Original post by gtdelarosa2Negative Z points away from the camera origin( into the screen ) and Positive Y points up, Positive X points towards the right.

Yes, that's a right handed system, but what about OpenGL requires this?
0

##### Share on other sites
Quote:
Original post by GaryNas
Quote:
 Original post by gtdelarosa2Negative Z points away from the camera origin( into the screen ) and Positive Y points up, Positive X points towards the right.

Yes, that's a right handed system, but what about OpenGL requires this?

Why do some countries drive on the right and some on the left side of the road ? It's a convention. They had to pick something.
0

##### Share on other sites
The pipeline requires the data to be as such for processing..i.e internally it makes the assumption that stuff are in a right handed coordinate system. Not directly related, but APIs have to make certain assumptions, ex. that is why by default vertices in GL have to be specified counter-clockwise...thats just the way it is.
0

##### Share on other sites
I have a hunch that this will be a multi-paged thread (probably closed too)
0

##### Share on other sites
Quote:
 Original post by Yann LWhy do some countries drive on the right and some on the left side of the road ? It's a convention. They had to pick something.

Do you mean they had to pick something for the glu library, or for OpenGL?

Let me give an example. Assume my models, and world are left handed. I use this left handed world in OpenGL and do not convert to a right handed system. Which part of OpenGL will have trouble with this left handed system? I believe the problem would be in clip space, but I'm not sure.
0

##### Share on other sites
Your models will be mirrored (I hope God, I'm right...)
0

##### Share on other sites
Quote:
 Original post by cgrantThe pipeline requires the data to be as such for processing..i.e internally it makes the assumption that stuff are in a right handed coordinate system. Not directly related, but APIs have to make certain assumptions, ex. that is why by default vertices in GL have to be specified counter-clockwise...thats just the way it is.

Ah, this is exactly what I'm getting at. Do you know which part of the pipeline requires a right handed system? I've searched all over for this info, but all I can find is "OpenGL is right handed", "DirectX is left handed".
0

##### Share on other sites
Quote:
 Original post by GaryNasDo you mean they had to pick something for the glu library, or for OpenGL?

glu is the OpenGL utility library, it's evident that both have to use the same conventions.

Quote:
 Original post by GaryNasLet me give an example. Assume my models, and world are left handed. I use this left handed world in OpenGL and do not convert to a right handed system. Which part of OpenGL will have trouble with this left handed system?

None at all. It will just not be displayed the way you intended it to be. Up, down, left, right, in, out - all that are human concepts. A mathematical processing framework, such as OpenGL, can't use these. You have to map these concepts of human perception to absolute mathematical terms. Just as OpenGL doesn't know what the colour red is, but it knows (1,0,0).

By supplying your own projection matrix to OpenGL, you can make it left or right handed. Or, assuming some vertex shader magic, you could even specify your points in a totally different coordinate system. Spherical polar, for example. It's all a question of conventions.

So to answer your question, there is no part of OpenGL that requires a certain handedness. Assuming we're talking about modern, non-FFP OpenGL.
0

##### Share on other sites
Quote:
 Original post by GaryNasI've searched all over for this info, but all I can find is "OpenGL is right handed", "DirectX is left handed".
That's all you can find, because that's the entirety of it. There's nothing more to say about it.

0

##### Share on other sites
The difference I see is actually in projection computation (as was already mentioned above). If you choose the view local x and y directions for spanning the view plane, and let stuff at less depth cover stuff at greater depth, then choosing whether depth increases with increasing local z or else increases with decreasing local z makes the difference. The former method would be LHS, and the latter one RHS.
0

##### Share on other sites
Yup, it is the projection matrix. I have done some D3D and GL code where both had to be right handed. I just manipulated the projection for D3D (actually, they have D3DXPersPectiveRH) and also for modelview rotation, there is the RH versions. Translation is universal. Scale is universal.

The other thing left to do is setup culling for D3D.
0

##### Share on other sites
Quote:
Original post by Daaark
Quote:
 Original post by GaryNasI've searched all over for this info, but all I can find is "OpenGL is right handed", "DirectX is left handed".
That's all you can find, because that's the entirety of it. There's nothing more to say about it.
I'm not sure it's quite that simple.

I said this same thing in another recent thread, but as far as I can tell, Direct3D/DirectX is no more left-handed than it is right-handed. It works fine with both left- and right-handed systems (as far as I can tell, at least), and the DX math library includes transform functions for each handedness.

Why Direct3D is thought of as being left-handed, I'm not sure, but I suspect it may be historical. Maybe someone else can shed some light on this.

My guess is that OpenGL can be used with a left-handed system just as easily as Direct3D can be used with a right-handed system (as was suggested previously). I haven't actually tried this myself though, so I can't say for sure.

If that's true though, then I would think that the only thing that makes OpenGL 'right-handed' is the few convenience functions that build transforms for which handedness matters (gluLookAt, gluPerspective, etc.). If you take these out of the picture (e.g. by using glLoad/MultMatrix, or by using the programmable pipeline), then I'm not sure that OpenGL can be said to have an inherent handedness.

So to get back to the original question, my guess is that the only thing that makes OpenGL 'right-handed' is a few convenience functions that you can easily do without, and that in fact are no longer even included as part of the API. (I could be overlooking something though.)
0

##### Share on other sites
Maybe I will tell a totally dumb thing, but I'm a bit tired.
I think that makes openGL right-handed, is that if you don't apply any transformations (identity as model-view and projection), a model made and viewed in a left handed editor would appear mirrored in onenGL in the said conditions.

0

##### Share on other sites
Quote:
 Original post by szecsMaybe I will tell a totally dumb thing, but I'm a bit tired.I think that makes openGL right-handed, is that if you don't apply any transformations (identity as model-view and projection), a model made and viewed in a left handed editor would appear mirrored in onenGL in the said conditions.Some one please clarify this.
I don't think that's right; if the projection matrix is identity, I don't think the visual output will be anything meaningful (in the general case, at least).
0

##### Share on other sites
Quote:
 Original post by jykif the projection matrix is identity, I don't think the visual output will be anything meaningful (in the general case, at least).
Sure it will. An identity projection matrix is just an unscaled orthographic projection.
0

##### Share on other sites
Quote:
 Original post by jykI said this same thing in another recent thread, but as far as I can tell, Direct3D/DirectX is no more left-handed than it is right-handed.

You may be thinking about row mayor vs column mayor notation, but anyway in order to use the opposite handedness multiply your matrices by/or use this as your identity matrix:

 [ 1  0  0  0 ][ 0  1  0  0 ][ 0  0 -1  0 ][ 0  0  0  1 ]
0

##### Share on other sites
Quote:
Original post by jyk
Quote:
 Original post by szecsMaybe I will tell a totally dumb thing, but I'm a bit tired.I think that makes openGL right-handed, is that if you don't apply any transformations (identity as model-view and projection), a model made and viewed in a left handed editor would appear mirrored in onenGL in the said conditions.Some one please clarify this.
I don't think that's right; if the projection matrix is identity, I don't think the visual output will be anything meaningful (in the general case, at least).
Most newbies don't even know about the projection matrix.
So the question still sands: Am I right in my previous post?
0

##### Share on other sites
Quote:
 Original post by szecsSo the question still sands: Am I right in my previous post?

You are, you won't see much because a pixel would take the whole screen (see swiftcoder's post), but that doesn't mean the model isn't there, in a right handed coordinate system [smile].
0

##### Share on other sites
Does that mean I have solved the problem?
Do I get promoted or something?

(BTW if the model is smaller than 1.0 unit, then it will shown nicely, the viewport (thus pixels) has nothing to do with the matrices.)
0

##### Share on other sites
Well, actually I think you can also switch handedness by providing a higher value for the left parameter than the right parameter OR higher for bottom than top for glFrustum or glOrtho, still, it would default to right handed.

Quote:
 Original post by szecs(BTW if the model is smaller than 1.0 unit, then it will shown nicely, the viewport (thus pixels) has nothing to do with the matrices.)

Yeah, you're right.
0

##### Share on other sites
Quote:
Original post by Kwizatz
Quote:
 Original post by jykI said this same thing in another recent thread, but as far as I can tell, Direct3D/DirectX is no more left-handed than it is right-handed.

You may be thinking about row mayor vs column mayor notation

Also, there's no such thing as 'row-major notation', at least as far as I'm aware. Are you talking about row- vs. column-vector notation?
0

## Create an account

Register a new account

Followers 0

• ### Similar Content

• By DaniDesu
#include "MyEngine.h" int main() { MyEngine myEngine; myEngine.run(); return 0; } MyEngine.h
#pragma once #include "MyWindow.h" #include "MyShaders.h" #include "MyShapes.h" class MyEngine { private: GLFWwindow * myWindowHandle; MyWindow * myWindow; public: MyEngine(); ~MyEngine(); void run(); }; MyEngine.cpp
#pragma once #include <glad\glad.h> #include <GLFW\glfw3.h> class MyWindow { private: GLFWwindow * windowHandle; int windowWidth; int windowHeight; const char * windowTitle; public: MyWindow(int windowWidth, int windowHeight, const char * windowTitle); ~MyWindow(); GLFWwindow * getWindowHandle(); void createWindow(); void MyWindow::destroyWindow(); }; MyWindow.cpp
#include "MyWindow.h" MyWindow::MyWindow(int windowWidth, int windowHeight, const char * windowTitle) { this->windowHandle = NULL; this->windowWidth = windowWidth; this->windowWidth = windowWidth; this->windowHeight = windowHeight; this->windowTitle = windowTitle; glfwInit(); } MyWindow::~MyWindow() { } GLFWwindow * MyWindow::getWindowHandle() { return this->windowHandle; } void MyWindow::createWindow() { // Use OpenGL 3.3 and GLSL 3.3 glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); // Limit backwards compatibility glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); // Prevent resizing window glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); // Create window this->windowHandle = glfwCreateWindow(this->windowWidth, this->windowHeight, this->windowTitle, NULL, NULL); glfwMakeContextCurrent(this->windowHandle); } void MyWindow::destroyWindow() { glfwTerminate(); } MyShapes.h
#pragma once #include <glad\glad.h> #include <GLFW\glfw3.h> class MyShapes { public: MyShapes(); ~MyShapes(); GLuint & drawTriangle(float coordinates[]); }; MyShapes.cpp
#include "MyShapes.h" MyShapes::MyShapes() { } MyShapes::~MyShapes() { } GLuint & MyShapes::drawTriangle(float coordinates[]) { GLuint vertexBufferObject{}; GLuint vertexArrayObject{}; // Create a VAO glGenVertexArrays(1, &vertexArrayObject); glBindVertexArray(vertexArrayObject); // Send vertices to the GPU glGenBuffers(1, &vertexBufferObject); glBindBuffer(GL_ARRAY_BUFFER, vertexBufferObject); glBufferData(GL_ARRAY_BUFFER, sizeof(coordinates), coordinates, GL_STATIC_DRAW); // Dertermine the interpretation of the array buffer glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3*sizeof(float), (void *)0); glEnableVertexAttribArray(0); // Unbind the buffers glBindBuffer(GL_ARRAY_BUFFER, 0); glBindVertexArray(0); return vertexArrayObject; } MyFileHandler.h
#pragma once #include <cstdio> #include <cstdlib> class MyFileHandler { private: const char * fileName; unsigned long fileSize; void setFileSize(); public: MyFileHandler(const char * fileName); ~MyFileHandler(); unsigned long getFileSize(); const char * readFile(); }; MyFileHandler.cpp
#include "MyFileHandler.h" MyFileHandler::MyFileHandler(const char * fileName) { this->fileName = fileName; this->setFileSize(); } MyFileHandler::~MyFileHandler() { } void MyFileHandler::setFileSize() { FILE * fileHandle = NULL; fopen_s(&fileHandle, this->fileName, "rb"); fseek(fileHandle, 0L, SEEK_END); this->fileSize = ftell(fileHandle); rewind(fileHandle); fclose(fileHandle); return; } unsigned long MyFileHandler::getFileSize() { return (this->fileSize); } const char * MyFileHandler::readFile() { char * buffer = (char *)malloc((this->fileSize)+1); FILE * fileHandle = NULL; fopen_s(&fileHandle, this->fileName, "rb"); fread(buffer, this->fileSize, sizeof(char), fileHandle); fclose(fileHandle); buffer[this->fileSize] = '\0'; return buffer; } VertexShader.glsl
#version 330 core layout (location = 0) vec3 VertexPositions; void main() { gl_Position = vec4(VertexPositions, 1.0f); } FragmentShader.glsl
#version 330 core out vec4 FragmentColor; void main() { FragmentColor = vec4(1.0f, 0.0f, 0.0f, 1.0f); } I am attempting to create a simple engine/graphics utility using some object-oriented paradigms. My first goal is to get some output from my engine, namely, a simple red triangle.
For this goal, the MyShapes class will be responsible for defining shapes such as triangles, polygons etc. Currently, there is only a drawTriangle() method implemented, because I first wanted to see whether it works or not before attempting to code other shape drawing methods.
The constructor of the MyEngine class creates a GLFW window (GLAD is also initialized here to load all OpenGL functionality), and the myEngine.run() method in Main.cpp is responsible for firing up the engine. In this run() method, the shaders get loaded from files via the help of my FileHandler class. The vertices for the triangle are processed by the myShapes.drawTriangle() method where a vertex array object, a vertex buffer object and vertrex attributes are set for this purpose.
The while loop in the run() method should be outputting me the desired red triangle, but all I get is a grey window area. Why?
(Note: I am aware that this code is not using any good software engineering practices (e.g. exceptions, error handling). I am planning to implement them later, once I get the hang of OpenGL.)

• By KarimIO
EDIT: I thought this was restricted to Attribute-Created GL contexts, but it isn't, so I rewrote the post.
Hey guys, whenever I call SwapBuffers(hDC), I get a crash, and I get a "Too many posts were made to a semaphore." from Windows as I call SwapBuffers. What could be the cause of this?
Update: No crash occurs if I don't draw, just clear and swap.
static PIXELFORMATDESCRIPTOR pfd = // pfd Tells Windows How We Want Things To Be { sizeof(PIXELFORMATDESCRIPTOR), // Size Of This Pixel Format Descriptor 1, // Version Number PFD_DRAW_TO_WINDOW | // Format Must Support Window PFD_SUPPORT_OPENGL | // Format Must Support OpenGL PFD_DOUBLEBUFFER, // Must Support Double Buffering PFD_TYPE_RGBA, // Request An RGBA Format 32, // Select Our Color Depth 0, 0, 0, 0, 0, 0, // Color Bits Ignored 0, // No Alpha Buffer 0, // Shift Bit Ignored 0, // No Accumulation Buffer 0, 0, 0, 0, // Accumulation Bits Ignored 24, // 24Bit Z-Buffer (Depth Buffer) 0, // No Stencil Buffer 0, // No Auxiliary Buffer PFD_MAIN_PLANE, // Main Drawing Layer 0, // Reserved 0, 0, 0 // Layer Masks Ignored }; if (!(hDC = GetDC(windowHandle))) return false; unsigned int PixelFormat; if (!(PixelFormat = ChoosePixelFormat(hDC, &pfd))) return false; if (!SetPixelFormat(hDC, PixelFormat, &pfd)) return false; hRC = wglCreateContext(hDC); if (!hRC) { std::cout << "wglCreateContext Failed!\n"; return false; } if (wglMakeCurrent(hDC, hRC) == NULL) { std::cout << "Make Context Current Second Failed!\n"; return false; } ... // OGL Buffer Initialization glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT); glBindVertexArray(vao); glUseProgram(myprogram); glDrawElements(GL_TRIANGLES, indexCount, GL_UNSIGNED_SHORT, (void *)indexStart); SwapBuffers(GetDC(window_handle));
• By Tchom
Hey devs!

I've been working on a OpenGL ES 2.0 android engine and I have begun implementing some simple (point) lighting. I had something fairly simple working, so I tried to get fancy and added color-tinting light. And it works great... with only one or two lights. Any more than that, the application drops about 15 frames per light added (my ideal is at least 4 or 5). I know implementing lighting is expensive, I just didn't think it was that expensive. I'm fairly new to the world of OpenGL and GLSL, so there is a good chance I've written some crappy shader code. If anyone had any feedback or tips on how I can optimize this code, please let me know.

uniform mat4 u_MVPMatrix; uniform mat4 u_MVMatrix; attribute vec4 a_Position; attribute vec3 a_Normal; attribute vec2 a_TexCoordinate; varying vec3 v_Position; varying vec3 v_Normal; varying vec2 v_TexCoordinate; void main() { v_Position = vec3(u_MVMatrix * a_Position); v_TexCoordinate = a_TexCoordinate; v_Normal = vec3(u_MVMatrix * vec4(a_Normal, 0.0)); gl_Position = u_MVPMatrix * a_Position; } Fragment Shader
precision mediump float; uniform vec4 u_LightPos["+numLights+"]; uniform vec4 u_LightColours["+numLights+"]; uniform float u_LightPower["+numLights+"]; uniform sampler2D u_Texture; varying vec3 v_Position; varying vec3 v_Normal; varying vec2 v_TexCoordinate; void main() { gl_FragColor = (texture2D(u_Texture, v_TexCoordinate)); float diffuse = 0.0; vec4 colourSum = vec4(1.0); for (int i = 0; i < "+numLights+"; i++) { vec3 toPointLight = vec3(u_LightPos[i]); float distance = length(toPointLight - v_Position); vec3 lightVector = normalize(toPointLight - v_Position); float diffuseDiff = 0.0; // The diffuse difference contributed from current light diffuseDiff = max(dot(v_Normal, lightVector), 0.0); diffuseDiff = diffuseDiff * (1.0 / (1.0 + ((1.0-u_LightPower[i])* distance * distance))); //Determine attenuatio diffuse += diffuseDiff; gl_FragColor.rgb *= vec3(1.0) / ((vec3(1.0) + ((vec3(1.0) - vec3(u_LightColours[i]))*diffuseDiff))); //The expensive part } diffuse += 0.1; //Add ambient light gl_FragColor.rgb *= diffuse; } Am I making any rookie mistakes? Or am I just being unrealistic about what I can do? Thanks in advance
• By yahiko00
Hi,
Not sure to post at the right place, if not, please forgive me...
For a game project I am working on, I would like to implement a 2D starfield as a background.
I do not want to deal with static tiles, since I plan to slowly animate the starfield. So, I am trying to figure out how to generate a random starfield for the entire map.
I feel that using a uniform distribution for the stars will not do the trick. Instead I would like something similar to the screenshot below, taken from the game Star Wars: Empire At War (all credits to Lucasfilm, Disney, and so on...).

Is there someone who could have an idea of a distribution which could result in such a starfield?
Any insight would be appreciated

• I have just noticed that, in quake 3 and half - life, dynamic models are effected from light map. For example in dark areas, gun that player holds seems darker. How did they achieve this effect ? I can use image based lighting techniques however (Like placing an environment probe and using it for reflections and ambient lighting), this tech wasn't used in games back then, so there must be a simpler method to do this.
Here is a link that shows how modern engines does it. Indirect Lighting Cache It would be nice if you know a paper that explains this technique. Can I apply this to quake 3' s light map generator and bsp format ?

• 13
• 11
• 18
• 18
• 15