|
25 | 25 | */ |
26 | 26 |
|
27 | 27 | #pragma once |
28 | | -#include "math/vector.hpp" |
| 28 | +#include "math/matrix.hpp" |
29 | 29 |
|
30 | 30 | namespace math::brdf |
31 | 31 | { |
@@ -119,40 +119,33 @@ static constexpr float2 hammersley(uint32 index, float invSampleCount) noexcept |
119 | 119 | */ |
120 | 120 | static f32x4 importanceSamplingNdfDggx(float2 u, float linearRoughness) noexcept |
121 | 121 | { |
| 122 | + // TODO: use faster alg +7.5%: https://arxiv.org/pdf/2306.05044 |
122 | 123 | auto a2 = linearRoughness * linearRoughness; |
123 | 124 | auto phi = u.x * float(M_PI * 2.0); |
124 | 125 | auto cosTheta2 = (1.0f - u.y) / std::fma(a2 - 1.0f, u.y, 1.0f); |
125 | 126 | auto cosTheta = std::sqrt(cosTheta2); |
126 | 127 | auto sinTheta = std::sqrt(1.0f - cosTheta2); |
127 | 128 | return f32x4(std::cos(phi) * sinTheta, std::sin(phi) * sinTheta, cosTheta); |
128 | 129 | } |
129 | | -// TODO: use faster alg +7.5%: https://arxiv.org/pdf/2306.05044 |
130 | 130 |
|
131 | 131 | /** |
132 | 132 | * @brief Computes diffuse irradiance from spherical harmonics (SH) using a 3rd-order. |
133 | 133 | * |
134 | 134 | * @details |
135 | | - * This function evaluates irradiance (light arriving at a surface) from an environment map, |
136 | | - * encoded using spherical harmonics (SH), for a given surface normal. |
| 135 | + * This function evaluates diffuse irradiance (light arriving at a surface) from an |
| 136 | + * environment map, encoded using spherical harmonics (SH), for a given surface normal. |
137 | 137 | * |
138 | 138 | * @param normal target sample normal vector |
139 | | - * @param[in] shBuffer IBL spherical harmonics buffer |
| 139 | + * @param[in] shDiffuse diffuse irradiance SH matrices |
140 | 140 | */ |
141 | | -static f32x4 diffuseIrradiance(f32x4 normal, const f32x4* shBuffer) noexcept |
| 141 | +static f32x4 diffuseIrradiance(f32x4 normal, const f32x4x4* shDiffuse) noexcept |
142 | 142 | { |
143 | 143 | auto qb = normal.swizzle<SwY, SwY, SwZ, SwZ>() * normal.swizzle<SwX, SwZ, SwZ, SwX>(); |
144 | | - qb.setZ(std::fma(qb.getZ(), 3.0f, -1.0f)); |
145 | | - auto ft = normal.getX() * normal.getX() - normal.getY() * normal.getY(); |
146 | | - |
147 | | - auto irradiance = shBuffer[0]; |
148 | | - irradiance = fma(shBuffer[1], f32x4(normal.getY()), irradiance); |
149 | | - irradiance = fma(shBuffer[2], f32x4(normal.getZ()), irradiance); |
150 | | - irradiance = fma(shBuffer[3], f32x4(normal.getX()), irradiance); |
151 | | - irradiance = fma(shBuffer[4], f32x4(qb.getX()), irradiance); |
152 | | - irradiance = fma(shBuffer[5], f32x4(qb.getY()), irradiance); |
153 | | - irradiance = fma(shBuffer[6], f32x4(qb.getZ()), irradiance); |
154 | | - irradiance = fma(shBuffer[7], f32x4(qb.getW()), irradiance); |
155 | | - irradiance = fma(shBuffer[8], f32x4(ft), irradiance); |
| 144 | + auto b1 = f32x4(1.0f, normal.getY(), normal.getZ()); |
| 145 | + auto b2 = f32x4(normal.getX(), qb.getX(), qb.getY()); |
| 146 | + auto b3 = f32x4(std::fma(qb.getZ(), 3.0f, -1.0f), qb.getW(), |
| 147 | + normal.getX() * normal.getX() - normal.getY() * normal.getY()); |
| 148 | + auto irradiance = shDiffuse[0] * b1 + shDiffuse[1] * b2 + shDiffuse[2] * b3; |
156 | 149 | return max(irradiance, f32x4::zero); |
157 | 150 | } |
158 | 151 |
|
|
0 commit comments