From f24011f642ee662277b5fcbbab1227f51613fdd0 Mon Sep 17 00:00:00 2001 From: "m.gaedke" Date: Wed, 25 Jan 2023 21:03:21 +0100 Subject: [PATCH] DepthofField Function added in this branch still runs into segFault --- CMakeLists.txt | 6 ++- camera/perspectivecamera.h | 6 +++ ex4.cpp | 84 +++++++++++++++++++++-------------- renderer/simplerenderer.cpp | 4 -- shader/depthoffieldshader.cpp | 47 ++++++++++++++++++++ shader/depthoffieldshader.h | 33 ++++++++++++++ 6 files changed, 141 insertions(+), 39 deletions(-) create mode 100644 shader/depthoffieldshader.cpp create mode 100644 shader/depthoffieldshader.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 5ed9dac..52d5575 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -28,7 +28,7 @@ file(GLOB shader_src "shader/*.cpp") # The tracey library add_library(tracey STATIC ${common_src} ${noise_src} ${camera_src} ${light_src} ${primitive_src} ${renderer_src} ${scene_src} ${shader_src} light/ambientlight.cpp light/ambientlight.h - light/spotlight.cpp light/spotlight.h post-processing/bloomshader.cpp post-processing/bloomshader.h) + light/spotlight.cpp light/spotlight.h post-processing/bloomshader.cpp post-processing/bloomshader.h shader/depthoffieldshader.cpp shader/depthoffieldshader.h) if(NOT WIN32) target_link_libraries(tracey ${CMAKE_THREAD_LIBS_INIT} ${X11_LIBRARIES}) endif() @@ -73,6 +73,10 @@ endif() add_executable(fancy1 fancy1.cpp) target_link_libraries(fancy1 tracey) +set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -O0") + +set(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -O0") + diff --git a/camera/perspectivecamera.h b/camera/perspectivecamera.h index 638f392..0d0f8f2 100644 --- a/camera/perspectivecamera.h +++ b/camera/perspectivecamera.h @@ -36,6 +36,12 @@ public: // Camera functions Ray createRay(float x, float y) const override; + //Getter + Vector3d getPosition() const { return position; } + Vector3d getRightDirection() const { return rightDirection; } + Vector3d getUpDirection() const { return upDirection; } + + protected: Vector3d position; Vector3d forwardDirection; diff --git a/ex4.cpp b/ex4.cpp index cadf20c..678962c 100644 --- a/ex4.cpp +++ b/ex4.cpp @@ -16,6 +16,7 @@ #include "shader/mirrorshader.h" #include "shader/phongshader.h" #include "shader/cooktorranceshader.h" +#include "shader/depthoffieldshader.h" #include "light/ambientlight.h" #include "light/pointlight.h" @@ -25,40 +26,6 @@ int main() { // Let's create a simple scene... SimpleScene scene; - // Add shaders - auto mirror = std::make_shared(); - auto white = std::make_shared(Color(0.9f, 0.9f, 0.9f)); - auto red = std::make_shared(Color(1.0f, 0.3f, 0.2f)); - auto blue = std::make_shared(Color(0.2f, 0.3f, 1.0f)); - auto orange = std::make_shared(Color(1.0f, 0.64f, 0.0f), 1.0f, Color(1.0f, 1.0f, 1.0f), 1.0f, 25.0f); - auto gold= std::make_shared(Color(0.83f, 0.69f, 0.22f), Color(1.0f, 1.0f, 0.0f), 1.2f, 0.2f); - auto blueMetallic = std::make_shared("data/blue-metallic-paint.binary", Color(7.0f, 7.0f, 7.0f)); - auto darkRed = std::make_shared("data/dark-red-paint.binary", Color(7.0f, 7.0f, 7.0f)); - - // Set up the walls - // --------------------------------------------------------------------------- - scene.add(std::make_shared(Vector3d(0.0f, 0.0f, +5.0f), Vector3d(0.0f, 0.0f, -1.0f), mirror)); - - scene.add(std::make_shared(Vector3d(0.0f, 0.0f, -5.0f), Vector3d(0.0f, 0.0f, +1.0f), mirror)); - scene.add(std::make_shared(Vector3d(0.0f, +5.0f, 0.0f), Vector3d(0.0f, -1.0f, 0.0f), white)); - scene.add(std::make_shared(Vector3d(0.0f, -5.0f, 0.0f), Vector3d(0.0f, +1.0f, 0.0f), white)); - scene.add(std::make_shared(Vector3d(+5.0f, 0.0f, 0.0f), Vector3d(-1.0f, 0.0f, 0.0f), blue)); - scene.add(std::make_shared(Vector3d(-5.0f, 0.0f, 0.0f), Vector3d(+1.0f, 0.0f, 0.0f), red)); - - scene.add(std::make_shared(Vector3d(-3.0f, 0.0f, 0.0f), 1.0f, blueMetallic)); - scene.add(std::make_shared(Vector3d(0.0f, 2.0f, 0.0f), 1.0f, orange)); - scene.add(std::make_shared(Vector3d(3.0f, 0.0f, 0.0f), 1.0f, darkRed)); - - // Add the teapot - auto teapot = std::make_shared(gold); - teapot->loadObj("data/teapot.obj", Vector3d(3.0f, 3.0f, 3.0f), Vector3d(0.0f, -5.0f, 0.0f)); - scene.add(teapot); - - // Add ambient light - scene.add(std::make_shared(0.15f)); - scene.add(std::make_shared(Vector3d(0.0f, 4.0f, -4.0f), 15.0f)); - scene.add(std::make_shared(Vector3d(0.0f, 4.0f, 4.0f), 15.0f)); - // Set up the camera PerspectiveCamera camera; camera.setFovAngle(90.0f); @@ -66,6 +33,55 @@ int main() { camera.setForwardDirection(Vector3d(0.0f, 0.0f, 1.0f)); camera.setUpDirection(Vector3d(0.0f, 1.0f, 0.0f)); + // Add shaders + auto mirror = std::make_shared(); + auto white = std::make_shared(Color(0.9f, 0.9f, 0.9f)); + auto red = std::make_shared(Color(1.0f, 0.3f, 0.2f)); + auto blue = std::make_shared(Color(0.2f, 0.3f, 1.0f)); + auto orange = std::make_shared(Color(1.0f, 0.64f, 0.0f), 1.0f, Color(1.0f, 1.0f, 1.0f), 1.0f, 25.0f); + auto gold= std::make_shared(Color(0.83f, 0.69f, 0.22f), Color(1.0f, 1.0f, 0.0f), 1.2f, 0.2f); + auto blueMetallic = std::make_shared("../data/blue-metallic-paint.binary", Color(7.0f, 7.0f, 7.0f)); + auto darkRed = std::make_shared("../data/dark-red-paint.binary", Color(7.0f, 7.0f, 7.0f)); + + auto dofShader = std::make_shared(scene, Color(0.9f, 0.9f, 0.9f), 100, 0.1f, 10.0f, 50.0f, camera); + + + + // Set up the walls + // --------------------------------------------------------------------------- + + scene.add(std::make_shared(Vector3d(0.0f, 0.0f, +5.0f), Vector3d(0.0f, 0.0f, -1.0f), mirror)); + + scene.add(std::make_shared(Vector3d(0.0f, 0.0f, -5.0f), Vector3d(0.0f, 0.0f, +1.0f), mirror)); + scene.add(std::make_shared(Vector3d(0.0f, +5.0f, 0.0f), Vector3d(0.0f, -1.0f, 0.0f), white)); + scene.add(std::make_shared(Vector3d(0.0f, -5.0f, 0.0f), Vector3d(0.0f, +1.0f, 0.0f), white)); + scene.add(std::make_shared(Vector3d(+5.0f, 0.0f, 0.0f), Vector3d(-1.0f, 0.0f, 0.0f), dofShader)); + scene.add(std::make_shared(Vector3d(-5.0f, 0.0f, 0.0f), Vector3d(+1.0f, 0.0f, 0.0f), red)); + + scene.add(std::make_shared(Vector3d(-3.0f, 0.0f, 0.0f), 1.0f, blueMetallic)); + scene.add(std::make_shared(Vector3d(0.0f, 2.0f, 0.0f), 1.0f, orange)); + scene.add(std::make_shared(Vector3d(3.0f, 0.0f, 0.0f), 1.0f, darkRed)); + + // Create a DOFShader instance with the desired aperture size, focal distance, and focal length + + // Use the DOFShader instance as the shader for an object in the scene + auto sphere = std::make_shared(Vector3d(-3.0f, 0.0f, 0.0f), 1.0f, dofShader); + + // Add the sphere to the scene + scene.add(sphere); + + // Add the teapot + auto teapot = std::make_shared(gold); + teapot->loadObj("../data/teapot.obj", Vector3d(3.0f, 3.0f, 3.0f), Vector3d(0.0f, -5.0f, 0.0f)); + scene.add(teapot); + + // Add ambient light + scene.add(std::make_shared(0.15f)); + //scene.add(std::make_shared(Vector3d(0.0f, 4.0f, -4.0f), 15.0f)); + scene.add(std::make_shared(Vector3d(0.0f, 2.5f, -4.0f), 7.0f)); + + + // Render the scene SimpleRenderer renderer; renderer.renderImage(scene, camera, 512, 512).save("result.png"); diff --git a/renderer/simplerenderer.cpp b/renderer/simplerenderer.cpp index ffd69e2..fea71a3 100644 --- a/renderer/simplerenderer.cpp +++ b/renderer/simplerenderer.cpp @@ -76,15 +76,11 @@ Texture SimpleRenderer::renderImage(Scene const &scene, Camera const &camera, in // Post-processing // Bloom shader - //Bloomshader bloomshader = Bloomshader(image, 0.48f, 10); - //bloomshader.thresholdshader(); image.save("original.png"); Bloomshader bloomEffect = Bloomshader(image.getImage()); image.setTexture(bloomEffect.bloom(0.55f, 5, 10.0f, 0.06f)); - //image = bloomshader.getimage(); - return image; } diff --git a/shader/depthoffieldshader.cpp b/shader/depthoffieldshader.cpp new file mode 100644 index 0000000..ab6672e --- /dev/null +++ b/shader/depthoffieldshader.cpp @@ -0,0 +1,47 @@ +#include + +#include "depthoffieldshader.h" + + +DOFShader::DOFShader(SimpleScene& _scene, Color const &_diffuseColor, int _numSamples, float _aperture, float _focalDistance, float _focalLength, PerspectiveCamera& _camera) : scene(_scene), diffuseColor(_diffuseColor), numSamples(_numSamples), aperture(_aperture), +focalDistance(_focalDistance), focalLength(_focalLength), camera(_camera) {} + +std::random_device DOFShader::rd; +std::mt19937 DOFShader::gen(DOFShader::rd()); + +Color DOFShader::shade(Scene const &scene, Ray const &ray) const { + Color color; + + // Accumulate the light over all light sources + for (const auto &light : scene.lights()) { + Light::Illumination const illum = light->illuminate(scene, ray); + Color const diffuse = this->diffuseColor * std::max(dotProduct(-illum.direction, ray.normal), 0.0f); + // Add the sample color to the final color + color += diffuse * sample(ray, illum); + } + + return color; +} + +Color DOFShader::sample(Ray ray, Light::Illumination const &illum) const { + + std::uniform_real_distribution dis(-1.0, 1.0); + + // calculate the point of focus + Vector3d focusPoint = ray.origin + ray.direction * focalDistance; + + // create a random point on the aperture + Vector3d rnd = Vector3d(dis(gen), dis(gen), 0); + Vector3d offset = aperture * (rnd.x * camera.getRightDirection() + rnd.y * camera.getUpDirection()); + + // create the new ray with the offset point + Vector3d dofRayStart = camera.getPosition() + offset; + Vector3d dofRayDir = normalized(focusPoint - (camera.getPosition() + offset)); + + Ray dofRay = Ray(dofRayStart, dofRayDir); + + // trace the new ray and sample the color + + Color tracedColor = scene.traceRay(dofRay); + return tracedColor; +} diff --git a/shader/depthoffieldshader.h b/shader/depthoffieldshader.h new file mode 100644 index 0000000..d9adeb9 --- /dev/null +++ b/shader/depthoffieldshader.h @@ -0,0 +1,33 @@ +#ifndef DEPTHOFFIELDSHADER_H +#define DEPTHOFFIELDSHADER_H + +#include "shader/shader.h" +#include "light/light.h" +#include "camera/perspectivecamera.h" +#include +#include "scene/simplescene.h" + +class DOFShader : public Shader { + +public: + // Constructor / Desctructor + DOFShader(SimpleScene& _scene, Color const &_diffuseColor, int _numSamples, float _aperture, float _focalDistance, float _focalLength, PerspectiveCamera& _camera); + virtual ~DOFShader() = default; + + // Shader functions + virtual Color shade(Scene const &scene, Ray const &ray) const; + +private: + float aperture, focalDistance, focalLength; + int numSamples; + PerspectiveCamera& camera; + SimpleScene& scene; + Color diffuseColor; + static std::random_device rd; + static std::mt19937 gen; + + + Color sample(Ray ray, Light::Illumination const &illum) const; +}; + +#endif \ No newline at end of file