46 lines
1.4 KiB
C++
46 lines
1.4 KiB
C++
#include <psemek/vecr/colorizer.hpp>
|
|
#include <psemek/math/swizzle.hpp>
|
|
|
|
namespace psemek::vecr
|
|
{
|
|
|
|
gfx::color_4f colorize(gfx::color_rgba const & color, math::point<float, 2> const &, sdf_sample const &)
|
|
{
|
|
return gfx::to_colorf(color);
|
|
}
|
|
|
|
gfx::color_4f colorize(gradient const & gradient, math::point<float, 2> const & p, sdf_sample const &)
|
|
{
|
|
return gfx::lerp(
|
|
gfx::to_colorf(gradient.color0),
|
|
gfx::to_colorf(gradient.color1),
|
|
math::clamp(sdf(gradient.shape, p).value + 0.5f, {0.f, 1.f})
|
|
);
|
|
}
|
|
|
|
gfx::color_4f colorize(lighting const & lighting, math::point<float, 2> const & p, sdf_sample const & sample)
|
|
{
|
|
auto const real_sample = lighting.shape ? sdf(lighting.shape, p) : sample;
|
|
|
|
auto normal = math::swizzle<0, 1, -1>(real_sample.gradient * lighting.slope);
|
|
normal[2] = 1.f;
|
|
normal = math::normalized(normal);
|
|
|
|
math::vector view{0.f, 0.f, 1.f};
|
|
|
|
auto reflected = 2.f * math::dot(normal, lighting.direction) * normal - lighting.direction;
|
|
|
|
auto NdotL = math::dot(normal, lighting.direction);
|
|
auto RdotV = math::dot(reflected, view);
|
|
|
|
auto lightness = 0.5f + 0.5f * NdotL;
|
|
|
|
auto specular = lighting.specular_intensity * std::pow(std::max(0.f, RdotV), lighting.specular_power);
|
|
|
|
auto result = gfx::lerp(gfx::to_colorf(lighting.color0), gfx::to_colorf(lighting.color1), lightness);
|
|
result = gfx::lerp(result, gfx::to_colorf(lighting.specular_color), specular);
|
|
|
|
return result;
|
|
}
|
|
|
|
}
|