diff --git a/src/acceleration/accel.cpp b/src/acceleration/accel.cpp index 64da596..56610a8 100644 --- a/src/acceleration/accel.cpp +++ b/src/acceleration/accel.cpp @@ -6,21 +6,12 @@ #include "../definitions/ray.hpp" #include "../definitions/primatives/triangle.hpp" -// enum AccelerationMode { -// MODE_ACCELERATION_DEFAULT, -// MODE_NONE, -// MODE_KD, -// MODE_KD_SLOW, -// MODE_BVH -// }; - Acceleration::Acceleration(AccelerationMode mode) { m_mode = mode; } void Acceleration::Construct(std::vector triangles) { switch (m_mode) { - case MODE_ACCELERATION_DEFAULT: case MODE_ACCELERATION_NONE: Constructed = false; break; @@ -55,7 +46,6 @@ void Acceleration::Construct(std::vector triangles) { bool Acceleration::Intersect(Ray ray, Triangle*& triMin, float& tMin) { if (!Constructed) return false; switch (m_mode) { - case MODE_ACCELERATION_DEFAULT: case MODE_ACCELERATION_NONE: break; diff --git a/src/acceleration/accel.hpp b/src/acceleration/accel.hpp index fe637c0..d41c936 100644 --- a/src/acceleration/accel.hpp +++ b/src/acceleration/accel.hpp @@ -14,14 +14,14 @@ class Triangle; class Acceleration { public: - Acceleration(AccelerationMode mode = MODE_ACCELERATION_DEFAULT); + Acceleration(AccelerationMode mode = MODE_ACCELERATION_KD_SLOW); void Construct(std::vector triangles); bool Intersect(Ray ray, Triangle*& triMin, float& tMin); bool Constructed = false; private: - AccelerationMode m_mode = MODE_ACCELERATION_DEFAULT; + AccelerationMode m_mode = MODE_ACCELERATION_KD_SLOW; // KDTree KDTree* m_kdtree = nullptr; diff --git a/src/core/renderer.hpp b/src/core/renderer.hpp index 99a3d0a..6d85293 100644 --- a/src/core/renderer.hpp +++ b/src/core/renderer.hpp @@ -28,7 +28,7 @@ public: private: int m_samples = -1; - OperationMode m_mode = MODE_OPERATION_DEFAULT; + OperationMode m_mode = MODE_OPERATION_PROGRESSIVE_GUI; DisplayInterface* m_interface = nullptr; FrameBuffer* m_framebuffer = nullptr; diff --git a/src/display/framebuffer.cpp b/src/display/framebuffer.cpp index c23af7d..3a2fd50 100644 --- a/src/display/framebuffer.cpp +++ b/src/display/framebuffer.cpp @@ -5,46 +5,6 @@ #include "../pixel.hpp" - -void FrameBuffer::SetPixel(int x, int y, glm::vec3 p) { - Pixel pixel{ (uint8_t)(pow(p.r, Gamma) * 255.0f), (uint8_t)(pow(p.g, Gamma) * 255.0f), (uint8_t)(pow(p.b, Gamma) * 255.0f) }; - Data[y * this->XRes + x] = pixel.rgb(); -} - -void FrameBuffer::SetPixelSafe(int x, int y, glm::vec3 p) { - if (x >= 0 && x < this->XRes && y >= 0 && this->YRes) { - Pixel pixel{ (uint8_t)(pow(p.r, Gamma) * 255.0f), (uint8_t)(pow(p.g, Gamma) * 255.0f), (uint8_t)(pow(p.b, Gamma) * 255.0f) }; - Data[y * this->XRes + x] = pixel.rgb(); - } -} - -void FrameBuffer::SetPixelSafe(int x, int y, glm::vec3 p) { - if (x >= 0 && x < this->XRes && y >= 0 && this->YRes) { - Pixel pixel{ (uint8_t)(pow(p.r, Gamma) * 255.0f), (uint8_t)(pow(p.g, Gamma) * 255.0f), (uint8_t)(pow(p.b, Gamma) * 255.0f) }; - Data[y * this->XRes + x] = pixel.rgb(); - } -} - -void FrameBuffer::DumpToFile(std::string path) { - // int stbi_write_png(char const* filename, int w, int h, int comp, const void* data, int stride_in_bytes); - stbi_write_png(path.c_str(), this->XRes, this->YRes, sizeof(uint32_t), this->Data, sizeof(uint32_t) * this->XRes); -} - -void FrameBuffer::SetFramebuffer(uint32_t* fb) { - free(Data); - Data = fb; -} - -void FrameBuffer::ClearFramebuffer() { - memset((void*)Data, 0, (XRes * YRes) * sizeof(uint32_t)); -} - -FrameBuffer::~FrameBuffer() { - free(Data); -} - - - FrameBuffer::FrameBuffer(int xres, int yres) { XRes = xres; YRes = yres; RenderData = (uint32_t*)malloc((xres * yres) * sizeof(uint32_t)); @@ -91,21 +51,53 @@ void FrameBuffer::AddPixelSafe(int x, int y, glm::vec3 p, int mode = 0) { } } -// PostProcesses based on previous input, the tonemap mode and -// the sample count for additive frames to average -void PostProcess(int spp, ToneMapMode mode = MODE_TONEMAP_CLAMP); +void FrameBuffer::PostProcess(int& spp, ToneMapMode mode, RenderMode rendermode) { + if (rendermode == MODE_RENDER_NORMALS || rendermode == MODE_RENDER_PATH_LENGTH) { + spp = 0; + for (int y = 0; y < h; y++) + for (int x = 0; x < w; x++) { + RenderPostProcess[y * w + x] = src[y * w + x]; + } + return; + } -// Saves the RenderData to a file, data must first be processed -// by the render engine / the engine manager based on mode -void DumpToFile(std::string path); + if (rendermode == MODE_RENDER_PATH_BOUNCES) { + spp++; + for (int y = 0; y < h; y++) + for (int x = 0; x < w; x++) { + dst[y * w + x] = src[y * w + x] / (float)spp; + } + return; + } -// Copys the active render data to the target framebuffer, -// relies on the framebuffers to be of equal size and not -// not that -void CopyData(uint32_t* dest); + SPP++; + for (int y = 0; y < h; y++) + for (int x = 0; x < w; x++) { + dst[y * w + x] = src[y * w + x] / (float)SPP; + } +} -// Clears the RenderTarget and the RenderData -void ClearFramebuffer(); +void FrameBuffer::DumpToFile(std::string path) { + // int stbi_write_png(char const* filename, int w, int h, int comp, const void* data, int stride_in_bytes); + // Red and Blue channels need to be swapped + stbi_write_png(path.c_str(), this->XRes, this->YRes, sizeof(uint32_t), this->RenderData, sizeof(uint32_t) * this->XRes); +} -~FrameBuffer(); +void FrameBuffer::CopyData(uint32_t* dest) { + memcpy((void*)dest, (void*)RenderData, (this->XRes * this->YRes) * sizeof(uint32_t)); +} + +void FrameBuffer::ClearFramebuffer() { + memset((void*)RenderTarget, 0, (this->XRes * this->YRes) * sizeof(glm::vec3)); + memset((void*)RenderPostProcess, 0, (this->XRes * this->YRes) * sizeof(glm::vec3)); + memset((void*)RenderData, 0, (this->XRes * this->YRes) * sizeof(uint32_t)); +} + +FrameBuffer::~FrameBuffer() { + free(RenderNormalsTarget); + free(RenderAlbedoTarget); + free(RenderTarget); + free(RenderPostProcess); + free(RenderData); +} diff --git a/src/display/framebuffer.hpp b/src/display/framebuffer.hpp index 6ea0de8..04d217d 100644 --- a/src/display/framebuffer.hpp +++ b/src/display/framebuffer.hpp @@ -29,9 +29,14 @@ public: // Add to the render target void AddPixelSafe(int x, int y, glm::vec3 p, int mode = 0); + // Sets a pixel on the RenderData framebuffer, ready for rendering + // by the display or whatever mode the engine is in. the framebuffer + // doesnt care. + void RenderSetPixelSafe(int x, int y, uint32_t p); + // PostProcesses based on previous input, the tonemap mode and // the sample count for additive frames to average - void PostProcess(int spp, ToneMapMode mode = MODE_TONEMAP_CLAMP); + void PostProcess(int& spp, ToneMapMode mode = MODE_TONEMAP_CLAMP, RenderMode rendermode = MODE_RENDER_PATHTRACE); // Saves the RenderData to a file, data must first be processed // by the render engine / the engine manager based on mode diff --git a/src/engine/renderengine.hpp b/src/engine/renderengine.hpp index 77739cb..a1f7be8 100644 --- a/src/engine/renderengine.hpp +++ b/src/engine/renderengine.hpp @@ -17,7 +17,7 @@ public: void PostProcess(glm::vec3* src, glm::vec3* dst, int w, int h); - RenderMode Mode = MODE_RENDER_DEFAULT; + RenderMode Mode = MODE_RENDER_PATHTRACE; int SPP = 0; int SPPDepth = 0; diff --git a/test/default.cpp b/test/default.cpp new file mode 100644 index 0000000..e69de29 diff --git a/test/main.cpp b/test/main.cpp index 6577ad7..8922c50 100644 --- a/test/main.cpp +++ b/test/main.cpp @@ -2,8 +2,8 @@ #include "../src/inferno.hpp" -static const int width = 1000; -static const int height = 1000; +static const int width = 300; +static const int height = 300; int main(int argc, char** argv) { InfernoEngine inferno; @@ -18,8 +18,8 @@ int main(int argc, char** argv) { Scene* scene = new Scene(width, height); scene->camera = new Camera(width, height); + scene->objects.push_back(new Sphere({ 0.0f, 0.0f, -4.0f }, 1.0f, new Material({ 1.0f, 1.0f, 1.0f }, 0.0f, 5.0f))); scene->objects.push_back(new Sphere({ 35.0f, 26.0f, 25.0f }, 15.0f, new Material({ 1.0f, 1.0f, 1.0f }, 0.0f, 5.0f))); - scene->objects.push_back(new Sphere({-0.457001f, 0.19f, -3.53899f}, 0.02f, new Material({ 1.0f, 0.9f, 0.8f }, 0.0f, 500.0f))); scene->objects.push_back(new Plane( { 0.0f, -1.0f, 0.0f }, { 0.0f, -1.0f, 0.0f }, new Material({ 0.847f, 0.792f, 0.658f }, 0.2f))); std::vector tris = LoadTrianglesBasic("E://Projects//Inferno//resources//dragon-normals.obj", "E://Projects//Inferno//resources"); diff --git a/test/stanford_dragon.cpp b/test/stanford_dragon.cpp new file mode 100644 index 0000000..a5dcfa1 --- /dev/null +++ b/test/stanford_dragon.cpp @@ -0,0 +1,36 @@ +#include + +#include "../src/inferno.hpp" + +static const int width = 1000; +static const int height = 1000; + +int main(int argc, char** argv) { + InfernoEngine inferno; + + inferno.SetMode(MODE_OPERATION_PROGRESSIVE_GUI); + + inferno.InitWindow(width, height); + + Scene* scene = new Scene(width, height); + scene->camera = new Camera(width, height); + + scene->objects.push_back(new Sphere({ 35.0f, 26.0f, 25.0f }, 15.0f, new Material({ 1.0f, 1.0f, 1.0f }, 0.0f, 5.0f))); + scene->objects.push_back(new Sphere({-0.457001f, 0.19f, -3.53899f}, 0.02f, new Material({ 1.0f, 0.9f, 0.8f }, 0.0f, 500.0f))); + scene->objects.push_back(new Plane( { 0.0f, -1.0f, 0.0f }, { 0.0f, -1.0f, 0.0f }, new Material({ 0.847f, 0.792f, 0.658f }, 0.2f))); + + std::vector tris = LoadTrianglesBasic("E://Projects//Inferno//resources//dragon-normals.obj", "E://Projects//Inferno//resources"); + // std::vector tris = LoadTrianglesBasic("//home//ben//programming//inferno//resources//dragon-normals.obj", "//home//ben//programming//inferno//resources//resources"); + + Mesh* mesh1 = new Mesh(tris); + mesh1->Translate({ 0.2f, -1.04, -3.8f }); + mesh1->Optimise(); + scene->meshs.push_back(mesh1); + + inferno.SetScene(scene); + + inferno.Ready(); + inferno.Render(); + + return 0; +}