RelationShip Between Camera and View Matrix - opengl

Why the View Matrix is inverse of A Camera Matrix ? I can't understand this relationship can anyone please explain this to me.
Formally Vector to a camera is calculated as follow
toCameraVector= (inverse(viewMatrix)*vec4(0,0,0,1.0)).xyz-worldPosition.xyz;

A camera in the 3D world is actually an imaginary object. There is no actual camera. So we need to simulate camera by doing things the opposite way. If we need to move the camera to the left in the 3D world, we move everything in the scene to the right. That is why the View Matrix is the inverse of the Camera Matrix.
For more info about Model, View and Projection matrices (and more) check out this.

Related

OpenGL Stereo View -- How to use GLM Math library for horizontal offset

I'm trying to use the GLM mathematics library to warp the projection matrix such that multiple cameras (e.g. a left eye and a right eye) are viewing the same view, but the camera frustum is distorted.
This is what I am trying to do with my cameras using GLM:
image
Note: One of the challenges I have for my camera, is that I only have in my OpenGL Graphics API a read-only view matrix and projection matrix. So even once I have the view and projection matrix, I can only move my camera using x,y,z for eye position, and then yaw,pitch,roll for view direction. Then I have standard OpenGL calls, but I am not sure how to shift or warp the projection matrix as shown below.
I think this second picture also accurately shows what I am trying to achieve with OpenGL.
Any tips on how to approach this problem? Do I need to implement a special lookAt function, or is there something built into GLM that can help me compute the right view?
A possible way to do this is:
Assume that X is the position of the "nose" (the half point between the 2 eyes).
Let V be the direction orthogonal to the left eye - right eye line.
The function X + t * V describes the "line of sight" in your last
picture.
Take t > 0 and set that as your look at point P/
Create 2 cameras with centers at the eyes, both with the exact same up direction, then use glm::lookat to look at P.

OpenGL camera direction

So I was reading this tutorial's "Inverting the Camera Orientation Matrix" section and I don't understand why, when calculating the camera's up direction, I need to multiply the inverse of orientation by the up direction vector, and not just orientation.
I drew the following image to illustrate my insight of the tutorial I read.
What did I get wrong?
Well, that tutorial explicitely states:
The way we calculate the up direction of the camera is by taking the
"directly upwards" unit vector (0,1,0) and "unrotate" it by using the
inverse of the camera's orientation matrix. Or, to explain it
differently, the up direction is always (0,1,0) after the camera
rotation has been applied, so we multiply (0,1,0) by the inverse
rotation, which gives us the up direction before the camera rotation
was applied.
The up direction which is calculated here is the up direction in world space. In eye space, the up vector is (0,1,0) (by convention, one could define it differently). As the view matrix will transform coordinates from world space to eye space, we need to use the inverse to transform that up vector from eye space to the world space. Your image is wrong as it does not correctly relate to eye and world space.

Why are model and view matrices specifically often combined together?

I'm having trouble understanding why the model and view matrices are traditionally combined together. I know that the less matrix multiplying you do in the vertex shader the better, but it makes much more sense to me to combine the projection and view matrices.
This is because they are both intrinsically camera properties. It makes sense to me to first transform vertices into world space with the model matrix, perform lighting etc., then use your combined camera matrix to translate to normalised clip space.
I know that I can do it that way if I want in a programmable pipeline, but I want to know why historically people combined the model and view matrices.
In graphics programming, camera doesn't exist. It's always fixed at (0,0,0) and looking towards (0,0,-1). Camera as everyone knows it is totally artificial and mimics the way we are used to observing objects, as humans, and by that I mean: moving around, pivoting our head and such. To mimic that, cg introduces the concept of camera. It is interesting and well known that it is the same thing whether will you move to camera to the right or to move all other objects in the scene to the left. That invariance is then transffered onto modelMatrix by combining all transformations on object in one matrix - MVMatrix.
View and Projection matrices are seperated because those matrices do very different transformations. One is very similar to modelMatrix and represents 3d, in-space transformations, and the other is used for calculating angles from which the objects are viewed.

Camera to world transformation and world to camera transformation

I am kind of confused by the camera to world vs. world to camera transformation.
In the openGL rendering pipeline, The transformation is from the world to the camera, right?
Basically, a view coordinate frame is constructed at the camera, then the object in the world is first translated relative to the camera and then rotated with the camera coordinate frame. is this what gluLookat is performing?
If I want to go from camera view back to world view, how it should be done?
Mathematically, I am thinking finding the inverse of the translate and rotate matrices, then apply the rotation before the translate, right?
Usually there are several transformations that map world positions to the screen. The following ones are the most common ones:
World transformation: Can be applied to objects in order to realign them relatively to other objects.
View transformation: After this transformation the camera is at O and looks in the z direction.
Projection transformation: Performs e.g. perspective transformations to simulate a real camera
Viewport adaption: This is basically a scaling and translation that maps the positions from range [-1, 1] to the viewport. This is usually the screen width and height.
gluLookAt is used to create a view transformation. You can imagine it as follows: Place the camera somewhere in your scene. Now transform the whole scene (with the camera) so that the camera is at the origin, it faces in the z direction and the y axis represents the up direction. This is a simple rigid body transformation that can be represented as an arbitrary rotation (with three degrees of freedom) and an arbitrary translation (with another three degrees of freedom). Every rigid body transformation can be split into separate rotations and translation. Even the sequence of evaluation can vary, if you choose the correct values. Transformations can be interpreted in different ways. I wrote a blog entry on that topic a while ago. If you're interested, take a look at it. Although it is for DirectX, the maths is pretty much the same for OpenGL. You just have to watch out for transposed matrices.
For the second question: Yes, you are right. You need to find the inverse transformation. This can be easily achieved with the inverse matrix. If you specified the view matrix V as follows:
V = R_xyz * T_xyz
then the inverse transformation V^-1 is
V^-1 = T_xyz^-1 * R_xyz^-1
However, this does not map screen positions to world positions because there is more transformation going on. I hope, that answers your questions.
Here is another interesting point. The view matrix is the inverse of the transformation that would align a camera model (at the origin, facing in z direction) at the specified position. This relation is called system transformation vs. model transformation.

Can I rotate the view of glOrtho()?

I'm making a program where I need an orthographic projection.
So, I'm using glOrtho(). I made a zoom function but I was wandering if you can rotate your view?
Because glOrho() only looks parralel to other planes.
Or is there another projection wich can do that.
glLookAt can rotate but it changes dimensions when further from the camera.
I read
How can I make the glOrtho parallelepiped rotating?
but it didn't give me an answer.
What's essential here is that you usually split the operations into two matrices: The (Model)View and The Projection.
While glOrtho() is usually called with glMatrixMode(GL_PROJECTION), all operations regarding moving and rotating the camera (such as glRotate*, glTranslate* and gluLookAt) should be preceeded by glMatrixMode(GL_MODELVIEW).
In fixed pipeline, the final position of the vertex is calculated by multiplying input data by these two matrices, and the projection used (orthographic or perspective or nonlinear whatnot) is separate from camera transformations.