-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathLightSampler.cpp
More file actions
66 lines (56 loc) · 1.9 KB
/
LightSampler.cpp
File metadata and controls
66 lines (56 loc) · 1.9 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
#include "LightSampler.hpp"
void UniformLightSampler::Add(const std::shared_ptr<Light>& light){
lights.push_back(light);
}
std::shared_ptr<Light> UniformLightSampler::Sample(float u) const{
if(lights.empty())return nullptr;
int index = std::min<int>((u * lights.size()), lights.size() - 1);
return lights[index];
}
float UniformLightSampler::PMF(const std::shared_ptr<Light>& light) const{
if(lights.empty())return 0;
return 1.0f / lights.size();
}
void UniformLightSampler::PreProcess(const AABB& bbox){
std::vector<std::shared_ptr<Light>> validLights;
validLights.reserve(lights.size());
for(auto&& light : lights){
light->PreProcess(bbox);
if(light->Power() < 0.01f)continue;
validLights.emplace_back(light);
}
lights = validLights;
}
void PowerLightSampler::Add(const std::shared_ptr<Light>& light){
lights.push_back(light);
}
std::shared_ptr<Light> PowerLightSampler::Sample(float u) const{
if(lights.empty())return nullptr;
float currPower = 0;
float power = u * totalPower;
//do binary search
for(std::size_t i = 0;i < lightPowers.size();i++){
currPower += lightPowers[i];
if(currPower >= power){
return lights[i];
}
}
return lights.back();
}
float PowerLightSampler::PMF(const std::shared_ptr<Light>& light) const{
if(totalPower == 0)return 1.0f;
return light->Power() / totalPower;
}
void PowerLightSampler::PreProcess(const AABB& bbox){
lightPowers.clear();
lightPowers.reserve(lights.size());
std::vector<std::shared_ptr<Light>> validLights; //we cull lights with very small power
validLights.reserve(lights.size());
for(auto&& light : lights){
light->PreProcess(bbox);
if(light->Power() < 0.01f)continue;
validLights.emplace_back(light);
totalPower += lightPowers.emplace_back(light->Power());
}
lights = validLights;
}