Skip to content

Commit

Permalink
ray marched objects can now cast shadows on rasterized objects
Browse files Browse the repository at this point in the history
  • Loading branch information
nilspettersson committed Nov 28, 2020
1 parent 7834b6f commit 942b465
Show file tree
Hide file tree
Showing 2 changed files with 56 additions and 13 deletions.
61 changes: 50 additions & 11 deletions shaders/lib/rayMarching.glsl
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ struct Ray{
vec4 dir;
float length;
int steps;
bool hitRasterized;
};

vec4 multQuat(vec4 q1, vec4 q2){
Expand Down Expand Up @@ -40,7 +41,7 @@ Ray getRay(){

vec4 dir = rotate_vector(cameraRotation, vec4(rayDir, rayDir.z));

return Ray(dir, 0, 0);
return Ray(dir, 0, 0, false);
}

//gets the distance to the closest object in the sdf function.
Expand All @@ -60,23 +61,30 @@ Ray rayMarch(Ray ray){
if(dist < 0.01 ){
break;
}
if(DistOrigin * cosA > depth || DistOrigin > 10000){
//if ray does not hit anything
if(DistOrigin > 900){
DistOrigin = -1;
break;
}
//if ray hits rasterized object
if(DistOrigin * cosA > depth){
ray.hitRasterized = true;
DistOrigin *= cosA;
break;
}

steps++;
}

return Ray(ray.dir, DistOrigin, steps);
return Ray(ray.dir, DistOrigin, steps, ray.hitRasterized);
}

Ray rayMarchShadow(Ray ray, vec3 origin, float length){
Ray rayMarchShadow(Ray ray, vec3 origin){

float cosA = ray.dir.w;
float DistOrigin = 0;
int steps = 0;
for(int i = 0; i < 150; i++){
for(int i = 0; i < 200; i++){
vec3 point = origin + ray.dir.xyz * DistOrigin;

float dist = sdf(point);
Expand All @@ -85,14 +93,15 @@ Ray rayMarchShadow(Ray ray, vec3 origin, float length){
if(dist < 0.01 ){
break;
}
if(DistOrigin > length + 400 || DistOrigin > 10000){
if(DistOrigin > 10000){
DistOrigin = -1;
break;
}

steps++;
}

return Ray(ray.dir, DistOrigin, steps);
return Ray(ray.dir, DistOrigin, steps, ray.hitRasterized);
}

//gets the normal for a pixel in ray marcher.
Expand Down Expand Up @@ -123,9 +132,9 @@ vec4 rayMarchDiffuse(Ray ray, vec3 color){


//if pixel is in shadow dont add current light.
Ray toLightRay = Ray(vec4(normalize(toLight), 0), length(toLight), 0);
Ray toLightRay = Ray(vec4(normalize(toLight), 0), length(toLight), 0, false);
vec3 point2 = rayOrigin + ray.dir.xyz * (ray.length - 0.02);
toLightRay = rayMarchShadow(toLightRay, point2, disToLight);
toLightRay = rayMarchShadow(toLightRay, point2);
if(toLightRay.length != -1){
continue;
}
Expand Down Expand Up @@ -160,9 +169,9 @@ vec4 rayMarchGlossy(Ray ray, float roughness){
float disToLight = length(toLight) * 1.2;

//if pixel is in shadow dont add current light.
Ray toLightRay = Ray(vec4(normalize(toLight), 0), length(toLight), 0);
Ray toLightRay = Ray(vec4(normalize(toLight), 0), length(toLight), 0, false);
vec3 point2 = rayOrigin + ray.dir.xyz * (ray.length - 0.02);
toLightRay = rayMarchShadow(toLightRay, point2, disToLight);
toLightRay = rayMarchShadow(toLightRay, point2);
if(toLightRay.length != -1){
continue;
}
Expand Down Expand Up @@ -201,4 +210,34 @@ vec4 rayMarchAmbient(Ray ray, vec3 ambientColor, float amount){
ambientColor /= max(ray.steps * amount, 4);
vec4 output = vec4(ambientColor, 1);
return output;
}

vec4 rayMarchShadows(Ray ray, vec3 color){
//finding the point of the intersection.
vec3 rayOrigin = cameraPosition;
rayOrigin.z *= -1;
vec3 point = rayOrigin + ray.dir.xyz * ray.length;


int shadowCount = 0;
for(int i = 0; i < lightCount; i++){
vec3 pos = lightPositions[i];
pos.z *= -1;
vec3 toLight = pos - point;
float disToLight = length(toLight);


//if pixel is in shadow dont add current light.
Ray toLightRay = Ray(vec4(normalize(toLight), ray.dir.z), length(toLight), 0, false);
vec3 point2 = rayOrigin + ray.dir.xyz * (ray.length - 0.02);
toLightRay = rayMarchShadow(toLightRay, point2);
if(toLightRay.length != -1){
shadowCount++;
}

}

vec4 diffuse = vec4(color, 1);
diffuse.xyz /= shadowCount + 1;
return diffuse;
}
8 changes: 6 additions & 2 deletions shaders/postShader2.glsl
Original file line number Diff line number Diff line change
Expand Up @@ -16,21 +16,25 @@ float sdf(vec3 point){
transform1 = vec3(4, -8, 2);
float box2 = sdBox(point - transform1, vec3(2, 0.2, 2));

return min(box, box2);
return (box);
}

fragment{
Ray ray = getRay();
ray = rayMarch(ray);
//vec4 diffuse = rayMarchDiffuse(rayDir, vec3(1, 0.5, 0.5));
vec4 diffuse = mix(rayMarchDiffuse(ray, vec3(1, 0, 0)), rayMarchGlossy(ray, 0.08), 0.5) + rayMarchAmbient(ray, vec3(0.2, 0.3, 0.4), 1);


vec4 output = texture;
if(ray.length == -1){
return vec4(output);
}
else if(ray.hitRasterized == true){
ray.length = depth / ray.dir.w;
return rayMarchShadows(ray, vec3(texture.xyz));
}
else{
vec4 diffuse = mix(rayMarchDiffuse(ray, vec3(1, 0, 0)), rayMarchGlossy(ray, 0.08), 0.5);
return vec4(diffuse);
}

Expand Down

0 comments on commit 942b465

Please sign in to comment.