Improved transfer function business
This commit is contained in:
parent
d978630f26
commit
fc2488c578
|
|
@ -10,6 +10,7 @@
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include "objs/sphere.h"
|
#include "objs/sphere.h"
|
||||||
|
|
||||||
|
// TODO: Probbably move this transfer function business into a different file
|
||||||
// Samples the voxel nearest to the given coordinates. TODO: Can be re-used in other places so move
|
// Samples the voxel nearest to the given coordinates. TODO: Can be re-used in other places so move
|
||||||
__device__ float sampleVolumeNearest(float* volumeData, const int volW, const int volH, const int volD, int vx, int vy, int vz) {
|
__device__ float sampleVolumeNearest(float* volumeData, const int volW, const int volH, const int volD, int vx, int vy, int vz) {
|
||||||
if (vx < 0) vx = 0;
|
if (vx < 0) vx = 0;
|
||||||
|
|
@ -44,6 +45,32 @@ __device__ float sampleVolumeTrilinear(float* volumeData, const int volW, const
|
||||||
return c0 * (1.0f - dz) + c1 * dz;
|
return c0 * (1.0f - dz) + c1 * dz;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Function to map a temperature to an RGB color
|
||||||
|
__device__ Color3 temperatureToRGB(float temperature) {
|
||||||
|
// atm, the scalar field is normalized
|
||||||
|
const float minTemp = 0.0f; // coldest == deep blue
|
||||||
|
const float maxTemp = 1.0f; // hottest temperature == deep red
|
||||||
|
|
||||||
|
temperature = clamp(temperature, minTemp, maxTemp);
|
||||||
|
float t = normalize(temperature, minTemp, maxTemp);
|
||||||
|
|
||||||
|
float r, g, b;
|
||||||
|
|
||||||
|
if (t < 0.5f) { // From blue to green
|
||||||
|
t *= 2.0f; // Scale to [0, 1]
|
||||||
|
r = interpolate(0.0f, 0.0f, t);
|
||||||
|
g = interpolate(0.0f, 1.0f, t);
|
||||||
|
b = interpolate(1.0f, 0.0f, t);
|
||||||
|
} else { // From green to red
|
||||||
|
t = (t - 0.5f) * 2.0f; // Scale to [0, 1]
|
||||||
|
r = interpolate(0.0f, 1.0f, t);
|
||||||
|
g = interpolate(1.0f, 0.0f, t);
|
||||||
|
b = interpolate(0.0f, 0.0f, t);
|
||||||
|
}
|
||||||
|
|
||||||
|
return Color3::init(r, g, b);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// Transfer function
|
// Transfer function
|
||||||
__device__ float4 transferFunction(float density, Vec3 grad, Point3 pos, Vec3 rayDir) {
|
__device__ float4 transferFunction(float density, Vec3 grad, Point3 pos, Vec3 rayDir) {
|
||||||
|
|
@ -52,7 +79,8 @@ __device__ float4 transferFunction(float density, Vec3 grad, Point3 pos, Vec3 ra
|
||||||
float alphaSample = density * 0.1f;
|
float alphaSample = density * 0.1f;
|
||||||
// result.w = 1.0f - expf(-density * 0.1f);
|
// result.w = 1.0f - expf(-density * 0.1f);
|
||||||
|
|
||||||
Color3 baseColor = Color3::init(density, 0.1f*density, 1.f - density); // TODO: Implement a proper transfer function
|
// Color3 baseColor = Color3::init(density, 0.1f*density, 1.f - density); // TODO: Implement a proper transfer function
|
||||||
|
Color3 baseColor = temperatureToRGB(density);
|
||||||
|
|
||||||
Vec3 normal = -grad.normalize();
|
Vec3 normal = -grad.normalize();
|
||||||
|
|
||||||
|
|
@ -80,6 +108,7 @@ __device__ float4 transferFunction(float density, Vec3 grad, Point3 pos, Vec3 ra
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// TODO: instead of IMAGEWIDTH and IMAGEHEIGHT this should reflect the windowSize;
|
// TODO: instead of IMAGEWIDTH and IMAGEHEIGHT this should reflect the windowSize;
|
||||||
__global__ void raycastKernel(float* volumeData, FrameBuffer framebuffer) {
|
__global__ void raycastKernel(float* volumeData, FrameBuffer framebuffer) {
|
||||||
int px = blockIdx.x * blockDim.x + threadIdx.x;
|
int px = blockIdx.x * blockDim.x + threadIdx.x;
|
||||||
|
|
@ -149,16 +178,13 @@ __global__ void raycastKernel(float* volumeData, FrameBuffer framebuffer) {
|
||||||
Point3 pos = d_cameraPos + rayDir * tCurrent;
|
Point3 pos = d_cameraPos + rayDir * tCurrent;
|
||||||
|
|
||||||
// Convert to volume indices
|
// Convert to volume indices
|
||||||
// float fx = pos.x * (VOLUME_WIDTH - 1);
|
|
||||||
// float fy = pos.y * (VOLUME_HEIGHT - 1);
|
|
||||||
// float fz = pos.z * (VOLUME_DEPTH - 1);
|
|
||||||
int ix = (int)roundf(pos.x);
|
int ix = (int)roundf(pos.x);
|
||||||
int iy = (int)roundf(pos.y);
|
int iy = (int)roundf(pos.y);
|
||||||
int iz = (int)roundf(pos.z);
|
int iz = (int)roundf(pos.z);
|
||||||
|
|
||||||
// Sample (pick appropriate method based on volume size)
|
// Sample (pick appropriate method based on volume size)
|
||||||
float density = sampleVolumeNearest(volumeData, VOLUME_WIDTH, VOLUME_HEIGHT, VOLUME_DEPTH, ix, iy, iz);
|
// float density = sampleVolumeNearest(volumeData, VOLUME_WIDTH, VOLUME_HEIGHT, VOLUME_DEPTH, ix, iy, iz);
|
||||||
// float density = sampleVolumeTrilinear(volumeData, VOLUME_WIDTH, VOLUME_HEIGHT, VOLUME_DEPTH, pos.x, pos.y, pos.z);
|
float density = sampleVolumeTrilinear(volumeData, VOLUME_WIDTH, VOLUME_HEIGHT, VOLUME_DEPTH, pos.x, pos.y, pos.z);
|
||||||
|
|
||||||
// If density ~ 0, skip shading
|
// If density ~ 0, skip shading
|
||||||
if (density > minAllowedDensity) {
|
if (density > minAllowedDensity) {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue