1

I am implementing a custom mathematics library to create model, view and projection matrices in OpenGL and DirectX. I am doing this, to improve my understanding in the mathematics behind 3D applications.

At first I took a look at right-handed and left-handed coordinate systems. I realized, that if I create my view matrix as well as my projection matrix with the same handedness, the scene renders correctly no matter if I use OpenGL or DirectX (except inverted translation/rotation/etc.). This is a bit confusing because every article I read pointed out, that OpenGL uses a right-handed and DirectX a left-handed coordinate system. Is my assumption right, that the coordinate system completely depends on the handedness of the view and projection matrices?

When I took a look at clip spaces, things became more difficult to understand. The articles stated, that the clip volume on the X and Y axis ranges from -1.0 to 1.0 in both APIs. On the Z axis OpenGL clips from -1.0 to 1.0 and DirectX clips from 0.0 to 1.0. However, in OpenGL the scene renders correctly no matter if I use a projection matrix for clipping between -1.0 and 1.0 or 0.0 and 1.0. In DirectX only the projection matrix for clipping between 0.0 and 1.0 works. If I use the other one, nothing is rendered. So my question to this topic is: Can the clipping volume be changed on the Z axis or are those fixed implementations. If they are fixed, then why can I use both types of clipping volumes in OpenGL and only a single one in DirectX?

genpfault
  • 51,148
  • 11
  • 85
  • 139
Erik So
  • 57
  • 8

1 Answers1

2

However, in OpenGL the scene renders correctly no matter if I use a projection matrix for clipping between -1.0 and 1.0 or 0.0 and 1.0. In DirectX only the projection matrix for clipping between 0.0 and 1.0 works

OpenGL renders because [0.0, 1.0] falls within the range [-1.0, 1.0], but DirectX does not because [-1.0, 1.0] can fall outside of [0.0, 1.0]. If you invert the depth of your test scene, you'll likely be able to see stuff in DirectX using the wrong projection matrix.

Can the clipping volume be changed on the Z axis or are those fixed implementations. If they are fixed, then why can I use both types of clipping volumes in OpenGL and only a single one in DirectX?

No, you can't change that behavior as it's part of the spec. The point of all the transformations you do as part of the rendering pipeline is to get your scene into clipping space. That means, for example, mapping your scene's depth from [-9999, 9999] down to [-1.0, 1.0] for OpenGL, or [0.0, 1.0] for DirectX

Is my assumption right, that the coordinate system completely depends on the handedness of the view and projection matrices?

Not sure what you're asking here. You already observed that a scene in OpenGL looks inverted in DirectX if you don't account for the difference in handedness. The view and projection matrix that your application uses doesn't change the behavior of the OpenGL and DirectX implementations.

user16978892
  • 150
  • 1
  • 7
  • Alright, this was very helpful already. With "depends on the handedness of the view and projection matrices" I mean the following: If I create right-handed matrices in both APIs, the scene looks identical in OpenGL and DirectX. So I assume, that the handedness is up to the programmer. – Erik So Jan 20 '22 at 17:49
  • The driver doesn't care what you're doing as long as the depth values you give it fall within the range it expects. The main thing to worry about is if you're using back-face culling, you'll get incorrect results if using the same matrix for both APIs. Even in that case however, you can usually configure the culling parameters to behave differently, so you don't have to make any changes to your matrices. – user16978892 Jan 20 '22 at 18:06
  • An example of using a right-handed coordinate system in DirectX is available here: https://anteru.net/blog/2011/using-right-left-handed-viewing-systems-with-both-directx-opengl/ – user16978892 Jan 20 '22 at 18:07
  • You are perfectly right. I did not enable face culling yet in the applications. Now I enabled it and I can clearly see, that the scene renders incorrectly if the wrong coordinate system is used. – Erik So Jan 20 '22 at 18:14
  • Back when OpenGL and DirectX used 'fixed-function' rendering state engines, the choice of right/left-handedness was baked into the API for vertex processing. With programmable shaders, it's up to the programmer and the API doesn't care. You just need to be consistent in your models, camera, shaders, and culling to get the 'right' result. – Chuck Walbourn Jan 21 '22 at 05:35
  • For more on the history of OpenGL vs. DirectX matrix conventions, see [this blog post](https://seanmiddleditch.github.io/matrices-handedness-pre-and-post-multiplication-row-vs-column-major-and-notations/). This also covers issues like the differences in depth range as well. – Chuck Walbourn Jan 21 '22 at 05:39