comparison base/AudioLevel.cpp @ 240:8133ae938704

* Fix incorrect meter-scaling value for 0dB; some tidying
author Chris Cannam
date Wed, 28 Feb 2007 11:20:14 +0000
parents fd331fac5f38
children dc46851837d6
comparison
equal deleted inserted replaced
239:71f869dac40b 240:8133ae938704
23 #include <iostream> 23 #include <iostream>
24 #include <map> 24 #include <map>
25 #include <vector> 25 #include <vector>
26 #include <cassert> 26 #include <cassert>
27 27
28 const float AudioLevel::DB_FLOOR = -1000.0; 28 const float AudioLevel::DB_FLOOR = -1000.f;
29 29
30 struct FaderDescription 30 struct FaderDescription
31 { 31 {
32 FaderDescription(float _minDb, float _maxDb, float _zeroPoint) : 32 FaderDescription(float _minDb, float _maxDb, float _zeroPoint) :
33 minDb(_minDb), maxDb(_maxDb), zeroPoint(_zeroPoint) { } 33 minDb(_minDb), maxDb(_maxDb), zeroPoint(_zeroPoint) { }
36 float maxDb; 36 float maxDb;
37 float zeroPoint; // as fraction of total throw 37 float zeroPoint; // as fraction of total throw
38 }; 38 };
39 39
40 static const FaderDescription faderTypes[] = { 40 static const FaderDescription faderTypes[] = {
41 FaderDescription(-40.0, +6.0, 0.75), // short 41 FaderDescription(-40.f, +6.f, 0.75f), // short
42 FaderDescription(-70.0, +10.0, 0.80), // long 42 FaderDescription(-70.f, +10.f, 0.80f), // long
43 FaderDescription(-70.0, 0.0, 1.00), // IEC268 43 FaderDescription(-70.f, 0.f, 1.00f), // IEC268
44 FaderDescription(-70.0, +10.0, 0.80), // IEC268 long 44 FaderDescription(-70.f, +10.f, 0.80f), // IEC268 long
45 FaderDescription(-40.0, 0.0, 1.00), // preview 45 FaderDescription(-40.f, 0.f, 1.00f), // preview
46 }; 46 };
47 47
48 typedef std::vector<float> LevelList; 48 typedef std::vector<float> LevelList;
49 static std::map<int, LevelList> previewLevelCache; 49 static std::map<int, LevelList> previewLevelCache;
50 static const LevelList &getPreviewLevelCache(int levels); 50 static const LevelList &getPreviewLevelCache(int levels);
59 } 59 }
60 60
61 float 61 float
62 AudioLevel::dB_to_multiplier(float dB) 62 AudioLevel::dB_to_multiplier(float dB)
63 { 63 {
64 if (dB == DB_FLOOR) return 0.0; 64 if (dB == DB_FLOOR) return 0.f;
65 float m = powf(10.0, dB / 10.0); 65 float m = powf(10.f, dB / 10.f);
66 return m; 66 return m;
67 } 67 }
68 68
69 /* IEC 60-268-18 fader levels. Thanks to Steve Harris. */ 69 /* IEC 60-268-18 fader levels. Thanks to Steve Harris. */
70 70
132 132
133 float value = level - zeroLevel; 133 float value = level - zeroLevel;
134 float scale = float(maxLevel - zeroLevel) / 134 float scale = float(maxLevel - zeroLevel) /
135 sqrtf(faderTypes[type].maxDb); 135 sqrtf(faderTypes[type].maxDb);
136 value /= scale; 136 value /= scale;
137 float dB = powf(value, 2.0); 137 float dB = powf(value, 2.f);
138 return dB; 138 return dB;
139 139
140 } else { 140 } else {
141 141
142 float value = zeroLevel - level; 142 float value = zeroLevel - level;
143 float scale = zeroLevel / sqrtf(0.0 - faderTypes[type].minDb); 143 float scale = zeroLevel / sqrtf(0.f - faderTypes[type].minDb);
144 value /= scale; 144 value /= scale;
145 float dB = powf(value, 2.0); 145 float dB = powf(value, 2.f);
146 return 0.0 - dB; 146 return 0.f - dB;
147 } 147 }
148 } 148 }
149 } 149 }
150 150
151 151
161 // result not as a percentage, but as a scale between 0 and 161 // result not as a percentage, but as a scale between 0 and
162 // whatever the "percentage" for our (possibly >0dB) max dB is. 162 // whatever the "percentage" for our (possibly >0dB) max dB is.
163 163
164 float maxPercent = iec_dB_to_fader(faderTypes[type].maxDb); 164 float maxPercent = iec_dB_to_fader(faderTypes[type].maxDb);
165 float percent = iec_dB_to_fader(dB); 165 float percent = iec_dB_to_fader(dB);
166 int faderLevel = int((maxLevel * percent) / maxPercent + 0.01); 166 int faderLevel = int((maxLevel * percent) / maxPercent + 0.01f);
167 167
168 if (faderLevel < 0) faderLevel = 0; 168 if (faderLevel < 0) faderLevel = 0;
169 if (faderLevel > maxLevel) faderLevel = maxLevel; 169 if (faderLevel > maxLevel) faderLevel = maxLevel;
170 return faderLevel; 170 return faderLevel;
171 171
172 } else { 172 } else {
173 173
174 int zeroLevel = int(maxLevel * faderTypes[type].zeroPoint); 174 int zeroLevel = int(maxLevel * faderTypes[type].zeroPoint);
175 175
176 if (dB >= 0.0) { 176 if (dB >= 0.f) {
177 177
178 if (faderTypes[type].maxDb <= 0.f) {
179
180 return maxLevel;
181
182 } else {
183
184 float value = sqrtf(dB);
185 float scale = (maxLevel - zeroLevel) / sqrtf(faderTypes[type].maxDb);
186 value *= scale;
187 int level = int(value + 0.01f) + zeroLevel;
188 if (level > maxLevel) level = maxLevel;
189 return level;
190 }
191
192 } else {
193
194 dB = 0.f - dB;
178 float value = sqrtf(dB); 195 float value = sqrtf(dB);
179 float scale = (maxLevel - zeroLevel) / sqrtf(faderTypes[type].maxDb); 196 float scale = zeroLevel / sqrtf(0.f - faderTypes[type].minDb);
180 value *= scale; 197 value *= scale;
181 int level = int(value + 0.01) + zeroLevel; 198 int level = zeroLevel - int(value + 0.01f);
182 if (level > maxLevel) level = maxLevel;
183 return level;
184
185 } else {
186
187 dB = 0.0 - dB;
188 float value = sqrtf(dB);
189 float scale = zeroLevel / sqrtf(0.0 - faderTypes[type].minDb);
190 value *= scale;
191 int level = zeroLevel - int(value + 0.01);
192 if (level < 0) level = 0; 199 if (level < 0) level = 0;
193 return level; 200 return level;
194 } 201 }
195 } 202 }
196 } 203 }
197 204
198 205
199 float 206 float
200 AudioLevel::fader_to_multiplier(int level, int maxLevel, FaderType type) 207 AudioLevel::fader_to_multiplier(int level, int maxLevel, FaderType type)
201 { 208 {
202 if (level == 0) return 0.0; 209 if (level == 0) return 0.f;
203 return dB_to_multiplier(fader_to_dB(level, maxLevel, type)); 210 return dB_to_multiplier(fader_to_dB(level, maxLevel, type));
204 } 211 }
205 212
206 int 213 int
207 AudioLevel::multiplier_to_fader(float multiplier, int maxLevel, FaderType type) 214 AudioLevel::multiplier_to_fader(float multiplier, int maxLevel, FaderType type)
208 { 215 {
209 if (multiplier == 0.0) return 0; 216 if (multiplier == 0.f) return 0;
210 float dB = multiplier_to_dB(multiplier); 217 float dB = multiplier_to_dB(multiplier);
211 int fader = dB_to_fader(dB, maxLevel, type); 218 int fader = dB_to_fader(dB, maxLevel, type);
212 return fader; 219 return fader;
213 } 220 }
214 221
234 assert(levels > 0); 241 assert(levels > 0);
235 return multiplier_to_fader(m, levels, PreviewLevel); 242 return multiplier_to_fader(m, levels, PreviewLevel);
236 243
237 /* The original multiplier_to_preview which follows is not thread-safe. 244 /* The original multiplier_to_preview which follows is not thread-safe.
238 245
239 if (m < 0.0) return -multiplier_to_preview(-m, levels); 246 if (m < 0.f) return -multiplier_to_preview(-m, levels);
240 247
241 const LevelList &ll = getPreviewLevelCache(levels); 248 const LevelList &ll = getPreviewLevelCache(levels);
242 int result = -1; 249 int result = -1;
243 250
244 int lo = 0, hi = levels; 251 int lo = 0, hi = levels;