iPlug2 - C++ Audio Plug-in Framework
Loading...
Searching...
No Matches
IPlugAPIBase.cpp
Go to the documentation of this file.
1/*
2 ==============================================================================
3
4 This file is part of the iPlug 2 library. Copyright (C) the iPlug 2 developers.
5
6 See LICENSE.txt for more info.
7
8 ==============================================================================
9*/
10
16#include <cmath>
17#include <cstdio>
18#include <ctime>
19#include <cassert>
20
21#include "IPlugAPIBase.h"
22
23using namespace iplug;
24
25IPlugAPIBase::IPlugAPIBase(Config c, EAPI plugAPI)
26 : IPluginBase(c.nParams, c.nPresets)
27{
28 mUniqueID = c.uniqueID;
29 mMfrID = c.mfrID;
30 mVersion = c.vendorVersion;
31 mPluginName.Set(c.pluginName, MAX_PLUGIN_NAME_LEN);
32 mProductName.Set(c.productName, MAX_PLUGIN_NAME_LEN);
33 mMfrName.Set(c.mfrName, MAX_PLUGIN_NAME_LEN);
34 mHasUI = c.plugHasUI;
35 mHostResize = c.plugHostResize;
36 SetEditorSize(c.plugWidth, c.plugHeight);
37 SetSizeConstraints(c.plugMinWidth, c.plugMaxWidth, c.plugMinHeight, c.plugMaxHeight);
38 mStateChunks = c.plugDoesChunks;
39 mAPI = plugAPI;
40 mBundleID.Set(c.bundleID);
41 mAppGroupID.Set(c.appGroupID);
42
43 Trace(TRACELOC, "%s:%s", c.pluginName, CurrentTime());
44
45 mParamDisplayStr.Set("", MAX_PARAM_DISPLAY_LEN);
46}
47
48IPlugAPIBase::~IPlugAPIBase()
49{
50 if(mTimer)
51 {
52 mTimer->Stop();
53 }
54
55 TRACE
56}
57
58void IPlugAPIBase::OnHostRequestingImportantParameters(int count, WDL_TypedBuf<int>& results)
59{
60 if(NParams() > count)
61 {
62 for (int i = 0; i < count; i++)
63 results.Add(i);
64 }
65}
66
68{
69 mTimer = std::unique_ptr<Timer>(Timer::Create(std::bind(&IPlugAPIBase::OnTimer, this, std::placeholders::_1), IDLE_TIMER_RATE));
70}
71
72bool IPlugAPIBase::CompareState(const uint8_t* pIncomingState, int startPos) const
73{
74 bool isEqual = true;
75
76 const double* data = (const double*) pIncomingState + startPos;
77
78 // dirty hack here because protools treats param values as 32 bit int and in IPlug they are 64bit float
79 // if we memcmp() the incoming state with the current they may have tiny differences due to the quantization
80 for (int i = 0; i < NParams(); i++)
81 {
82 float v = (float) GetParam(i)->Value();
83 float vi = (float) *(data++);
84
85 isEqual &= (std::fabs(v - vi) < 0.00001);
86 }
87
88 return isEqual;
89}
90
91bool IPlugAPIBase::EditorResizeFromUI(int viewWidth, int viewHeight, bool needsPlatformResize)
92{
93 if (needsPlatformResize)
94 return EditorResize(viewWidth, viewHeight);
95 else
96 return true;
97}
98
99#pragma mark -
100
101void IPlugAPIBase::SetHost(const char* host, int version)
102{
103 assert(mHost == kHostUninit);
104
105 mRawHostNameStr.Set(host);
106 mHost = LookUpHost(host);
107 mHostVersion = version;
108
109 WDL_String vStr;
110 GetVersionStr(version, vStr);
111 Trace(TRACELOC, "host_%sknown:%s:%s", (mHost == kHostUnknown ? "un" : ""), host, vStr.Get());
112
115}
116
117void IPlugAPIBase::SetParameterValue(int idx, double normalizedValue)
118{
119 Trace(TRACELOC, "%d:%f", idx, normalizedValue);
120 GetParam(idx)->SetNormalized(normalizedValue);
121 InformHostOfParamChange(idx, normalizedValue);
122 OnParamChange(idx, kUI);
123}
124
126{
127 for (int p = 0; p < NParams(); p++)
128 {
129 double normalizedValue = GetParam(p)->GetNormalized();
130 InformHostOfParamChange(p, normalizedValue);
131 }
132}
133
134void IPlugAPIBase::SendParameterValueFromAPI(int paramIdx, double value, bool normalized)
135{
136 if (normalized)
137 value = GetParam(paramIdx)->FromNormalized(value);
138
139 mParamChangeFromProcessor.PushFromArgs(paramIdx, value);
140}
141
142void IPlugAPIBase::OnTimer(Timer& t)
143{
144 if(HasUI())
145 {
146// VST3 ********************************************************************************
147#if defined VST3P_API || defined VST3_API
148 while (mMidiMsgsFromProcessor.ElementsAvailable())
149 {
150 IMidiMsg msg;
151 mMidiMsgsFromProcessor.Pop(msg);
152#ifdef VST3P_API // distributed
153 TransmitMidiMsgFromProcessor(msg);
154#else
155 SendMidiMsgFromDelegate(msg);
156#endif
157 }
158
159 while (mSysExDataFromProcessor.ElementsAvailable())
160 {
161 SysExData msg;
162 mSysExDataFromProcessor.Pop(msg);
163#ifdef VST3P_API // distributed
164 TransmitSysExDataFromProcessor(msg);
165#else
166 SendSysexMsgFromDelegate({msg.mOffset, msg.mData, msg.mSize});
167#endif
168 }
169// !VST3 ******************************************************************************
170#else
171 while(mParamChangeFromProcessor.ElementsAvailable())
172 {
173 ParamTuple p;
174 mParamChangeFromProcessor.Pop(p);
175 SendParameterValueFromDelegate(p.idx, p.value, false);
176 }
177
178 while (mMidiMsgsFromProcessor.ElementsAvailable())
179 {
180 IMidiMsg msg;
181 mMidiMsgsFromProcessor.Pop(msg);
182 SendMidiMsgFromDelegate(msg);
183 }
184
185 while (mSysExDataFromProcessor.ElementsAvailable())
186 {
187 SysExData msg;
188 mSysExDataFromProcessor.Pop(msg);
189 SendSysexMsgFromDelegate({msg.mOffset, msg.mData, msg.mSize});
190 }
191#endif
192 }
193
194 OnIdle();
195}
196
197void IPlugAPIBase::SendMidiMsgFromUI(const IMidiMsg& msg)
198{
199 DeferMidiMsg(msg); // queue the message so that it will be handled by the processor
200 EDITOR_DELEGATE_CLASS::SendMidiMsgFromUI(msg); // for remote editors
201}
202
203void IPlugAPIBase::SendSysexMsgFromUI(const ISysEx& msg)
204{
205 DeferSysexMsg(msg); // queue the message so that it will be handled by the processor
206 EDITOR_DELEGATE_CLASS::SendSysexMsgFromUI(msg); // for remote editors
207}
208
209void IPlugAPIBase::SendArbitraryMsgFromUI(int msgTag, int ctrlTag, int dataSize, const void* pData)
210{
211 OnMessage(msgTag, ctrlTag, dataSize, pData); // IPlugAPIBase implementation handles non distributed plug-ins - just call OnMessage() directly
212
213 EDITOR_DELEGATE_CLASS::SendArbitraryMsgFromUI(msgTag, ctrlTag, dataSize, pData);
214}
void CreateTimer()
Called by the API class to create the timer that pumps the parameter/message queues.
virtual void OnIdle()
Override this method to get an "idle"" call on the main thread.
Definition: IPlugAPIBase.h:111
virtual bool CompareState(const uint8_t *pIncomingState, int startPos) const
Override this method to implement a custom comparison of incoming state data with your plug-ins state...
void SetParameterValue(int paramIdx, double normalizedValue)
SetParameterValue is called from the UI in the middle of a parameter change gesture (possibly via del...
virtual void SendParameterValueFromAPI(int paramIdx, double value, bool normalized)
This is called from the plug-in API class in order to update UI controls linked to plug-in parameters...
void SetHost(const char *host, int version)
Called to set the name of the current host, if known (calls on to HostSpecificInit() and OnHostIdenti...
virtual void DirtyParametersFromUI() override
In a distributed VST3 or WAM plugin, if you modify the parameters on the UI side (e....
virtual void HostSpecificInit()
This method is implemented in some API classes, in order to do specific initialisation for particular...
Definition: IPlugAPIBase.h:155
virtual void OnHostIdentified()
Implement this to do something specific when IPlug becomes aware of the particular host that is hosti...
Definition: IPlugAPIBase.h:69
virtual void OnHostRequestingImportantParameters(int count, WDL_TypedBuf< int > &results)
Called by AUv3 plug-ins to get the "overview parameters".
bool Pop(T &item)
Definition: IPlugQueue.h:74
size_t ElementsAvailable() const
Definition: IPlugQueue.h:106
bool PushFromArgs(Args ...args)
Definition: IPlugQueue.h:91
Base class that contains plug-in info and state manipulation methods.
bool HasUI() const
static void GetVersionStr(int versionInteger, WDL_String &str)
Helper function to get the semantic version number as a string from an integer.
static EHost LookUpHost(const char *inHost)
Gets the host ID from a human-readable name.
Encapsulates a MIDI message and provides helper functions.
Definition: IPlugMidi.h:31
A struct for dealing with SysEx messages.
Definition: IPlugMidi.h:539
In certain cases we need to queue parameter changes for transferral between threads.
Definition: IPlugStructs.h:33
This structure is used when queueing Sysex messages.
Definition: IPlugStructs.h:45
Base class for timer.
Definition: IPlugTimer.h:40