Test cases for vec_roll_to_mat3_normalized

The function vec_roll_to_mat3_normalized() basically has to handle 3 scenarios:

- When a bone is oriented along the negative Y axis
- When a bone is very close to the negative Y axis
- All other cases

The tests in the Differential make sure that all 3 situations are covered.

Reviewed By: sybren, mont29

Differential Revision: https://developer.blender.org/D9525
This commit is contained in:
Gaia Clary 2020-11-09 18:57:40 +01:00
parent b9bd47c2e2
commit 923b314a7a
1 changed files with 67 additions and 0 deletions

View File

@ -90,4 +90,71 @@ TEST(mat3_vec_to_roll, Rotationmatrix)
}
}
TEST(vec_roll_to_mat3_normalized, Rotationmatrix)
{
float negative_y_axis[3][3];
unit_m3(negative_y_axis);
negative_y_axis[0][0] = negative_y_axis[1][1] = -1.0f;
const float roll = 0.0f;
float roll_mat[3][3];
/* If normalized_vector is -Y, simple symmetry by Z axis. */
{
const float normalized_vector[3] = {0.0f, -1.0f, 0.0f};
vec_roll_to_mat3_normalized(normalized_vector, roll, roll_mat);
EXPECT_M3_NEAR(roll_mat, negative_y_axis, FLT_EPSILON);
}
/* If normalized_vector is far enough from -Y, apply the general case. */
{
const float expected_roll_mat[3][3] = {{1.000000f, 0.000000f, 0.000000f},
{0.000000f, -0.999989986f, -0.000000f},
{0.000000f, 0.000000f, 1.000000f}};
const float normalized_vector[3] = {0.0f, -1.0f + 1e-5f, 0.0f};
vec_roll_to_mat3_normalized(normalized_vector, roll, roll_mat);
EXPECT_M3_NEAR(roll_mat, expected_roll_mat, FLT_EPSILON);
}
#if 0
/* TODO: This test will pass after fixing T82455) */
/* If normalized_vector is close to -Y and
* it has X and Z values above a threshold,
* apply the special case. */
{
const float expected_roll_mat[3][3] = {{0.000000f, -9.99999975e-06f, 1.000000f},
{9.99999975e-06f, -0.999999881f, 9.99999975e-06f},
{1.000000f, -9.99999975e-06, 0.000000f}};
const float normalized_vector[3] = {1e-24, -0.999999881, 0};
vec_roll_to_mat3_normalized(normalized_vector, roll, roll_mat);
EXPECT_M3_NEAR(roll_mat, expected_roll_mat, FLT_EPSILON);
}
#endif
/* If normalized_vector is in a critical range close to -Y, apply the special case. */
{
const float expected_roll_mat[3][3] = {{0.000000f, -9.99999975e-06f, 1.000000f},
{9.99999975e-06f, -0.999999881f, 9.99999975e-06f},
{1.000000f, -9.99999975e-06, 0.000000f}};
const float normalized_vector[3] = {1e-5f, -0.999999881f, 1e-5f}; /* Corner Case. */
vec_roll_to_mat3_normalized(normalized_vector, roll, roll_mat);
EXPECT_M3_NEAR(roll_mat, expected_roll_mat, FLT_EPSILON);
}
/* If normalized_vector is far enough from -Y, apply the general case. */
{
const float expected_roll_mat[3][3] = {{0.788675129f, -0.577350259f, -0.211324856f},
{0.577350259f, 0.577350259f, 0.577350259f},
{-0.211324856f, -0.577350259f, 0.788675129f}};
const float vector[3] = {1.0f, 1.0f, 1.0f}; /* Arbitrary Value. */
float normalized_vector[3];
normalize_v3_v3(normalized_vector, vector);
vec_roll_to_mat3_normalized(normalized_vector, roll, roll_mat);
EXPECT_M3_NEAR(roll_mat, expected_roll_mat, FLT_EPSILON);
}
}
} // namespace blender::bke::tests