Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
alexbevi
GitHub Repository: alexbevi/BizHawk
Path: blob/master/libsnes/bsnes/nall/dsp/resample/average.hpp
2 views
1
#ifdef NALL_DSP_INTERNAL_HPP
2
3
struct ResampleAverage : Resampler {
4
inline void setFrequency();
5
inline void clear();
6
inline void sample();
7
inline void sampleLinear();
8
ResampleAverage(DSP &dsp) : Resampler(dsp) {}
9
10
real fraction;
11
real step;
12
};
13
14
void ResampleAverage::setFrequency() {
15
fraction = 0.0;
16
step = dsp.settings.frequency / frequency;
17
}
18
19
void ResampleAverage::clear() {
20
fraction = 0.0;
21
}
22
23
void ResampleAverage::sample() {
24
//can only average if input frequency >= output frequency
25
if(step < 1.0) return sampleLinear();
26
27
fraction += 1.0;
28
29
real scalar = 1.0;
30
if(fraction > step) scalar = 1.0 - (fraction - step);
31
32
for(unsigned c = 0; c < dsp.settings.channels; c++) {
33
dsp.output.write(c) += dsp.buffer.read(c) * scalar;
34
}
35
36
if(fraction >= step) {
37
for(unsigned c = 0; c < dsp.settings.channels; c++) {
38
dsp.output.write(c) /= step;
39
}
40
dsp.output.wroffset++;
41
42
fraction -= step;
43
for(unsigned c = 0; c < dsp.settings.channels; c++) {
44
dsp.output.write(c) = dsp.buffer.read(c) * fraction;
45
}
46
}
47
48
dsp.buffer.rdoffset++;
49
}
50
51
void ResampleAverage::sampleLinear() {
52
while(fraction <= 1.0) {
53
real *channel = (real*)alloca(dsp.settings.channels * sizeof(real));
54
55
for(unsigned n = 0; n < dsp.settings.channels; n++) {
56
real a = dsp.buffer.read(n, -1);
57
real b = dsp.buffer.read(n, -0);
58
59
real mu = fraction;
60
61
channel[n] = a * (1.0 - mu) + b * mu;
62
}
63
64
dsp.write(channel);
65
fraction += step;
66
}
67
68
dsp.buffer.rdoffset++;
69
fraction -= 1.0;
70
}
71
72
#endif
73
74