]> git.tdb.fi Git - ext/openal.git/blob - core/bformatdec.h
Import OpenAL Soft 1.23.1 sources
[ext/openal.git] / core / bformatdec.h
1 #ifndef CORE_BFORMATDEC_H
2 #define CORE_BFORMATDEC_H
3
4 #include <array>
5 #include <cstddef>
6 #include <memory>
7
8 #include "almalloc.h"
9 #include "alspan.h"
10 #include "ambidefs.h"
11 #include "bufferline.h"
12 #include "devformat.h"
13 #include "filters/splitter.h"
14 #include "vector.h"
15
16 struct FrontStablizer;
17
18
19 using ChannelDec = std::array<float,MaxAmbiChannels>;
20
21 class BFormatDec {
22     static constexpr size_t sHFBand{0};
23     static constexpr size_t sLFBand{1};
24     static constexpr size_t sNumBands{2};
25
26     struct ChannelDecoder {
27         union MatrixU {
28             float Dual[sNumBands][MAX_OUTPUT_CHANNELS];
29             float Single[MAX_OUTPUT_CHANNELS];
30         } mGains{};
31
32         /* NOTE: BandSplitter filter is unused with single-band decoding. */
33         BandSplitter mXOver;
34     };
35
36     alignas(16) std::array<FloatBufferLine,2> mSamples;
37
38     const std::unique_ptr<FrontStablizer> mStablizer;
39     const bool mDualBand{false};
40
41     /* TODO: This should ideally be a FlexArray, since ChannelDecoder is rather
42      * small and only a few are needed (3, 4, 5, 7, typically). But that can
43      * only be used in a standard layout struct, and a std::unique_ptr member
44      * (mStablizer) causes GCC and Clang to warn it's not.
45      */
46     al::vector<ChannelDecoder> mChannelDec;
47
48 public:
49     BFormatDec(const size_t inchans, const al::span<const ChannelDec> coeffs,
50         const al::span<const ChannelDec> coeffslf, const float xover_f0norm,
51         std::unique_ptr<FrontStablizer> stablizer);
52
53     bool hasStablizer() const noexcept { return mStablizer != nullptr; }
54
55     /* Decodes the ambisonic input to the given output channels. */
56     void process(const al::span<FloatBufferLine> OutBuffer, const FloatBufferLine *InSamples,
57         const size_t SamplesToDo);
58
59     /* Decodes the ambisonic input to the given output channels with stablization. */
60     void processStablize(const al::span<FloatBufferLine> OutBuffer,
61         const FloatBufferLine *InSamples, const size_t lidx, const size_t ridx, const size_t cidx,
62         const size_t SamplesToDo);
63
64     static std::unique_ptr<BFormatDec> Create(const size_t inchans,
65         const al::span<const ChannelDec> coeffs, const al::span<const ChannelDec> coeffslf,
66         const float xover_f0norm, std::unique_ptr<FrontStablizer> stablizer);
67
68     DEF_NEWDEL(BFormatDec)
69 };
70
71 #endif /* CORE_BFORMATDEC_H */