Skip to content
Snippets Groups Projects
Commit 0879fe45 authored by Tim Übelhör's avatar Tim Übelhör
Browse files

Implemented OpenGL camera distortion

parent da0b6523
Branches
Tags
No related merge requests found
......@@ -16,7 +16,7 @@
"type": "cppdbg",
"request": "launch",
"program": "${workspaceFolder}/build/bin/scigl_viewer",
"args": ["${workspaceFolder}/model/beckenkamm.dae"],
"args": ["${workspaceFolder}/model/cube.blend"],
"stopAtEntry": false,
"cwd": "${workspaceFolder}",
"environment": [],
......
......@@ -33,5 +33,7 @@ struct CameraIntrinsics
float near = 0.1;
/*! The far plane for OpenGL */
float far = 15;
/*! OpenCV rational distortion coefficients */
float dist_coeffs[8];
};
} // namespace scigl_render
\ No newline at end of file
......@@ -11,109 +11,56 @@ Wraps a shader program for simplified compilation and usage.
class Shader
{
public:
/*!
Compiles the shader program from the given sources.
*/
/*! Compiles the shader program from the given sources. */
Shader(const std::string &vertex_source, const std::string &geometry_source,
const std::string &fragment_source);
/*!
Activate this shader program.
*/
/*! Activate this shader program. */
void activate() const;
/*!
Deactivate this shader program.
The active program "refers to an invalid program object and the results of
shader execution are undefined. However, this is not an error." (khronos.org)
*/
/*! Deactivate this shader program. */
void deactivate() const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setBool(const std::string &name, bool value) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setInt(const std::string &name, int value) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setFloat(const std::string &name, float value) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setVec2(const std::string &name, const glm::vec2 &value) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setVec2(const std::string &name, float x, float y) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setVec3(const std::string &name, const glm::vec3 &value) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setVec3(const std::string &name, float x, float y, float z) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setVec4(const std::string &name, const glm::vec4 &value) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setVec4(const std::string &name, float x, float y, float z, float w)
const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setMat2(const std::string &name, const glm::mat2 &mat) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setMat3(const std::string &name, const glm::mat3 &mat) const;
/*!
Set the uniform variable value in the shader program.
\param name the variables name
\param the value to be set.
*/
/*! Set the uniform variable value in the shader program. */
void setMat4(const std::string &name, const glm::mat4 &mat) const;
/*! Set the uniform variable value in the shader program. */
void setArray(const std::string &name, const float array[], int count) const;
private:
/*!
Reference to this shader program.
......
File added
......@@ -49,7 +49,7 @@ int main(int argc, char *argv[])
// ExampleRender render(context, shader, GL_BGR, GL_UNSIGNED_BYTE, GL_RGB8, 3);
OnscreenRender render(shader);
// Intrinsics of my shitty webcam
CameraIntrinsics camera_intrinsics;
CameraIntrinsics camera_intrinsics = {};
camera_intrinsics.near = 0.01;
camera_intrinsics.far = 15;
camera_intrinsics.width = 640;
......@@ -58,6 +58,7 @@ int main(int argc, char *argv[])
camera_intrinsics.c_y = 310;
camera_intrinsics.f_x = 511;
camera_intrinsics.f_y = 513;
camera_intrinsics.dist_coeffs[0] = 5;
CvCamera camera(camera_intrinsics);
// Test if Cartesian -> Quaternion works
CartesianPose camera_pose = {glm::vec3(0, 0, 0), glm::vec3(0, 0, 0)};
......@@ -65,8 +66,10 @@ int main(int argc, char *argv[])
DiffuseLight light;
Model model(argv[1]);
model.pose.position = glm::vec3(0, 0, 0.5);
model.pose.orientation.x = 0.707;
model.pose.orientation.w = 0.707;
light.position = glm::vec3(0, 0, 0);
light.color = glm::vec3(0.5, 0.5, 0.5);
light.color = glm::vec3(1, 1, 1);
// main loop
int old_enter_pressed = GLFW_RELEASE;
......
......@@ -41,7 +41,7 @@ glm::mat4 CvCamera::calc_projection_matrix(const CameraIntrinsics &intrinsics)
// y-axis points to the opposite direction
perspective[1][0] = -intrinsics.s;
perspective[1][1] = -intrinsics.f_y;
// z-axis points to thhe opposite direction
// z-axis points to the opposite direction
perspective[2][0] = -intrinsics.c_x;
perspective[2][1] = -intrinsics.c_y;
perspective[2][3] = -1;
......@@ -80,6 +80,8 @@ void CvCamera::set_in_shader(const Shader &shader) const
shader.activate();
shader.setMat4("projection_matrix", get_projection_matrix());
shader.setMat4("view_matrix", get_view_matrix());
shader.setArray("dist_coeffs", this->intrinsics.dist_coeffs,
sizeof(this->intrinsics.dist_coeffs));
}
CameraIntrinsics CvCamera::get_intrinsics() const
......
......@@ -144,4 +144,10 @@ void Shader::setMat4(const std::string &name, const glm::mat4 &mat) const
GL_FALSE, &mat[0][0]);
}
void Shader::setArray(
const std::string &name, const float array[], int count) const
{
glUniform1fv(glGetUniformLocation(program_id, name.c_str()), count, array);
}
} // namespace scigl_render
......@@ -17,18 +17,46 @@ layout (location = 1) in vec3 normal_in;
layout (location = 2) in vec2 texture_coordinate_in;
uniform mat4 model_matrix;
uniform mat4 view_matrix;
uniform float dist_coeffs[8];
uniform mat4 projection_matrix;
uniform vec3 light_position;
out vec2 texture_coordinate;
out vec3 normal;
out vec3 light_direction;
// distort the real world vertices using the rational model
vec4 distort(vec4 view_pos)
{
// normalize
float z = view_pos[2];
float z_inv = 1 / z;
float x1 = view_pos[0] * z_inv;
float y1 = view_pos[1] * z_inv;
// precalculations
float x1_2 = x1*x1;
float y1_2 = y1*y1;
float x1_y1 = x1*y1;
float r2 = x1_2 + y1_2;
float r4 = r2*r2;
float r6 = r4*r2;
// rational distortion factor
float r_dist = (1 + dist_coeffs[0]*r2 +dist_coeffs[1]*r4 + dist_coeffs[4]*r6)
/ (1 + dist_coeffs[5]*r2 + dist_coeffs[6]*r4 + dist_coeffs[7]*r6);
// full (rational + tangential) distortion
float x2 = x1*r_dist + 2*dist_coeffs[2]*x1_y1 + dist_coeffs[3]*(r2 + 2*x1_2);
float y2 = y1*r_dist + 2*dist_coeffs[3]*x1_y1 + dist_coeffs[2]*(r2 + 2*y1_2);
// denormalize for projection (which is a linear operation)
return vec4(x2*z, y2*z, z, view_pos[3]);
}
void main()
{
vec4 local_pos = vec4(position, 1.0);
vec4 world_pos = model_matrix * local_pos;
vec4 view_pos = view_matrix * world_pos;
gl_Position = projection_matrix * view_pos;
vec4 dist_pos = distort(view_pos);
gl_Position = projection_matrix * dist_pos;
// lighting on world coordinates not distorted ones
normal = mat3(transpose(inverse(model_matrix))) * normal_in;
light_direction = normalize(light_position - world_pos.xyz);
texture_coordinate = texture_coordinate_in;
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment