EX02 Fixes

This commit is contained in:
Stephen Seo 2021-08-21 17:32:27 +09:00
parent 2bf4dd0cf7
commit 2f8726b705
2 changed files with 24 additions and 28 deletions

View file

@ -10,15 +10,14 @@
const float PI = std::acos(-1.0f); const float PI = std::acos(-1.0f);
glm::vec3 Ex02::RT::Internal::defaultSpherePos() { glm::vec3 Ex02::RT::Internal::defaultSpherePos() {
// the default model matrix pushes everything back 2 units, return glm::vec3{0.0f, 0.0f, -2.5f};
// so it should be ok to define the sphere at location 0
return glm::vec3{0.0f, 0.0f, 0.0f};
} }
glm::vec3 Ex02::RT::Internal::defaultLightPos() { glm::vec3 Ex02::RT::Internal::defaultLightPos() {
return glm::vec3{1.0f, 1.0f, 0.0f}; return glm::vec3{4.0f, 4.0f, 0.0f};
} }
/*
glm::mat4x4 Ex02::RT::Internal::defaultMVP() { glm::mat4x4 Ex02::RT::Internal::defaultMVP() {
glm::mat4x4 mvp = glm::perspective( glm::mat4x4 mvp = glm::perspective(
PI / 2.0f, PI / 2.0f,
@ -38,6 +37,7 @@ glm::mat4x4 Ex02::RT::Internal::defaultMVP() {
return mvp; return mvp;
} }
*/
std::optional<glm::vec3> Ex02::RT::Internal::rayToSphere( std::optional<glm::vec3> Ex02::RT::Internal::rayToSphere(
glm::vec3 rayPos, glm::vec3 rayPos,
@ -73,13 +73,18 @@ std::optional<glm::vec3> Ex02::RT::Internal::rayToSphere(
+ rayDir.y * tempVec.y + rayDir.y * tempVec.y
+ rayDir.z * tempVec.z; + rayDir.z * tempVec.z;
float dist = -temp - std::sqrt(delta); float dist = -temp - std::sqrt(delta);
if(dist < 0.0f) { float dist2 = -temp + std::sqrt(delta);
dist = -temp + std::sqrt(delta); float min = dist > dist2 ? dist2 : dist;
if(dist < 0.0f) { float max = dist > dist2 ? dist : dist2;
if(min < 0.0f) {
if(max < 0.0f) {
return {}; return {};
} else {
return {rayPos + rayDir * max};
} }
} else {
return {rayPos + rayDir * min};
} }
return {rayPos + rayDir * dist};
} }
} }
@ -97,46 +102,39 @@ std::vector<unsigned char> Ex02::RT::renderGraySphere(
float sphereRadius, float sphereRadius,
int threadCount, int threadCount,
glm::vec3 spherePos, glm::vec3 spherePos,
glm::vec3 lightPos, glm::vec3 lightPos) {
glm::mat4x4 mvp) {
std::vector<unsigned char> grayscalePixels; std::vector<unsigned char> grayscalePixels;
grayscalePixels.resize(outputWidth * outputHeight); grayscalePixels.resize(outputWidth * outputHeight);
// glm::vec3 tr_spherePos = mvp * glm::vec4{spherePos, 1.0f};
// glm::vec3 tr_lightPos = mvp * glm::vec4{lightPos, 1.0f};
glm::vec3 tr_spherePos = glm::vec3{0.0f, 0.0f, -2.0f};
glm::vec3 tr_lightPos = glm::vec3{1.0f, 1.0f, 0.0f};
glm::vec3 rayPos{0.0f, 0.0f, 0.0f}; glm::vec3 rayPos{0.0f, 0.0f, 0.0f};
if(threadCount == 1) { if(threadCount == 1) {
for(unsigned int j = 0; j < outputHeight; ++j) { for(unsigned int j = 0; j < outputHeight; ++j) {
float offsetY = ((float)j - ((float)outputHeight / 2.0f)); float offsetY = ((float)j + 0.5f - ((float)outputHeight / 2.0f));
for(unsigned int i = 0; i < outputWidth; ++i) { for(unsigned int i = 0; i < outputWidth; ++i) {
float offsetX = ((float)i - ((float)outputWidth / 2.0f)); float offsetX = ((float)i + 0.5f - ((float)outputWidth / 2.0f));
glm::vec3 rayDir = glm::vec3{ glm::vec3 rayDir = glm::vec3{
offsetX, offsetY, -EX02_RAY_TRACER_DRAW_PLANE}; offsetX, offsetY, -EX02_RAY_TRACER_DRAW_PLANE};
auto rayResult = Internal::rayToSphere( auto rayResult = Internal::rayToSphere(
rayPos, rayDir, tr_spherePos, sphereRadius); rayPos, rayDir, spherePos, sphereRadius);
if(rayResult) { if(rayResult) {
glm::vec3 toLight = *rayResult - tr_lightPos; glm::vec3 toLight = lightPos - *rayResult;
toLight /= std::sqrt( toLight /= std::sqrt(
toLight.x * toLight.x toLight.x * toLight.x
+ toLight.y * toLight.y + toLight.y * toLight.y
+ toLight.z * toLight.z); + toLight.z * toLight.z);
glm::vec3 toLightPos = *rayResult + toLight * 2.4f; glm::vec3 toLightPos = *rayResult + toLight;
auto collResult = Internal::rayToSphere( auto collResult = Internal::rayToSphere(
toLightPos, toLight, tr_spherePos, sphereRadius); toLightPos, toLight, spherePos, sphereRadius);
if(collResult) { if(collResult) {
continue; continue;
} }
glm::vec3 resultToLight = tr_lightPos - *rayResult;
glm::vec3 resultToOrigin = rayPos - *rayResult; glm::vec3 resultToOrigin = rayPos - *rayResult;
float angle = Internal::angleBetweenRays( float angle = Internal::angleBetweenRays(
resultToLight, toLight,
resultToOrigin); resultToOrigin);
if(angle <= PI && angle >= 0.0f) { if(angle <= PI && angle >= 0.0f) {
grayscalePixels.at(i + j * outputWidth) = grayscalePixels.at(i + j * outputWidth) =
(1.0f - angle / PI) * 255.0f; (angle / PI) * 255.0f;
} }
} }
} }

View file

@ -20,7 +20,6 @@ namespace RT {
namespace Internal { namespace Internal {
glm::vec3 defaultSpherePos(); glm::vec3 defaultSpherePos();
glm::vec3 defaultLightPos(); glm::vec3 defaultLightPos();
glm::mat4x4 defaultMVP();
std::optional<glm::vec3> rayToSphere( std::optional<glm::vec3> rayToSphere(
glm::vec3 rayPos, glm::vec3 rayPos,
@ -39,8 +38,7 @@ std::vector<unsigned char> renderGraySphere(
float sphereRadius, float sphereRadius,
int threadCount = 1, int threadCount = 1,
glm::vec3 spherePos = Internal::defaultSpherePos(), glm::vec3 spherePos = Internal::defaultSpherePos(),
glm::vec3 lightPos = Internal::defaultLightPos(), glm::vec3 lightPos = Internal::defaultLightPos()
glm::mat4x4 mvp = Internal::defaultMVP()
); );
void writeGrayscaleToFile( void writeGrayscaleToFile(