annotate audio/AudioGenerator.h @ 626:51ecc3e2d71c

Don't resample an incoming audio file to match the main model's rate, if the aim of importing is to replace the main model anyway
author Chris Cannam
date Tue, 09 Oct 2018 15:55:16 +0100
parents 7d3a6357ce64
children 161063152ddd
rev   line source
Chris@43 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
Chris@43 2
Chris@43 3 /*
Chris@43 4 Sonic Visualiser
Chris@43 5 An audio file viewer and annotation editor.
Chris@43 6 Centre for Digital Music, Queen Mary, University of London.
Chris@43 7 This file copyright 2006 Chris Cannam.
Chris@43 8
Chris@43 9 This program is free software; you can redistribute it and/or
Chris@43 10 modify it under the terms of the GNU General Public License as
Chris@43 11 published by the Free Software Foundation; either version 2 of the
Chris@43 12 License, or (at your option) any later version. See the file
Chris@43 13 COPYING included with this distribution for more information.
Chris@43 14 */
Chris@43 15
Chris@616 16 #ifndef SV_AUDIO_GENERATOR_H
Chris@616 17 #define SV_AUDIO_GENERATOR_H
Chris@43 18
Chris@43 19 class NoteModel;
matthiasm@281 20 class FlexiNoteModel;
Chris@43 21 class DenseTimeValueModel;
Chris@43 22 class SparseOneDimensionalModel;
Chris@108 23 class Playable;
Chris@307 24 class ClipMixer;
Chris@313 25 class ContinuousSynth;
Chris@43 26
Chris@43 27 #include <QObject>
Chris@43 28 #include <QMutex>
Chris@43 29
Chris@43 30 #include <set>
Chris@43 31 #include <map>
Chris@275 32 #include <vector>
Chris@43 33
Chris@436 34 #include "base/BaseTypes.h"
Chris@616 35 #include "data/model/Model.h"
Chris@436 36
Chris@43 37 class AudioGenerator : public QObject
Chris@43 38 {
Chris@43 39 Q_OBJECT
Chris@43 40
Chris@43 41 public:
Chris@43 42 AudioGenerator();
Chris@43 43 virtual ~AudioGenerator();
Chris@43 44
Chris@43 45 /**
Chris@43 46 * Add a data model to be played from and initialise any necessary
Chris@43 47 * audio generation code. Returns true if the model will be
Chris@108 48 * played. The model will be added regardless of the return
Chris@108 49 * value.
Chris@43 50 */
Chris@43 51 virtual bool addModel(Model *model);
Chris@43 52
Chris@43 53 /**
Chris@43 54 * Remove a model.
Chris@43 55 */
Chris@43 56 virtual void removeModel(Model *model);
Chris@43 57
Chris@43 58 /**
Chris@43 59 * Remove all models.
Chris@43 60 */
Chris@43 61 virtual void clearModels();
Chris@43 62
Chris@43 63 /**
Chris@305 64 * Reset playback, clearing buffers and the like.
Chris@43 65 */
Chris@43 66 virtual void reset();
Chris@43 67
Chris@43 68 /**
Chris@43 69 * Set the target channel count. The buffer parameter to mixModel
Chris@43 70 * must always point to at least this number of arrays.
Chris@43 71 */
Chris@366 72 virtual void setTargetChannelCount(int channelCount);
Chris@43 73
Chris@43 74 /**
Chris@43 75 * Return the internal processing block size. The frameCount
Chris@43 76 * argument to all mixModel calls must be a multiple of this
Chris@43 77 * value.
Chris@43 78 */
Chris@436 79 virtual sv_frame_t getBlockSize() const;
Chris@43 80
Chris@43 81 /**
Chris@43 82 * Mix a single model into an output buffer.
Chris@43 83 */
Chris@613 84 virtual sv_frame_t mixModel(Model *model,
Chris@613 85 sv_frame_t startFrame,
Chris@613 86 sv_frame_t frameCount,
Chris@613 87 float **buffer,
Chris@613 88 sv_frame_t fadeIn = 0,
Chris@613 89 sv_frame_t fadeOut = 0);
Chris@43 90
Chris@43 91 /**
Chris@43 92 * Specify that only the given set of models should be played.
Chris@43 93 */
Chris@43 94 virtual void setSoloModelSet(std::set<Model *>s);
Chris@43 95
Chris@43 96 /**
Chris@43 97 * Specify that all models should be played as normal (if not
Chris@43 98 * muted).
Chris@43 99 */
Chris@43 100 virtual void clearSoloModelSet();
Chris@43 101
Chris@43 102 protected slots:
Chris@309 103 void playClipIdChanged(const Playable *, QString);
Chris@43 104
Chris@43 105 protected:
Chris@436 106 sv_samplerate_t m_sourceSampleRate;
Chris@366 107 int m_targetChannelCount;
Chris@366 108 int m_waveType;
Chris@43 109
Chris@43 110 bool m_soloing;
Chris@43 111 std::set<Model *> m_soloModelSet;
Chris@43 112
Chris@43 113 struct NoteOff {
Chris@43 114
Chris@615 115 NoteOff(float _freq, sv_frame_t _offFrame, sv_frame_t _onFrame) :
Chris@615 116 frequency(_freq), offFrame(_offFrame), onFrame(_onFrame) { }
Chris@275 117
Chris@308 118 float frequency;
Chris@615 119 sv_frame_t offFrame;
Chris@615 120
Chris@615 121 // This is the frame at which the note whose note-off appears
Chris@615 122 // here began. It is used to determine when we should silence
Chris@615 123 // a note because the playhead has jumped back in time - if
Chris@615 124 // the current frame for rendering is earlier than this one,
Chris@615 125 // then we should end and discard the note
Chris@615 126 //
Chris@615 127 sv_frame_t onFrame;
Chris@43 128
Chris@595 129 struct Comparator {
Chris@595 130 bool operator()(const NoteOff &n1, const NoteOff &n2) const {
Chris@615 131 if (n1.offFrame != n2.offFrame) {
Chris@615 132 return n1.offFrame < n2.offFrame;
Chris@615 133 } else if (n1.onFrame != n2.onFrame) {
Chris@615 134 return n1.onFrame < n2.onFrame;
Chris@615 135 } else {
Chris@615 136 return n1.frequency < n2.frequency;
Chris@615 137 }
Chris@595 138 }
Chris@595 139 };
Chris@43 140 };
Chris@43 141
Chris@307 142
Chris@616 143 typedef std::map<const ModelId, ClipMixer *> ClipMixerMap;
Chris@43 144
Chris@178 145 typedef std::multiset<NoteOff, NoteOff::Comparator> NoteOffSet;
Chris@616 146 typedef std::map<const ModelId, NoteOffSet> NoteOffMap;
Chris@43 147
Chris@616 148 typedef std::map<const ModelId, ContinuousSynth *> ContinuousSynthMap;
Chris@313 149
Chris@43 150 QMutex m_mutex;
Chris@313 151
Chris@307 152 ClipMixerMap m_clipMixerMap;
Chris@43 153 NoteOffMap m_noteOffs;
Chris@43 154 static QString m_sampleDir;
Chris@43 155
Chris@313 156 ContinuousSynthMap m_continuousSynthMap;
Chris@313 157
Chris@313 158 bool usesClipMixer(const Model *);
Chris@349 159 bool wantsQuieterClips(const Model *);
Chris@313 160 bool usesContinuousSynth(const Model *);
Chris@313 161
Chris@307 162 ClipMixer *makeClipMixerFor(const Model *model);
Chris@313 163 ContinuousSynth *makeSynthFor(const Model *model);
Chris@307 164
Chris@108 165 static void initialiseSampleDir();
Chris@43 166
Chris@436 167 virtual sv_frame_t mixDenseTimeValueModel
Chris@436 168 (DenseTimeValueModel *model, sv_frame_t startFrame, sv_frame_t frameCount,
Chris@436 169 float **buffer, float gain, float pan, sv_frame_t fadeIn, sv_frame_t fadeOut);
Chris@43 170
Chris@436 171 virtual sv_frame_t mixClipModel
Chris@436 172 (Model *model, sv_frame_t startFrame, sv_frame_t frameCount,
Chris@313 173 float **buffer, float gain, float pan);
Chris@313 174
Chris@436 175 virtual sv_frame_t mixContinuousSynthModel
Chris@436 176 (Model *model, sv_frame_t startFrame, sv_frame_t frameCount,
Chris@313 177 float **buffer, float gain, float pan);
Chris@275 178
Chris@436 179 static const sv_frame_t m_processingBlockSize;
Chris@382 180
Chris@382 181 float **m_channelBuffer;
Chris@436 182 sv_frame_t m_channelBufSiz;
Chris@382 183 int m_channelBufCount;
Chris@43 184 };
Chris@43 185
Chris@43 186 #endif
Chris@43 187