Audacity 3.2.0
VampEffect.cpp
Go to the documentation of this file.
1/**********************************************************************
2
3 Audacity: A Digital Audio Editor
4
5 VampEffect.cpp
6
7 Chris Cannam, with heavy borrowing from LadspaEffect.cpp
8
9 Vamp is an audio analysis and feature extraction plugin API.
10 http://www.vamp-plugins.org/
11
12**********************************************************************/
13#if defined(USE_VAMP)
14#include "VampEffect.h"
15#include "../AnalysisTracks.h"
16#include "../EffectEditor.h"
17
18#include <vamp-hostsdk/Plugin.h>
19#include <vamp-hostsdk/PluginChannelAdapter.h>
20#include <vamp-hostsdk/PluginInputDomainAdapter.h>
21
22#include <wx/wxprec.h>
23#include <wx/checkbox.h>
24#include <wx/choice.h>
25#include <wx/combobox.h>
26#include <wx/slider.h>
27#include <wx/statbox.h>
28#include <wx/stattext.h>
29#include <wx/textctrl.h>
30#include <wx/scrolwin.h>
31#include <wx/version.h>
32
33
34#include "ShuttleGui.h"
35#include "../../widgets/valnum.h"
36#include "AudacityMessageBox.h"
37
38#include "../../LabelTrack.h"
39#include "WaveTrack.h"
40
41enum
42{
43 ID_Program = 10000,
44 ID_Sliders = 11000,
45 ID_Choices = 12000,
46 ID_Texts = 13000,
47 ID_Toggles = 14000,
48};
49
51//
52// VampEffect
53//
55
56BEGIN_EVENT_TABLE(VampEffect, wxEvtHandler)
57 EVT_SLIDER(wxID_ANY, VampEffect::OnSlider)
58 EVT_TEXT(wxID_ANY, VampEffect::OnTextCtrl)
59 EVT_CHECKBOX(wxID_ANY, VampEffect::OnCheckBox)
60 EVT_CHOICE(wxID_ANY, VampEffect::OnChoice)
62
63VampEffect::VampEffect(std::unique_ptr<Vamp::Plugin> &&plugin,
64 const PluginPath & path,
65 int output,
66 bool hasParameters)
67: mPlugin(std::move(plugin)),
68 mPath(path),
69 mOutput(output),
70 mHasParameters(hasParameters),
71 mRate(0)
72{
73 mKey = mPath.BeforeFirst(wxT('/')).ToUTF8();
74 mName = mPath.AfterFirst(wxT('/'));
75}
76
78{
79}
80
81// ============================================================================
82// ComponentInterface implementation
83// ============================================================================
84
86{
87 return mPath;
88}
89
91{
92 return mName;
93}
94
96{
97 return { wxString::FromUTF8(mPlugin->getMaker().c_str()) };
98}
99
101{
102 return wxString::Format(wxT("%d"), mPlugin->getPluginVersion());
103}
104
106{
107 return Verbatim(
108 wxString::FromUTF8(mPlugin->getCopyright().c_str()) );
109}
110
111// ============================================================================
112// EffectDefinitionInterface implementation
113// ============================================================================
114
116{
117 return EffectTypeAnalyze;
118}
119
121{
122 return VAMPEFFECTS_FAMILY;
123}
124
126{
127 return mHasParameters;
128}
129
131{
132 return false;
133}
134
136{
137 return mPlugin->getMaxChannelCount();
138}
139
141 const EffectSettings &, CommandParameters & parms) const
142{
143 for (size_t p = 0, paramCount = mParameters.size(); p < paramCount; p++)
144 {
145 wxString key = wxString::FromUTF8(mParameters[p].identifier.c_str());
146 float value = mPlugin->getParameter(mParameters[p].identifier);
147 float lower = mParameters[p].minValue;
148 float upper = mParameters[p].maxValue;
149
150 if (mParameters[p].isQuantized &&
151 mParameters[p].quantizeStep == 1.0 &&
152 lower == 0.0 &&
153 upper == 1.0)
154 {
155 bool val = value > 0.5;
156
157 parms.Write(key, val);
158 }
159 else if (mParameters[p].isQuantized &&
160 mParameters[p].quantizeStep == 1.0 &&
161 !mParameters[p].valueNames.empty())
162 {
163 std::vector<EnumValueSymbol> choices;
164 int val = 0;
165
166 for (size_t i = 0, choiceCount = mParameters[p].valueNames.size(); i < choiceCount; i++)
167 {
168 wxString choice = wxString::FromUTF8(mParameters[p].valueNames[i].c_str());
169 if (size_t(value - mParameters[p].minValue + 0.5) == i)
170 {
171 val = i;
172 }
173 choices.push_back(choice);
174 }
175
176 parms.WriteEnum(key, val, choices.data(), choices.size());
177 }
178 else
179 {
180 parms.Write(key, value);
181 }
182 }
183
184 return true;
185}
186
188 const CommandParameters & parms, EffectSettings &settings) const
189{
190 // First pass verifies values
191 for (size_t p = 0, paramCount = mParameters.size(); p < paramCount; p++)
192 {
193 wxString key = wxString::FromUTF8(mParameters[p].identifier.c_str());
194 float lower = mParameters[p].minValue;
195 float upper = mParameters[p].maxValue;
196 bool good = false;
197
198 if (mParameters[p].isQuantized &&
199 mParameters[p].quantizeStep == 1.0 &&
200 lower == 0.0 &&
201 upper == 1.0)
202 {
203 bool val;
204
205 good = parms.Read(key, &val);
206 }
207 else if (mParameters[p].isQuantized &&
208 mParameters[p].quantizeStep == 1.0 &&
209 !mParameters[p].valueNames.empty())
210 {
211 std::vector<EnumValueSymbol> choices;
212 int val;
213
214 for (size_t i = 0, choiceCount = mParameters[p].valueNames.size(); i < choiceCount; i++)
215 {
216 wxString choice = wxString::FromUTF8(mParameters[p].valueNames[i].c_str());
217 choices.push_back(choice);
218 }
219
220 good = parms.ReadEnum(key, &val, choices.data(), choices.size()) && val != wxNOT_FOUND;
221 }
222 else
223 {
224 double val;
225
226 good = parms.Read(key, &val) && val >= lower && val <= upper;
227 }
228
229 if (!good)
230 {
231 return false;
232 }
233 }
234
235 // Second pass sets the variables
236 for (size_t p = 0, paramCount = mParameters.size(); p < paramCount; p++)
237 {
238 wxString key = wxString::FromUTF8(mParameters[p].identifier.c_str());
239 float lower = mParameters[p].minValue;
240 float upper = mParameters[p].maxValue;
241
242 if (mParameters[p].isQuantized &&
243 mParameters[p].quantizeStep == 1.0 &&
244 lower == 0.0 &&
245 upper == 1.0)
246 {
247 bool val;
248
249 parms.Read(key, &val);
250
251 mPlugin->setParameter(mParameters[p].identifier, val ? upper : lower);
252 }
253 else if (mParameters[p].isQuantized &&
254 mParameters[p].quantizeStep == 1.0 &&
255 !mParameters[p].valueNames.empty())
256 {
257 std::vector<EnumValueSymbol> choices;
258 int val = 0;
259
260 for (size_t i = 0, choiceCount = mParameters[p].valueNames.size(); i < choiceCount; i++)
261 {
262 wxString choice = wxString::FromUTF8(mParameters[p].valueNames[i].c_str());
263 choices.push_back(choice);
264 }
265
266 parms.ReadEnum(key, &val, choices.data(), choices.size());
267
268 mPlugin->setParameter(mParameters[p].identifier, (float) val);
269 }
270 else
271 {
272 double val;
273
274 parms.Read(key, &val);
275
276 if (mParameters[p].isQuantized)
277 {
278 float qs = mParameters[p].quantizeStep;
279
280 if (qs != 0.0)
281 {
282 val = (int)((val - lower) / qs + 0.5) * qs + lower;
283 }
284 }
285
286 mPlugin->setParameter(mParameters[p].identifier, val);
287 }
288 }
289
290 return true;
291}
292
294{
295 mRate = 0.0;
296
297 // PRL: this loop checked that channels of a track have the same rate,
298 // but there was no check that all tracks have one rate, and only the first
299 // is remembered in mRate. Is that correct?
300
301 for (auto leader : inputTracks()->Leaders<const WaveTrack>()) {
302 auto channelGroup = TrackList::Channels( leader );
303 auto rate = (*channelGroup.first++) -> GetRate();
304 for(auto channel : channelGroup) {
305 if (rate != channel->GetRate())
306 // PRL: Track rate might not match individual clip rates.
307 // So is this check not adequate?
308 {
309 // TODO: more-than-two-channels-message
311 XO(
312"Sorry, Vamp Plug-ins cannot be run on stereo tracks where the individual channels of the track do not match.") );
313 return false;
314 }
315 }
316 if (mRate == 0.0)
317 mRate = rate;
318 }
319
320 if (mRate <= 0.0)
321 {
323 }
324
325 // The plugin must be reloaded to allow changing parameters
326
327 Vamp::HostExt::PluginLoader *loader = Vamp::HostExt::PluginLoader::getInstance();
328 mPlugin.reset(loader->loadPlugin(mKey, mRate, Vamp::HostExt::PluginLoader::ADAPT_ALL));
329 if (!mPlugin)
330 {
332 XO("Sorry, failed to load Vamp Plug-in."));
333 return false;
334 }
335
336 return true;
337}
338
340{
341 if (!mPlugin)
342 {
343 return false;
344 }
345
346 int count = 0;
347
348 bool multiple = false;
349 unsigned prevTrackChannels = 0;
350
351 if (GetNumWaveGroups() > 1)
352 {
353 // if there is another track beyond this one and any linked one,
354 // then we're processing more than one track. That means we
355 // should use the originating track name in each NEW label
356 // track's name, to make clear which is which
357 multiple = true;
358 }
359
360 std::vector<std::shared_ptr<AddedAnalysisTrack>> addedTracks;
361
362 for (auto leader : inputTracks()->Leaders<const WaveTrack>())
363 {
364 auto channelGroup = TrackList::Channels(leader);
365 auto left = *channelGroup.first++;
366
367 unsigned channels = 1;
368
369 // channelGroup now contains all but the first channel
370 const WaveTrack *right =
371 channelGroup.size() ? *channelGroup.first++ : nullptr;
372 if (right)
373 channels = 2;
374
375 sampleCount start = 0;
376 sampleCount len = 0;
377 GetBounds(*left, right, &start, &len);
378
379 // TODO: more-than-two-channels
380
381 size_t step = mPlugin->getPreferredStepSize();
382 size_t block = mPlugin->getPreferredBlockSize();
383
384 bool initialiseRequired = true;
385
386 if (block == 0)
387 {
388 if (step != 0)
389 {
390 block = step;
391 }
392 else
393 {
394 block = 1024;
395 }
396 }
397
398 if (step == 0)
399 {
400 step = block;
401 }
402
403 if (prevTrackChannels > 0)
404 {
405 // Plugin has already been initialised, so if the number of
406 // channels remains the same, we only need to do a reset.
407 // Otherwise we need to re-construct the whole plugin,
408 // because a Vamp plugin can't be re-initialised.
409 if (prevTrackChannels == channels)
410 {
411 mPlugin->reset();
412 initialiseRequired = false;
413 }
414 else
415 {
417 Init();
418 }
419 }
420
421 if (initialiseRequired)
422 {
423 if (!mPlugin->initialise(channels, step, block))
424 {
426 XO("Sorry, Vamp Plug-in failed to initialize."));
427 return false;
428 }
429 }
430
431 const auto effectName = GetSymbol().Translation();
432 addedTracks.push_back(AddAnalysisTrack(*this,
433 multiple
434 ? wxString::Format( _("%s: %s"), left->GetName(), effectName )
435 : effectName
436 ));
437 LabelTrack *ltrack = addedTracks.back()->get();
438
439 FloatBuffers data{ channels, block };
440
441 auto originalLen = len;
442
443 auto pos = start;
444
445 while (len != 0)
446 {
447 const auto request = limitSampleBufferSize( block, len );
448
449 if (left)
450 {
451 left->GetFloats(data[0].get(), pos, request);
452 }
453
454 if (right)
455 {
456 right->GetFloats(data[1].get(), pos, request);
457 }
458
459 if (request < block)
460 {
461 for (unsigned int c = 0; c < channels; ++c)
462 {
463 for (decltype(block) i = request; i < block; ++i)
464 {
465 data[c][i] = 0.f;
466 }
467 }
468 }
469
470 // UNSAFE_SAMPLE_COUNT_TRUNCATION
471 // Truncation in case of very long tracks!
472 Vamp::RealTime timestamp = Vamp::RealTime::frame2RealTime(
473 long( pos.as_long_long() ),
474 (int)(mRate + 0.5)
475 );
476
477 Vamp::Plugin::FeatureSet features = mPlugin->process(
478 reinterpret_cast< float** >( data.get() ), timestamp);
479 AddFeatures(ltrack, features);
480
481 if (len > (int)step)
482 {
483 len -= step;
484 }
485 else
486 {
487 len = 0;
488 }
489
490 pos += step;
491
492 if (channels > 1)
493 {
494 if (TrackGroupProgress(count,
495 (pos - start).as_double() /
496 originalLen.as_double() ))
497 {
498 return false;
499 }
500 }
501 else
502 {
503 if (TrackProgress(count,
504 (pos - start).as_double() /
505 originalLen.as_double() ))
506 {
507 return false;
508 }
509 }
510 }
511
512 Vamp::Plugin::FeatureSet features = mPlugin->getRemainingFeatures();
513 AddFeatures(ltrack, features);
514
515 prevTrackChannels = channels;
516 }
517
518 // All completed without cancellation, so commit the addition of tracks now
519 for (auto &addedTrack : addedTracks)
520 addedTrack->Commit();
521
522 return true;
523}
524
525std::unique_ptr<EffectEditor> VampEffect::PopulateOrExchange(
527 const EffectOutputs *)
528{
529 mUIParent = S.GetParent();
530 Vamp::Plugin::ProgramList programs = mPlugin->getPrograms();
531
532 mParameters = mPlugin->getParameterDescriptors();
533
534 auto count = mParameters.size();
535
536 mToggles.reinit( count );
537 mSliders.reinit( count );
538 mFields.reinit( count );
539 mLabels.reinit( count );
540 mChoices.reinit( count );
541 mValues.reinit( count );
542
543 wxScrolledWindow *scroller = S.Style(wxVSCROLL | wxTAB_TRAVERSAL)
544 .StartScroller(2);
545 {
546 S.StartStatic(XO("Plugin Settings"));
547 {
548 S.StartMultiColumn(5, wxEXPAND);
549 {
550 S.SetStretchyCol(3);
551
552 if (!programs.empty())
553 {
554 S.AddPrompt(XXO("Program"));
555
556 S.Id(ID_Program);
557 mProgram = S.Name(XO("Program"))
558 .MinSize( { -1, -1 } )
559 .Position(wxEXPAND | wxALIGN_CENTER_VERTICAL | wxALL)
560 .AddChoice( {},
561 [&]{
562 TranslatableStrings choices;
563 for (const auto &program : programs)
564 choices.push_back(
565 Verbatim(wxString::FromUTF8(program.c_str())));
566 return choices;
567 }(),
568 Verbatim( wxString::FromUTF8(mPlugin->getCurrentProgram().c_str()) )
569 );
570
571 S.AddSpace(1, 1);
572 S.AddSpace(1, 1);
573 S.AddSpace(1, 1);
574 }
575
576 for (size_t p = 0; p < count; p++)
577 {
578 wxString tip = wxString::FromUTF8(mParameters[p].description.c_str());
579 wxString unit = wxString::FromUTF8(mParameters[p].unit.c_str());
580
581 float value = mPlugin->getParameter(mParameters[p].identifier);
582
583 mToggles[p] = NULL;
584 mChoices[p] = NULL;
585 mSliders[p] = NULL;
586 mFields[p] = NULL;
587 mValues[p] = 0.0;
588
589 wxString labelText = wxString::FromUTF8(mParameters[p].name.c_str());
590 if (!unit.empty())
591 {
592 labelText += wxT(" (") + unit + wxT(")");
593 }
594 /* i18n-hint: An item name introducing a value, which is not part of the string but
595 appears in a following text box window; translate with appropriate punctuation */
596 S.AddPrompt(XXO("%s:").Format( labelText ));
597
598 if (mParameters[p].isQuantized &&
599 mParameters[p].quantizeStep == 1.0 &&
600 mParameters[p].minValue == 0.0 &&
601 mParameters[p].maxValue == 1.0)
602 {
603 S.Id(ID_Toggles + p);
604 mToggles[p] = S.ToolTip( Verbatim( tip ) )
605 .Name( Verbatim( labelText ) )
606 .Position(wxALIGN_LEFT | wxALIGN_CENTER_VERTICAL | wxALL)
607 .AddCheckBox( {},
608 value > 0.5 );
609
610 S.AddSpace(1, 1);
611 S.AddSpace(1, 1);
612 S.AddSpace(1, 1);
613
614 }
615 else if (mParameters[p].isQuantized &&
616 mParameters[p].quantizeStep == 1.0 &&
617 !mParameters[p].valueNames.empty())
618 {
619 TranslatableStrings choices;
620 int selected = -1;
621
622 for (size_t i = 0, cnt = mParameters[p].valueNames.size(); i < cnt; i++)
623 {
624 wxString choice = wxString::FromUTF8(mParameters[p].valueNames[i].c_str());
625 if (size_t(value - mParameters[p].minValue + 0.5) == i)
626 {
627 selected = i;
628 }
629 choices.push_back( Verbatim( choice ) );
630 }
631
632 S.Id(ID_Choices + p);
633 mChoices[p] = S.ToolTip( Verbatim( tip ) )
634 .Name( Verbatim( labelText ) )
635 .Position(wxEXPAND | wxALIGN_CENTER_VERTICAL | wxALL)
636 .MinSize( { -1, -1 } )
637 .AddChoice( {}, choices, selected );
638
639 S.AddSpace(1, 1);
640 S.AddSpace(1, 1);
641 S.AddSpace(1, 1);
642 }
643 else
644 {
645 mValues[p] = value;
646
647 float range = mParameters[p].maxValue - mParameters[p].minValue;
648
649 S.Id(ID_Texts + p);
650 mFields[p] = S.ToolTip( Verbatim( tip ) )
651 .Name( Verbatim( labelText ) )
652 .Position(wxALIGN_CENTER_VERTICAL | wxALL)
653 .Validator<FloatingPointValidator<float>>(
654 6, &mValues[p],
655 (range < 10
656 ? NumValidatorStyle::THREE_TRAILING_ZEROES
657 : range < 100
658 ? NumValidatorStyle::TWO_TRAILING_ZEROES
659 : NumValidatorStyle::ONE_TRAILING_ZERO),
660 mParameters[p].minValue, mParameters[p].maxValue)
661 .AddTextBox( {}, wxT(""), 12);
662
663 wxString str = Internat::ToDisplayString(mParameters[p].minValue);
664 S.AddPrompt( Verbatim( str ) );
665
666 S.Id(ID_Sliders + p);
667 mSliders[p] = S.ToolTip( Verbatim( tip ) )
668 .Name( Verbatim( labelText ) )
669 .Style(wxSL_HORIZONTAL)
670 .MinSize( { 150, -1 } )
671 .AddSlider( {}, 0, 1000, 0);
672
674 S.AddUnits( Verbatim( str ) );
675 }
676 }
677 }
678 S.EndMultiColumn();
679 }
680 S.EndStatic();
681 }
682 S.EndScroller();
683
684 scroller->SetScrollRate(0, 20);
685
686 return nullptr;
687}
688
690{
691 if (!mUIParent->TransferDataToWindow())
692 {
693 return false;
694 }
695
697
698 return true;
699}
700
702{
703 if (!mUIParent->Validate() || !mUIParent->TransferDataFromWindow())
704 {
705 return false;
706 }
707
708 return true;
709}
710
711// VampEffect implementation
712
714 Vamp::Plugin::FeatureSet &features)
715{
716 for (Vamp::Plugin::FeatureList::iterator fli = features[mOutput].begin();
717 fli != features[mOutput].end(); ++fli)
718 {
719 Vamp::RealTime ftime0 = fli->timestamp;
720 double ltime0 = ftime0.sec + (double(ftime0.nsec) / 1000000000.0);
721
722 Vamp::RealTime ftime1 = ftime0;
723 if (fli->hasDuration) ftime1 = ftime0 + fli->duration;
724 double ltime1 = ftime1.sec + (double(ftime1.nsec) / 1000000000.0);
725
726 wxString label = LAT1CTOWX(fli->label.c_str());
727 if (label == wxString())
728 {
729 if (fli->values.empty())
730 {
731 label = wxString::Format(LAT1CTOWX("%.3f"), ltime0);
732 }
733 else
734 {
735 label = wxString::Format(LAT1CTOWX("%.3f"), *fli->values.begin());
736 }
737 }
738
739 ltrack->AddLabel(SelectedRegion(ltime0, ltime1), label);
740 }
741}
742
744{
745 for (size_t p = 0, cnt = mParameters.size(); p < cnt; p++)
746 {
747 float value = mPlugin->getParameter(mParameters[p].identifier);
748
749 if (mParameters[p].isQuantized &&
750 mParameters[p].quantizeStep == 1.0 &&
751 mParameters[p].minValue == 0.0 &&
752 mParameters[p].maxValue == 1.0)
753 {
754 mToggles[p]->SetValue(value > 0.5);
755 }
756 else if (mParameters[p].isQuantized &&
757 mParameters[p].quantizeStep == 1.0 &&
758 !mParameters[p].valueNames.empty())
759 {
760 mChoices[p]->SetSelection(size_t(value - mParameters[p].minValue + 0.5));
761 }
762 else
763 {
764 mValues[p] = value;
765 mFields[p]->GetValidator()->TransferToWindow();
766
767 float lower = mParameters[p].minValue;
768 float upper = mParameters[p].maxValue;
769 float range = upper - lower;
770
771 if (mParameters[p].isQuantized)
772 {
773 float qs = mParameters[p].quantizeStep;
774
775 if (qs != 0.0)
776 {
777 value = (int)((value - lower) / qs + 0.5) * qs + lower;
778 }
779 }
780
781 mSliders[p]->SetValue((int)(((value - lower) / range) * 1000.0 + 0.5));
782 }
783 }
784}
785
786void VampEffect::OnCheckBox(wxCommandEvent &event)
787{
788 int p = event.GetId() - ID_Toggles;
789
790 mPlugin->setParameter(mParameters[p].identifier, mToggles[p]->GetValue());
791}
792
793void VampEffect::OnChoice(wxCommandEvent & evt)
794{
795 int p = evt.GetId();
796
797 // special value for programs
798 if (p == ID_Program)
799 {
800 Vamp::Plugin::ProgramList programs = mPlugin->getPrograms();
801 mPlugin->selectProgram(programs[evt.GetInt()]);
803 return;
804 }
805
806 mPlugin->setParameter(mParameters[p - ID_Choices].identifier, evt.GetInt());
807}
808
809void VampEffect::OnSlider(wxCommandEvent & evt)
810{
811 int p = evt.GetId() - ID_Sliders;
812
813 float lower = mParameters[p].minValue;
814 float upper = mParameters[p].maxValue;
815 float range = upper - lower;
816 float val = (evt.GetInt() / 1000.0) * range;
817
818 if (mParameters[p].isQuantized)
819 {
820 float qs = mParameters[p].quantizeStep;
821
822 if (qs != 0.0)
823 {
824 val = (int)(val / qs + 0.5) * qs;
825 }
826 }
827
828 val += lower;
829
830 mValues[p] = val;
831 mFields[p]->GetValidator()->TransferToWindow();
832
833 mPlugin->setParameter(mParameters[p].identifier, val);
834}
835
836void VampEffect::OnTextCtrl(wxCommandEvent & evt)
837{
838 int p = evt.GetId() - ID_Texts;
839
840 mFields[p]->GetValidator()->TransferFromWindow();
841
842 float lower = mParameters[p].minValue;
843 float upper = mParameters[p].maxValue;
844 float range = upper - lower;
845 float val = mValues[p];
846
847 if (mParameters[p].isQuantized)
848 {
849 float qs = mParameters[p].quantizeStep;
850
851 if (qs != 0.0)
852 {
853 val = (int)((val - lower) / qs + 0.5) * qs + lower;
854 }
855 }
856
857 mPlugin->setParameter(mParameters[p].identifier, val);
858
859 mSliders[p]->SetValue((int)(((val - lower) / range) * 1000.0 + 0.5));
860}
861
862#endif
wxT("CloseDown"))
std::shared_ptr< AddedAnalysisTrack > AddAnalysisTrack(Effect &effect, const wxString &name)
END_EVENT_TABLE()
static const AudacityProject::AttachedObjects::RegisteredFactory key
#define str(a)
const TranslatableString name
Definition: Distortion.cpp:76
EffectType
@ EffectTypeAnalyze
XO("Cut/Copy/Paste")
XXO("&Cut/Copy/Paste Toolbar")
wxString PluginPath
type alias for identifying a Plugin supplied by a module, each module defining its own interpretation...
Definition: Identifier.h:214
#define LAT1CTOWX(X)
Definition: Internat.h:158
#define _(s)
Definition: Internat.h:73
size_t limitSampleBufferSize(size_t bufferSize, sampleCount limit)
Definition: SampleCount.cpp:22
TranslatableString label
Definition: TagsEditor.cpp:164
#define S(N)
Definition: ToChars.cpp:64
static Settings & settings()
Definition: TrackInfo.cpp:83
TranslatableString Verbatim(wxString str)
Require calls to the one-argument constructor to go through this distinct global function name.
std::vector< TranslatableString > TranslatableStrings
@ ID_Texts
Definition: VampEffect.cpp:46
@ ID_Choices
Definition: VampEffect.cpp:45
@ ID_Program
Definition: VampEffect.cpp:43
@ ID_Sliders
Definition: VampEffect.cpp:44
@ ID_Toggles
Definition: VampEffect.cpp:47
#define VAMPEFFECTS_FAMILY
Definition: VampEffect.h:36
void reinit(Integral count, bool initialize=false)
Definition: MemoryX.h:57
size_t size() const
How many attachment pointers are in the Site.
Definition: ClientData.h:251
CommandParameters, derived from wxFileConfig, is essentially doing the same things as the SettingsVis...
bool WriteEnum(const wxString &key, int value, const EnumValueSymbol choices[], size_t nChoices)
bool ReadEnum(const wxString &key, int *pi, const EnumValueSymbol choices[], size_t nChoices, const ObsoleteMap obsoletes[]=nullptr, size_t nObsoletes=0) const
ComponentInterfaceSymbol pairs a persistent string identifier used internally with an optional,...
const wxString Translation() const
const TrackList * inputTracks() const
Definition: EffectBase.h:94
double mProjectRate
Definition: EffectBase.h:115
bool TrackGroupProgress(int whichGroup, double frac, const TranslatableString &={}) const
Definition: Effect.cpp:360
bool TrackProgress(int whichTrack, double frac, const TranslatableString &={}) const
Definition: Effect.cpp:350
void GetBounds(const WaveTrack &track, const WaveTrack *pRight, sampleCount *start, sampleCount *len)
Definition: Effect.cpp:370
int GetNumWaveGroups() const
Definition: Effect.h:142
Performs effect computation.
Hold values to send to effect output meters.
static int DoMessageBox(const EffectPlugin &plugin, const TranslatableString &message, long style=DefaultMessageBoxStyle, const TranslatableString &titleStr={})
Abstract base class used in importing a file.
static wxString ToDisplayString(double numberToConvert, int digitsAfterDecimalPoint=-1)
Convert a number to a string, uses the user's locale's decimal separator.
Definition: Internat.cpp:161
A LabelTrack is a Track that holds labels (LabelStruct).
Definition: LabelTrack.h:87
int AddLabel(const SelectedRegion &region, const wxString &title)
Definition: LabelTrack.cpp:944
bool GetFloats(float *buffer, sampleCount start, size_t len, fillFormat fill=fillZero, bool mayThrow=true, sampleCount *pNumWithinClips=nullptr) const
Retrieve samples from a track in floating-point format, regardless of the storage format.
Definition: SampleTrack.h:83
Defines a selected portion of a project.
Derived from ShuttleGuiBase, an Audacity specific class for shuttling data to and from GUI.
Definition: ShuttleGui.h:625
static auto Channels(TrackType *pTrack) -> TrackIterRange< TrackType >
Definition: Track.h:1406
Holds a msgid for the translation catalog; may also bind format arguments.
ArrayOf< wxCheckBox * > mToggles
Definition: VampEffect.h:113
void OnCheckBox(wxCommandEvent &evt)
Definition: VampEffect.cpp:786
Floats mValues
Definition: VampEffect.h:108
bool IsDefault() const override
Whether the effect sorts "above the line" in the menus.
Definition: VampEffect.cpp:130
PluginPath GetPath() const override
Definition: VampEffect.cpp:85
bool TransferDataToWindow(const EffectSettings &settings) override
Definition: VampEffect.cpp:689
ComponentInterfaceSymbol GetSymbol() const override
Definition: VampEffect.cpp:90
bool TransferDataFromWindow(EffectSettings &settings) override
Definition: VampEffect.cpp:701
EffectFamilySymbol GetFamily() const override
Report identifier and user-visible name of the effect protocol.
Definition: VampEffect.cpp:120
bool IsInteractive() const override
Whether the effect needs a dialog for entry of settings.
Definition: VampEffect.cpp:125
void OnTextCtrl(wxCommandEvent &evt)
Definition: VampEffect.cpp:836
double mRate
Definition: VampEffect.h:101
ArrayOf< wxSlider * > mSliders
Definition: VampEffect.h:110
void UpdateFromPlugin()
Definition: VampEffect.cpp:743
PluginPath mPath
Definition: VampEffect.h:95
EffectType GetType() const override
Type determines how it behaves.
Definition: VampEffect.cpp:115
VendorSymbol GetVendor() const override
Definition: VampEffect.cpp:95
Vamp::Plugin::ParameterList mParameters
Definition: VampEffect.h:106
ArrayOf< wxChoice * > mChoices
Definition: VampEffect.h:114
ArrayOf< wxStaticText * > mLabels
Definition: VampEffect.h:112
int mOutput
Definition: VampEffect.h:96
wxChoice * mProgram
Definition: VampEffect.h:115
wxString mName
Definition: VampEffect.h:100
std::unique_ptr< Vamp::Plugin > mPlugin
Definition: VampEffect.h:94
TranslatableString GetDescription() const override
Definition: VampEffect.cpp:105
bool Process(EffectInstance &instance, EffectSettings &settings) override
Definition: VampEffect.cpp:339
ArrayOf< wxTextCtrl * > mFields
Definition: VampEffect.h:111
bool mHasParameters
Definition: VampEffect.h:97
virtual ~VampEffect()
Definition: VampEffect.cpp:77
std::unique_ptr< EffectEditor > PopulateOrExchange(ShuttleGui &S, EffectInstance &instance, EffectSettingsAccess &access, const EffectOutputs *pOutputs) override
Add controls to effect panel; always succeeds.
Definition: VampEffect.cpp:525
bool Init() override
Definition: VampEffect.cpp:293
wxWeakRef< wxWindow > mUIParent
Definition: VampEffect.h:92
bool SaveSettings(const EffectSettings &settings, CommandParameters &parms) const override
Store settings as keys and values.
Definition: VampEffect.cpp:140
void OnSlider(wxCommandEvent &evt)
Definition: VampEffect.cpp:809
bool LoadSettings(const CommandParameters &parms, EffectSettings &settings) const override
Restore settings from keys and values.
Definition: VampEffect.cpp:187
unsigned GetAudioInCount() const override
How many input buffers to allocate at once.
Definition: VampEffect.cpp:135
Vamp::HostExt::PluginLoader::PluginKey mKey
Definition: VampEffect.h:99
wxString GetVersion() const override
Definition: VampEffect.cpp:100
void OnChoice(wxCommandEvent &evt)
Definition: VampEffect.cpp:793
void AddFeatures(LabelTrack *track, Vamp::Plugin::FeatureSet &features)
Definition: VampEffect.cpp:713
A Track that contains audio waveform data.
Definition: WaveTrack.h:51
Positions or offsets within audio files need a wide type.
Definition: SampleCount.h:19
auto begin(const Ptr< Type, BaseDeleter > &p)
Enables range-for.
Definition: PackedArray.h:150
double GetRate(const Track &track)
Definition: TimeTrack.cpp:179
STL namespace.
Externalized state of a plug-in.