Clean up some includes
[openal-soft.git] / core / voice.h
blob5dca571052993b1cf6960c556d7ed587fdd8e646
1 #ifndef CORE_VOICE_H
2 #define CORE_VOICE_H
4 #include <array>
5 #include <atomic>
6 #include <bitset>
7 #include <chrono>
8 #include <cstddef>
9 #include <memory>
10 #include <optional>
11 #include <string>
13 #include "almalloc.h"
14 #include "alspan.h"
15 #include "bufferline.h"
16 #include "buffer_storage.h"
17 #include "devformat.h"
18 #include "filters/biquad.h"
19 #include "filters/nfc.h"
20 #include "filters/splitter.h"
21 #include "mixer/defs.h"
22 #include "mixer/hrtfdefs.h"
23 #include "resampler_limits.h"
24 #include "uhjfilter.h"
25 #include "vector.h"
27 struct ContextBase;
28 struct DeviceBase;
29 struct EffectSlot;
30 enum class DistanceModel : unsigned char;
32 using uint = unsigned int;
35 inline constexpr size_t MaxSendCount{6};
38 enum class SpatializeMode : unsigned char {
39 Off,
40 On,
41 Auto
44 enum class DirectMode : unsigned char {
45 Off,
46 DropMismatch,
47 RemixMismatch
51 inline constexpr uint MaxPitch{10};
54 enum {
55 AF_None = 0,
56 AF_LowPass = 1,
57 AF_HighPass = 2,
58 AF_BandPass = AF_LowPass | AF_HighPass
62 struct DirectParams {
63 BiquadFilter LowPass;
64 BiquadFilter HighPass;
66 NfcFilter NFCtrlFilter;
68 struct {
69 HrtfFilter Old{};
70 HrtfFilter Target{};
71 alignas(16) std::array<float,HrtfHistoryLength> History{};
72 } Hrtf;
74 struct {
75 std::array<float,MaxOutputChannels> Current{};
76 std::array<float,MaxOutputChannels> Target{};
77 } Gains;
80 struct SendParams {
81 BiquadFilter LowPass;
82 BiquadFilter HighPass;
84 struct {
85 std::array<float,MaxAmbiChannels> Current{};
86 std::array<float,MaxAmbiChannels> Target{};
87 } Gains;
91 struct VoiceBufferItem {
92 std::atomic<VoiceBufferItem*> mNext{nullptr};
94 CallbackType mCallback{nullptr};
95 void *mUserData{nullptr};
97 uint mBlockAlign{0u};
98 uint mSampleLen{0u};
99 uint mLoopStart{0u};
100 uint mLoopEnd{0u};
102 std::byte *mSamples{nullptr};
106 struct VoiceProps {
107 float Pitch;
108 float Gain;
109 float OuterGain;
110 float MinGain;
111 float MaxGain;
112 float InnerAngle;
113 float OuterAngle;
114 float RefDistance;
115 float MaxDistance;
116 float RolloffFactor;
117 std::array<float,3> Position;
118 std::array<float,3> Velocity;
119 std::array<float,3> Direction;
120 std::array<float,3> OrientAt;
121 std::array<float,3> OrientUp;
122 bool HeadRelative;
123 DistanceModel mDistanceModel;
124 Resampler mResampler;
125 DirectMode DirectChannels;
126 SpatializeMode mSpatializeMode;
128 bool DryGainHFAuto;
129 bool WetGainAuto;
130 bool WetGainHFAuto;
131 float OuterGainHF;
133 float AirAbsorptionFactor;
134 float RoomRolloffFactor;
135 float DopplerFactor;
137 std::array<float,2> StereoPan;
139 float Radius;
140 float EnhWidth;
142 /** Direct filter and auxiliary send info. */
143 struct {
144 float Gain;
145 float GainHF;
146 float HFReference;
147 float GainLF;
148 float LFReference;
149 } Direct;
150 struct SendData {
151 EffectSlot *Slot;
152 float Gain;
153 float GainHF;
154 float HFReference;
155 float GainLF;
156 float LFReference;
158 std::array<SendData,MaxSendCount> Send;
161 struct VoicePropsItem : public VoiceProps {
162 std::atomic<VoicePropsItem*> next{nullptr};
165 enum : uint {
166 VoiceIsStatic,
167 VoiceIsCallback,
168 VoiceIsAmbisonic,
169 VoiceCallbackStopped,
170 VoiceIsFading,
171 VoiceHasHrtf,
172 VoiceHasNfc,
174 VoiceFlagCount
177 struct Voice {
178 enum State {
179 Stopped,
180 Playing,
181 Stopping,
182 Pending
185 std::atomic<VoicePropsItem*> mUpdate{nullptr};
187 VoiceProps mProps{};
189 std::atomic<uint> mSourceID{0u};
190 std::atomic<State> mPlayState{Stopped};
191 std::atomic<bool> mPendingChange{false};
194 * Source offset in samples, relative to the currently playing buffer, NOT
195 * the whole queue.
197 std::atomic<int> mPosition{};
198 /** Fractional (fixed-point) offset to the next sample. */
199 std::atomic<uint> mPositionFrac{};
201 /* Current buffer queue item being played. */
202 std::atomic<VoiceBufferItem*> mCurrentBuffer{};
204 /* Buffer queue item to loop to at end of queue (will be NULL for non-
205 * looping voices).
207 std::atomic<VoiceBufferItem*> mLoopBuffer{};
209 std::chrono::nanoseconds mStartTime{};
211 /* Properties for the attached buffer(s). */
212 FmtChannels mFmtChannels{};
213 FmtType mFmtType{};
214 uint mFrequency{};
215 uint mFrameStep{}; /**< In steps of the sample type size. */
216 uint mBytesPerBlock{}; /**< Or for PCM formats, BytesPerFrame. */
217 uint mSamplesPerBlock{}; /**< Always 1 for PCM formats. */
218 AmbiLayout mAmbiLayout{};
219 AmbiScaling mAmbiScaling{};
220 uint mAmbiOrder{};
222 std::unique_ptr<DecoderBase> mDecoder;
223 uint mDecoderPadding{};
225 /** Current target parameters used for mixing. */
226 uint mStep{0};
228 ResamplerFunc mResampler{};
230 InterpState mResampleState{};
232 std::bitset<VoiceFlagCount> mFlags{};
233 uint mNumCallbackBlocks{0};
234 uint mCallbackBlockBase{0};
236 struct TargetData {
237 int FilterType{};
238 al::span<FloatBufferLine> Buffer;
240 TargetData mDirect;
241 std::array<TargetData,MaxSendCount> mSend;
243 /* The first MaxResamplerPadding/2 elements are the sample history from the
244 * previous mix, with an additional MaxResamplerPadding/2 elements that are
245 * now current (which may be overwritten if the buffer data is still
246 * available).
248 using HistoryLine = std::array<float,MaxResamplerPadding>;
249 al::vector<HistoryLine,16> mPrevSamples{2};
251 struct ChannelData {
252 float mAmbiHFScale{}, mAmbiLFScale{};
253 BandSplitter mAmbiSplitter;
255 DirectParams mDryParams;
256 std::array<SendParams,MaxSendCount> mWetParams;
258 al::vector<ChannelData> mChans{2};
260 Voice() = default;
261 ~Voice() = default;
263 Voice(const Voice&) = delete;
264 Voice& operator=(const Voice&) = delete;
266 void mix(const State vstate, ContextBase *Context, const std::chrono::nanoseconds deviceTime,
267 const uint SamplesToDo);
269 void prepare(DeviceBase *device);
271 static void InitMixer(std::optional<std::string> resopt);
274 extern Resampler ResamplerDefault;
276 #endif /* CORE_VOICE_H */