I want to transform a vector(0,0,0) to a new point with the transformation matrix but if you do the transformation [matrix * v] you would end up at vector(0,0,0) every time. I am thinking there is an added step that I need to do for this to end up working.
Transforming 3D zero-vector with a 3x3 matrix will always result in the zero-vector because 3x3 matrices can only represent linear transforms. But translations are not linear. Therefore, you need to use homogeneous coordinates and a 4x4 matrix. If you have a 4x4 translation matrix, you need to add 1 as the fourth dimension to the vector, so it will get (0, 0, 0, 1) and transform this with your matrix. If the matrix is just a translation (or in general an affine transform), you just need to cut off the fourth dimension to get the final 3D vector.
Related
I need to calculate a 4x4 matrix (for OpenGL) that can transform a 3d object on the left to one on the right. Transformation applied only in one axis.
EDIT:
The inputs are a given 3d object (points) to be deformed and a single variable for the amount of deformation.
A picture represents a cube projected to plane showing only relevant changes. There are no changes in the axis perpendicular to view plane.
The relative position of these two objects is not relevant and used only to show "before and after" situation.
******* wrong answer was here *******
It's somewhat opposite to 2D perspective matrix with further perspective division. So, to do this "perspective" thing inversely, you need to do something opposite to perspective division then multiply the result by an inverted "perspective" matrix. And though the perspective matrix may be inverted, I have no idea what is "opposite to perspective division". I think you just can't do it with matrices. You'll have to transform Y coord of each vertex instead
How do I set a camera rotation given a rotational matrix M (M is a 4 by 4 matrix)
glLoadMatrix():
Description
glLoadMatrix replaces the current matrix with the one whose elements are specified by m. The current matrix is the projection matrix, modelview matrix, or texture matrix, depending on the current matrix mode (see glMatrixMode).
I am new to opencv. and I am right now going through with the concept of Image Transformation in OpenCV. So my question is,
1) Why does Affine Transformation use 2*3 matrix and perspective transformation use 3*3 matrix?
2) When to use Affine transformation and Perspective transformation over each other?
Any Suggestions?
1) It is not a question about OpenCV but rather about mathematics. Applying affine transformation to point (x,y) means the following:
x_new = a*x + b*y + c;
y_new = d*x + e*y + f;
And so affine transform has 6 degrees of freedom: a, b, c, d, e, f. They are stored in 2x3 matrix: a, b, c in the first row, and d, e, f in the second row. You can apply transform to a point by multiplying of matrix and vector.
Perspective transform of (x,y) would be:
z = g*x + h*y + 1;
x_new = (a*x + b*y + c)/z;
y_new = (d*x + e*y + f)/z;
As you can see it has 8 degrees of freedom that are stored in 3x3 matrix. Third row is g, h, 1.
See also homogeneous coordinates for more information about why this representation is so convenient.
2) Affine transformation is also called 'weak perspective' transformation: if you are looking at some scene from different perspective but size of the scene is small relatively to distance to the camera (i.e. parallel lines remain more or less parallel), than you may use affine transform. Otherwise perspective transform will be required.
It is better to consider a hole family of transformations - then you really remember what is what. Let’s go from simplest to complex ones:
1. Euclidean - this is a rigid rotation in plane plus translation. Basically all you can do with a piece of paper lying on the table.
2. Similarity - more general transformation where you can rotate, translate and also scale (hence it is non-rigid);
3. Affine - adds another operation - shear - which would make a parallelogram from a rectangle. This kind of sheer happens during orthographic projection or when objects are viewed from a long distance (compared to their size); parallel lines are still preserved.
4. Homography or perspective transformation - most general transformation and it will make a trapezoid out of rectangle (that is different amount of shear applied to each side). This happens when projecting planar objects from close distance. Remember how train trucks converge to a point at infinity? hence the name perspective. It also means that unlike other transformations we have to apply a division at some point. This what a third row does when we convert from Homogeneous to Cartesian coordinates we divide by a value in a last third row.
This transformation is the only one that cannot be optimally computed using linear algebra and requires non-linear optimization (coz of devision). In camera projections homography happens in three cases:
1. between flat surface and its image;
2. between arbitrary images of 3D scene when camera rotates but not translates;
3. during zoom operation.
In other words whenever a flat camera sensor crosses the same optical rays you have a homography.
The following site says to use the model_view matrix when computing the normal matrix (assuming we are not using the built in gl_NormalMatrix): (site)Light House. I have the following algorithm in my program:
//Calculate Normal matrix
// 1. Multiply the model matrix by the view matrix and then grab the upper left
// corner 3 x 3 matrix.
mat3x3 mv_orientation = glext::orientation_matrix<float, glext::column>(
glext::model_view<float, glext::column>(glext_model_, glext_view_));
// 2. Because openGL matrices use homogeneous coordinate an affine inversion
// should work???
mv_orientation.affine_invert();
// 3. The normal matrix is defined as the transpose of the inverse of the upper
// left 3 X 3 matrix
mv_orientation.transpose();
// 4. Place this into the shader
basic_shader_.set_uniform_3d_matrix("normal_matrix", mv_orientation.to_gl_matrix());
Assuming most statements above are correct in the aforementioned code. Do you not include the projection matrix in the computation of the normal matrix? If not why, does the projection matrix not affect the normals like they do points?
That's because projection is not an affine transformation. Projections don't maintain the inner product and then they don't maintain the angles. And the real angles that have effect on the light diffusion and reflection are the angles in the affine 3d space. So using also the projection matrix would get you different angles, wrong angles, and hence wrong lights.
Do you not include the projection matrix in the computation of the normal matrix?
No. Normals are required for calculations, like illumination, happening in world and/or view space. It doesn't make sense from a mathematical point of you to do this after projection.
If not why, does the projection matrix not affect the normals like they do points?
Because it would make no sense. That normals should not undergo projective transformation was the original reason to have a separate projection matrix. If you'd put normals through the projection they'd loose their meaning and usefullness.
(perhaps this is better for a math Stack Exchange?)
I have a chain composed of bones. Each bone has a with a tip and tail. The following code computes where its tip will be, given a rotation, and sets the next link in the chain's position appropriately:
// Quaternion is a hand-rolled class that works correctly (as far as I can tell.)
Quaternion quat = new Quaternion(getRotationAngleDegrees(), getRotation());
// figure out where the tip will be after applying the rotation
Vector3f rotatedTip = quat.applyRotationTo(tip);
// set the next bone's tail to be at this one's tip
updateNextPosFrom(rotatedTip);
This works if the rotation is supposed to occur around the origin of the object's coordinate system. But what if I want the rotation to occur around some other arbitrary point in the object? I'm not sure how to translate the quaternion. What is the best way to do it?
(I'm using JOGL / OpenGL.)
Dual quaternions are useful for expressing rigid spatial transformations (combined rotations and translations.)
Based on dual numbers (one of the Clifford algebras, d = a + e b where a, b are real and e is unequal to zero but e^2 = 0), dual quaternions, U + e V, can represent lines in space with U the unit direction quaternion and V the moment about a reference point. In this way, dual quaternion lines are very much like Pluecker lines.
While the quaternion transform Q V Q* (Q* is the quaternion conjugate of Q) is used to rotate a unit vector quaternion V about a point, a similar dual quaternion form can be used to apply to line a screw transform (the rigid rotation about an axis combined with a translation along the axis.)
Just as any rigid 2D transform can be resolved to a rotation about a point, any rigid 3D transform can be resolved to a screw.
For such power and expressiveness, dual quaternion references are thin, and the Wikipedia article is as good a place as any to start.
A quaternion is used specifically to handle a rotation factor, but does not include a translation at all.
Typically, in this situation, you'll want to apply a rotation to a point based on the "bone's" length, but centered at the origin. You can then translate post-rotation to the proper location in space.
Quaternions are generally used to represent rotations only; they cannot represent translations as well.
You need to convert your quaternion into a rotation matrix, insert it into the appropriate part of your standard OpenGL 4x4 matrix, and combine it with a translation in order to rotate about an arbitrary point.
4x4 rotation matrix:
[ r r r 0 ]
[ r r r 0 ] <- the r's are the 3x3 rotation matrix from the wiki article
[ r r r 0 ]
[ 0 0 0 1 ]
The Wikipedia page on forward kinematics points to this paper: Introduction to Homogeneous Transformations & Robot Kinematics.
Edit : This answer is wrong. It argues on 4x4 transformation matrices properties, which are not quaternions...
I might have got it wrong but to me (unlike some answers) a quaternion is indeed a tool to handle rotations and translations (and more). It is a 4x4 matrix where the last column represents the translation. Using matrix algebra, replace the 3-vector (x, y, z) by the 4-vector (x, y, z, 1) and compute the transformed vector by the matrix. You will find that values of the last column of the matrix will be added to the coordinates x, y, z of the original vector, as in a translation.
A 3x3 matrix for a 3D space represents a linear transformation (like rotation around the origin). You cannot use a 3x3 matrix for an affine transformation like a translation. So I understand simply the quaternions as a little "trick" to represent more kinds of transformations using matrix algebra. The trick is to add a fourth coordinate equal to 1 and to use 4x4 matrices. Because matrix algebra remains valid, you can combine space transformations by multiplying the matrices, which is indeed powerful.