1
0
Fork 0
mirror of https://github.com/juce-framework/JUCE.git synced 2026-01-09 23:34:20 +00:00

VST3: Update SDK to 3.7.14

This commit is contained in:
reuk 2025-09-17 20:11:30 +01:00
parent 94863f91d4
commit 597b5644a0
No known key found for this signature in database
48 changed files with 1365 additions and 881 deletions

View file

@ -140,13 +140,14 @@ uint32 PLUGIN_API FObject::release ()
}
#endif
if (FUnknownPrivate::atomicAdd (refCount, -1) == 0)
auto rc = FUnknownPrivate::atomicAdd (refCount, -1);
if (rc == 0)
{
refCount = -1000;
delete this;
return 0;
}
return refCount;
return rc;
}
//------------------------------------------------------------------------

View file

@ -21,5 +21,7 @@
#pragma -a-
#elif SMTG_OS_WINDOWS
#pragma pack(pop)
#elif SMTG_OS_LINUX
#pragma pack(pop)
#endif
//---------------------------------------------------------------------------------------------------

View file

@ -36,5 +36,11 @@
#else
#pragma pack(8)
#endif
#elif SMTG_OS_LINUX
#if SMTG_PLATFORM_64
#pragma pack(push, 16)
#else
#pragma pack(push, 8)
#endif
#endif
//----------------------------------------------------------------------------------------------

View file

@ -45,27 +45,27 @@
#define SMTG_OS_IOS 0
#define SMTG_OS_OSX 0
#if defined(_M_IX86)
#if defined (_M_IX86)
#define SMTG_CPU_X86 1
#else
#define SMTG_CPU_X86 0
#endif
#if defined(_M_AMD64)
#if defined (_M_AMD64)
#define SMTG_CPU_X86_64 1
#else
#define SMTG_CPU_X86_64 0
#endif
#if defined(_M_ARM)
#if defined (_M_ARM)
#define SMTG_CPU_ARM 1
#else
#define SMTG_CPU_ARM 0
#endif
#if defined(_M_ARM64)
#if defined (_M_ARM64)
#define SMTG_CPU_ARM_64 1
#else
#define SMTG_CPU_ARM_64 0
#endif
#if defined(_M_ARM64EC)
#if defined (_M_ARM64EC)
#define SMTG_CPU_ARM_64EC 1
#else
#define SMTG_CPU_ARM_64EC 0
@ -83,12 +83,14 @@
#define SMTG_HIDDEN_SYMBOL
#ifdef _MSC_VER
#pragma warning (disable : 4244) //! @brief warning C4244: Conversion from 'type1' to 'type2', possible loss of data.
#pragma warning (disable : 4250) //! @brief warning C4250: Inheritance via dominance is allowed
#if !defined (SMTG_DISABLE_DEFAULT_DIAGNOSTICS)
#pragma warning (disable : 4244) //! @brief warning C4244: Conversion from 'type1' to 'type2', possible loss of data.
#pragma warning (disable : 4250) //! @brief warning C4250: Inheritance via dominance is allowed
#pragma warning (3 : 4189) //! @brief warning C4189: local variable is initialized but not referenced
#pragma warning (3 : 4238) //! @brief warning C4238: nonstandard extension used : class rvalue used as lvalue
#endif
#pragma warning (3 : 4189) //! @brief warning C4189: local variable is initialized but not referenced
#pragma warning (3 : 4238) //! @brief warning C4238: nonstandard extension used: class rvalue used as lvalue
#endif
#endif // _MSC_VER
#if defined (_WIN64) || defined (_M_ARM64)
#define SMTG_PLATFORM_64 1
@ -107,12 +109,12 @@
#define SMTG_CPP17 (__cplusplus >= 201703L || ((_MSC_FULL_VER >= 190024210L) && (_MSVC_LANG >= 201703L)))
#define SMTG_CPP20 (__cplusplus >= 202002L)
#define SMTG_HAS_NOEXCEPT ((_MSC_FULL_VER >= 190023026L) || (SMTG_INTEL_CXX11_MODE && SMTG_INTEL_COMPILER >= 1300))
#if ((_MSC_FULL_VER >= 190024210L) || (SMTG_INTEL_CXX11_MODE && SMTG_INTEL_COMPILER >= 1500) || (defined(__MINGW32__) && SMTG_CPP11))
#if ((_MSC_FULL_VER >= 190024210L) || (SMTG_INTEL_CXX11_MODE && SMTG_INTEL_COMPILER >= 1500) || (defined (__MINGW32__) && SMTG_CPP11))
#define SMTG_HAS_CPP11_CONSTEXPR 1
#else
#define SMTG_HAS_CPP11_CONSTEXPR 0
#endif
#if (((_MSC_VER >= 1915L) && (_MSVC_LANG >= 201402L)) || (SMTG_INTEL_CXX11_MODE && SMTG_INTEL_COMPILER > 1700) || (defined(__MINGW32__) && SMTG_CPP14))
#if (((_MSC_VER >= 1915L) && (_MSVC_LANG >= 201402L)) || (SMTG_INTEL_CXX11_MODE && SMTG_INTEL_COMPILER > 1700) || (defined (__MINGW32__) && SMTG_CPP14))
#define SMTG_HAS_CPP14_CONSTEXPR 1
#else
#define SMTG_HAS_CPP14_CONSTEXPR 0
@ -123,7 +125,7 @@
//-----------------------------------------------------------------------------
// LINUX
//-----------------------------------------------------------------------------
#elif __gnu_linux__ || __linux__
#elif (defined (__gnu_linux__) && __gnu_linux__) || (defined (__linux__) && __linux__)
#define SMTG_OS_LINUX 1
#define SMTG_OS_MACOS 0
#define SMTG_OS_WINDOWS 0
@ -133,12 +135,12 @@
#define SMTG_CPU_X86 __i386__
#define SMTG_CPU_X86_64 __x86_64__
#if defined(__arm__)
#if defined (__arm__)
#define SMTG_CPU_ARM __arm__
#else
#define SMTG_CPU_ARM 0
#endif
#if defined(__aarch64__)
#if defined (__aarch64__)
#define SMTG_CPU_ARM_64 __aarch64__
#else
#define SMTG_CPU_ARM_64 0
@ -173,7 +175,7 @@
#define SMTG_CPP14 (__cplusplus >= 201402L)
#define SMTG_CPP17 (__cplusplus >= 201703L)
#define SMTG_CPP20 (__cplusplus >= 202002L)
#if defined(__GNUG__) && __GNUG__ < 8
#if defined (__GNUG__) && __GNUG__ < 8
#define SMTG_CPP11_STDLIBSUPPORT 0
#else
#define SMTG_CPP11_STDLIBSUPPORT 1
@ -226,7 +228,7 @@
#define SMTG_EXPORT_SYMBOL __attribute__ ((visibility ("default")))
#define SMTG_HIDDEN_SYMBOL __attribute__ ((visibility ("hidden")))
#if !defined(__PLIST__) && !defined(SMTG_DISABLE_DEFAULT_DIAGNOSTICS)
#if !defined (__PLIST__) && !defined (SMTG_DISABLE_DEFAULT_DIAGNOSTICS)
#ifdef __clang__
#pragma GCC diagnostic ignored "-Wswitch-enum"
#pragma GCC diagnostic ignored "-Wparentheses"

View file

@ -153,7 +153,7 @@ namespace Steinberg
// always inline macros (only when RELEASE is 1)
//----------------------------------------------------------------------------
#if RELEASE
#if defined(RELEASE) && RELEASE
#if SMTG_OS_MACOS || SMTG_OS_LINUX || defined(__MINGW32__)
#define SMTG_ALWAYS_INLINE __inline__ __attribute__((__always_inline__))
#define SMTG_NEVER_INLINE __attribute__((noinline))

View file

@ -22,9 +22,8 @@
#if SMTG_OS_WINDOWS
#include <objbase.h>
#endif
#if SMTG_OS_MACOS
#elif SMTG_OS_MACOS
#include <CoreFoundation/CoreFoundation.h>
#if !defined (SMTG_USE_STDATOMIC_H)
@ -115,7 +114,6 @@ int32 PLUGIN_API atomicAdd (int32& var, int32 d)
//------------------------------------------------------------------------
// FUID implementation
//------------------------------------------------------------------------
FUID::FUID ()
{
memset (data, 0, sizeof (TUID));
@ -140,6 +138,7 @@ FUID::FUID (FUID&& other)
memcpy (data, other.data, sizeof (TUID));
}
//------------------------------------------------------------------------
FUID& FUID::operator= (FUID&& other)
{
memcpy (data, other.data, sizeof (TUID));
@ -151,10 +150,6 @@ FUID& FUID::operator= (FUID&& other)
bool FUID::generate ()
{
#if SMTG_OS_WINDOWS
#if defined(_M_ARM64) || defined(_M_ARM)
//#warning implement me!
return false;
#else
GUID guid;
HRESULT hr = CoCreateGuid (&guid);
switch (hr)
@ -164,7 +159,6 @@ bool FUID::generate ()
case (HRESULT)RPC_S_UUID_LOCAL_ONLY:
default: return false;
}
#endif
#elif SMTG_OS_MACOS
CFUUIDRef uuid = CFUUIDCreate (kCFAllocatorDefault);

View file

@ -119,7 +119,8 @@ public: \
//------------------------------------------------------------------------
#define FUNKNOWN_CTOR { __funknownRefCount = 1; }
#if SMTG_FUNKNOWN_DTOR_ASSERT
#if defined(SMTG_FUNKNOWN_DTOR_ASSERT) && SMTG_FUNKNOWN_DTOR_ASSERT
#include <cassert>
#define FUNKNOWN_DTOR { assert (__funknownRefCount == 0); }
#else

View file

@ -276,14 +276,15 @@ struct RefCounted
uint32 PLUGIN_API release ()
{
if (--refCount == 0)
auto rc = --refCount;
if (rc == 0)
{
destroyInstance ();
refCount = -1000;
delete this;
return 0;
return uint32 ();
}
return refCount;
return rc;
}
//------------------------------------------------------------------------

View file

@ -48,8 +48,10 @@ public:
/** The class ID must be a 16 bytes unique id that is used to create the object.
This ID is also used to identify the preset list when used with presets. */
virtual tresult PLUGIN_API getClassID (char8* uid) = 0;
/** Store all members/data in the passed IAttributes. */
virtual tresult PLUGIN_API saveAttributes (IAttributes* ) = 0;
/** Restore all members/data from the passed IAttributes. */
virtual tresult PLUGIN_API loadAttributes (IAttributes* ) = 0;
//------------------------------------------------------------------------
@ -81,53 +83,62 @@ class IAttributes: public FUnknown
public:
//------------------------------------------------------------------------
/*! \name Methods to write attributes
******************************************************************************************************** */
********************************************************************************************************
*/
//@{
/** Store any data in the archive. It is even possible to store sub-attributes by creating
a new IAttributes instance via the IHostClasses interface and pass it to the parent in the
FVariant. In this case the archive must take the ownership of the newly created object, which
is true for all objects that have been created only for storing. You tell the archive to take
ownership by adding the FVariant::kOwner flag to the FVariant::type member (data.type |= FVariant::kOwner).
When using the PAttributes functions, this is done through a function parameter.*/
virtual tresult PLUGIN_API set (IAttrID attrID, const FVariant& data) = 0;
* a new IAttributes instance via the IHostClasses interface and pass it to the parent in the
* FVariant. In this case the archive must take the ownership of the newly created object,
* which is true for all objects that have been created only for storing. You tell the archive
* to take ownership by adding the FVariant::kOwner flag to the FVariant::type member (data.type
* |= FVariant::kOwner). When using the PAttributes functions, this is done through a function
* parameter.*/
virtual tresult PLUGIN_API set (IAttrID attrID /*in*/, const FVariant& data /*in*/) = 0;
/** Store a list of data in the archive. Please note that the type of data is not mixable! So
you can only store a list of integers or a list of doubles/strings/etc. You can also store a list
of subattributes or other objects that implement the IPersistent interface.*/
virtual tresult PLUGIN_API queue (IAttrID listID, const FVariant& data) = 0;
* you can only store a list of integers or a list of doubles/strings/etc. You can also store a
* list of subattributes or other objects that implement the IPersistent interface.*/
virtual tresult PLUGIN_API queue (IAttrID listID /*in*/, const FVariant& data /*in*/) = 0;
/** Store binary data in the archive. Parameter 'copyBytes' specifies if the passed data should be copied.
The archive cannot take the ownership of binary data. Either it just references a buffer in order
to write it to a file (copyBytes = false) or it copies the data to its own buffers (copyBytes = true).
When binary data should be stored in the default pool for example, you must always copy it!*/
virtual tresult PLUGIN_API setBinaryData (IAttrID attrID, void* data, uint32 bytes, bool copyBytes) = 0;
/** Store binary data in the archive. Parameter 'copyBytes' specifies if the passed data should
* be copied. The archive cannot take the ownership of binary data. Either it just references a
* buffer in order to write it to a file (copyBytes = false) or it copies the data to its own
* buffers (copyBytes = true). When binary data should be stored in the default pool for
* example, you must always copy it!*/
virtual tresult PLUGIN_API setBinaryData (IAttrID attrID /*in*/, void* data /*in*/,
uint32 bytes /*in*/, bool copyBytes /*in*/) = 0;
//@}
/*! \name Methods to read attributes
******************************************************************************************************** */
/*! \name Methods to read attributes
********************************************************************************************************
*/
//@{
/** Get data previously stored to the archive. */
virtual tresult PLUGIN_API get (IAttrID attrID, FVariant& data) = 0;
virtual tresult PLUGIN_API get (IAttrID attrID /*in*/, FVariant& data /*out*/) = 0;
/** Get list of data previously stored to the archive. As long as there are queue members the method
will return kResultTrue. When the queue is empty, the methods returns kResultFalse. All lists except from
object lists can be reset which means that the items can be read once again. \see IAttributes::resetQueue */
virtual tresult PLUGIN_API unqueue (IAttrID listID, FVariant& data) = 0;
/** Get list of data previously stored to the archive. As long as there are queue members the
* method will return kResultTrue. When the queue is empty, the methods returns kResultFalse.
* All lists except from object lists can be reset which means that the items can be read once
* again. \see IAttributes::resetQueue */
virtual tresult PLUGIN_API unqueue (IAttrID listID /*in*/, FVariant& data /*out*/) = 0;
/** Get the amount of items in a queue. */
virtual int32 PLUGIN_API getQueueItemCount (IAttrID) = 0;
/** Reset a queue. If you need to restart reading a queue, you have to reset it. You can reset a queue at any time.*/
virtual tresult PLUGIN_API resetQueue (IAttrID attrID) = 0;
virtual int32 PLUGIN_API getQueueItemCount (IAttrID attrId /*in*/) = 0;
/** Reset a queue. If you need to restart reading a queue, you have to reset it. You can reset a
* queue at any time.*/
virtual tresult PLUGIN_API resetQueue (IAttrID attrID /*in*/) = 0;
/** Reset all queues in the archive.*/
virtual tresult PLUGIN_API resetAllQueues () = 0;
/** Read binary data from the archive. The data is copied into the passed buffer. The size of that buffer
must fit the size of data stored in the archive which can be queried via IAttributes::getBinaryDataSize */
virtual tresult PLUGIN_API getBinaryData (IAttrID attrID, void* data, uint32 bytes) = 0;
/** Get the size in bytes of binary data in the archive. */
virtual uint32 PLUGIN_API getBinaryDataSize (IAttrID attrID) = 0;
/** Read binary data from the archive. The data is copied into the passed buffer. The size of
* that buffer must fit the size of data stored in the archive which can be queried via
* IAttributes::getBinaryDataSize */
virtual tresult PLUGIN_API getBinaryData (IAttrID attrID /*in*/, void* data /*inout*/,
uint32 bytes /*in*/) = 0;
/** Get the size in bytes of binary data in the archive. */
virtual uint32 PLUGIN_API getBinaryDataSize (IAttrID attrID /*in*/) = 0;
//@}
//------------------------------------------------------------------------
@ -148,8 +159,9 @@ class IAttributes2 : public IAttributes
public:
/** Returns the number of existing attributes. */
virtual int32 PLUGIN_API countAttributes () const = 0;
/** Returns the attribute's ID for the given index. */
virtual IAttrID PLUGIN_API getAttributeID (int32 index) const = 0;
virtual IAttrID PLUGIN_API getAttributeID (int32 index /*in*/) const = 0;
//------------------------------------------------------------------------
static const FUID iid;
};

View file

@ -42,7 +42,7 @@ public:
@note Extensive memory allocations etc. should be performed in this method rather than in
the class' constructor! If the method does NOT return kResultOk, the object is released
immediately. In this case terminate is not called! */
virtual tresult PLUGIN_API initialize (FUnknown* context) = 0;
virtual tresult PLUGIN_API initialize (FUnknown* context /*in*/) = 0;
/** This function is called before the plug-in is unloaded and can be used for
cleanups. You have to release all references to any host application interfaces. */
@ -194,7 +194,7 @@ class IPluginFactory : public FUnknown
public:
//------------------------------------------------------------------------
/** Fill a PFactoryInfo structure with information about the plug-in vendor. */
virtual tresult PLUGIN_API getFactoryInfo (PFactoryInfo* info) = 0;
virtual tresult PLUGIN_API getFactoryInfo (PFactoryInfo* info /*inout*/) = 0;
/** Returns the number of exported classes by this factory. If you are using the CPluginFactory
* implementation provided by the SDK, it returns the number of classes you registered with
@ -202,10 +202,11 @@ public:
virtual int32 PLUGIN_API countClasses () = 0;
/** Fill a PClassInfo structure with information about the class at the specified index. */
virtual tresult PLUGIN_API getClassInfo (int32 index, PClassInfo* info) = 0;
virtual tresult PLUGIN_API getClassInfo (int32 index /*in*/, PClassInfo* info /*inout*/) = 0;
/** Create a new class instance. */
virtual tresult PLUGIN_API createInstance (FIDString cid, FIDString _iid, void** obj) = 0;
virtual tresult PLUGIN_API createInstance (FIDString cid /*in*/, FIDString _iid /*in*/,
void** obj /*out*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
@ -322,7 +323,7 @@ class IPluginFactory2 : public IPluginFactory
public:
//------------------------------------------------------------------------
/** Returns the class info (version 2) for a given index. */
virtual tresult PLUGIN_API getClassInfo2 (int32 index, PClassInfo2* info) = 0;
virtual tresult PLUGIN_API getClassInfo2 (int32 index /*in*/, PClassInfo2* info /*out*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
@ -448,10 +449,11 @@ class IPluginFactory3 : public IPluginFactory2
public:
//------------------------------------------------------------------------
/** Returns the unicode class info for a given index. */
virtual tresult PLUGIN_API getClassInfoUnicode (int32 index, PClassInfoW* info) = 0;
virtual tresult PLUGIN_API getClassInfoUnicode (int32 index /*in*/,
PClassInfoW* info /*out*/) = 0;
/** Receives information about host*/
virtual tresult PLUGIN_API setHostContext (FUnknown* context) = 0;
virtual tresult PLUGIN_API setHostContext (FUnknown* context /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -87,6 +87,12 @@ const FIDString kPlatformTypeX11EmbedWindowID = "X11EmbedWindowID"; ///< X11 Win
- [plug imp]
- [released: 3.0.0]
\par Coordinates
The coordinates utilized within the ViewRect are native to the view system of the parent type.
This implies that on macOS (kPlatformTypeNSView), the coordinates are expressed in logical
units (independent of the screen scale factor), whereas on Windows (kPlatformTypeHWND) and
Linux (kPlatformTypeX11EmbedWindowID), the coordinates are expressed in physical units (pixels).
\par Sizing of a view
Usually, the size of a plug-in view is fixed. But both the host and the plug-in can cause
a view to be resized:
@ -206,7 +212,6 @@ public:
DECLARE_CLASS_IID (IPlugFrame, 0x367FAF01, 0xAFA94693, 0x8D4DA2A0, 0xED0882A3)
#if SMTG_OS_LINUX
//------------------------------------------------------------------------
namespace Linux {
@ -280,8 +285,4 @@ DECLARE_CLASS_IID (IRunLoop, 0x18C35366, 0x97764F1A, 0x9C5B8385, 0x7A871389)
//------------------------------------------------------------------------
} // namespace Linux
#endif
//------------------------------------------------------------------------
} // namespace Steinberg

View file

@ -44,8 +44,8 @@ The host may call setContentScaleFactor in a different context, for example: sca
editor for better readability.
When a plug-in handles this (by returning kResultTrue), it needs to scale the width and height of
its view by the scale factor and inform the host via a IPlugFrame::resizeView(). The host will then
call IPlugView::onSize().
its view by the scale factor and inform the host via a IPlugFrame::resizeView (). The host will then
call IPlugView::onSize ().
Note that the host is allowed to call setContentScaleFactor() at any time the IPlugView is valid.
If this happens before the IPlugFrame object is set on your view, make sure that when the host calls
@ -60,7 +60,11 @@ public:
//------------------------------------------------------------------------
typedef float ScaleFactor;
virtual tresult PLUGIN_API setContentScaleFactor (ScaleFactor factor) = 0;
/** Set the Content Scale Factor
* @param factor the scale factor requested by the host
* @return kResultTrue when a plug-in handles this
* \note [UI-thread] */
virtual tresult PLUGIN_API setContentScaleFactor (ScaleFactor factor /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
};

View file

@ -41,32 +41,36 @@ class IAttributeList : public FUnknown
{
public:
//------------------------------------------------------------------------
/** \ingroup vst3typedef */
typedef const char* AttrID;
/** Sets integer value. */
virtual tresult PLUGIN_API setInt (AttrID id, int64 value) = 0;
virtual tresult PLUGIN_API setInt (AttrID id /*in*/, int64 value /*in*/) = 0;
/** Gets integer value. */
virtual tresult PLUGIN_API getInt (AttrID id, int64& value) = 0;
virtual tresult PLUGIN_API getInt (AttrID id /*in*/, int64& value /*out*/) = 0;
/** Sets float value. */
virtual tresult PLUGIN_API setFloat (AttrID id, double value) = 0;
virtual tresult PLUGIN_API setFloat (AttrID id /*in*/, double value /*in*/) = 0;
/** Gets float value. */
virtual tresult PLUGIN_API getFloat (AttrID id, double& value) = 0;
virtual tresult PLUGIN_API getFloat (AttrID id /*in*/, double& value /*out*/) = 0;
/** Sets string value (UTF16) (must be null-terminated!). */
virtual tresult PLUGIN_API setString (AttrID id, const TChar* string) = 0;
virtual tresult PLUGIN_API setString (AttrID id /*in*/, const TChar* string /*in*/) = 0;
/** Gets string value (UTF16). Note that Size is in Byte, not the string Length!
Do not forget to multiply the length by sizeof (TChar)! */
virtual tresult PLUGIN_API getString (AttrID id, TChar* string, uint32 sizeInBytes) = 0;
Do not forget to multiply the length by sizeof (TChar)! */
virtual tresult PLUGIN_API getString (AttrID id /*in*/, TChar* string /*out*/,
uint32 sizeInBytes /*in*/) = 0;
/** Sets binary data. */
virtual tresult PLUGIN_API setBinary (AttrID id, const void* data, uint32 sizeInBytes) = 0;
virtual tresult PLUGIN_API setBinary (AttrID id /*in*/, const void* data /*in*/,
uint32 sizeInBytes /*in*/) = 0;
/** Gets binary data. */
virtual tresult PLUGIN_API getBinary (AttrID id, const void*& data, uint32& sizeInBytes) = 0;
virtual tresult PLUGIN_API getBinary (AttrID id /*in*/, const void*& data /*out*/,
uint32& sizeInBytes) = 0;
//------------------------------------------------------------------------
static const FUID iid;
};
@ -81,9 +85,10 @@ DECLARE_CLASS_IID (IAttributeList, 0x1E5F0AEB, 0xCC7F4533, 0xA2544011, 0x38AD5EE
- [released: 3.6.0]
- [optional]
Interface to access preset meta information from stream, used, for example, in setState in order to inform the plug-in about
the current context in which the preset loading occurs (Project context or Preset load (see \ref StateType))
or used to get the full file path of the loaded preset (if available).
Interface to access preset meta information from stream, for example used in setState\getState
in order to inform the plug-in about the current context in which the preset loading\saving occurs
(Project context or Preset load\save (see \ref StateType)) or used to get the full file path of the
loaded preset (if available).
\code{.cpp}
//------------------------------------------------------------------------
@ -96,12 +101,12 @@ tresult PLUGIN_API MyPlugin::setState (IBStream* state)
FUnknownPtr<IStreamAttributes> stream (state);
if (stream)
{
IAttributeList* list = stream->getAttributes ();
if (list)
if (IAttributeList* list = stream->getAttributes ())
{
// get the current type (project/Default..) of this state
String128 string;
if (list->getString (PresetAttributes::kStateType, string, 128 * sizeof (TChar)) == kResultTrue)
if (list->getString (PresetAttributes::kStateType, string, 128 * sizeof (TChar)) ==
kResultTrue)
{
UString128 tmp (string);
char ascii[128];
@ -114,15 +119,16 @@ tresult PLUGIN_API MyPlugin::setState (IBStream* state)
// get the full file path of this state
TChar fullPath[1024];
if (list->getString (PresetAttributes::kFilePathStringType, fullPath, 1024 * sizeof (TChar)) == kResultTrue)
if (list->getString (PresetAttributes::kFilePathStringType, fullPath,
1024 * sizeof (TChar)) == kResultTrue)
{
// here we have the full path ...
}
}
}
//...read the state here.....
return kResultTrue;
//...read the state here.....
return kResultTrue;
}
\endcode
*/
@ -131,7 +137,7 @@ class IStreamAttributes : public FUnknown
public:
//------------------------------------------------------------------------
/** Gets filename (without file extension) of the stream. */
virtual tresult PLUGIN_API getFileName (String128 name) = 0;
virtual tresult PLUGIN_API getFileName (String128 name /*inout*/) = 0;
/** Gets meta information list. */
virtual IAttributeList* PLUGIN_API getAttributes () = 0;

View file

@ -43,9 +43,8 @@ struct ProcessContext;
namespace PlugType
{
/**
\defgroup plugType Plug-in Type used for subCategories */
/*@{*/
//------------------------------------------------------------------------
* \defgroup plugType Plug-in Type used for subCategories
* @{ */
SMTG_CONSTEXPR const CString kFx = "Fx"; ///< others type (not categorized)
SMTG_CONSTEXPR const CString kFxAnalyzer = "Fx|Analyzer"; ///< Scope, FFT-Display, Loudness Processing...
SMTG_CONSTEXPR const CString kFxBass = "Fx|Bass"; ///< Tools dedicated to Bass Guitar
@ -94,8 +93,7 @@ SMTG_CONSTEXPR const CString kMono = "Mono"; ///< used for Mono only plug-
SMTG_CONSTEXPR const CString kStereo = "Stereo"; ///< used for Stereo only plug-in [optional]
SMTG_CONSTEXPR const CString kSurround = "Surround"; ///< used for Surround only plug-in [optional]
//------------------------------------------------------------------------
/*@}*/
/**@}*/
}
//------------------------------------------------------------------------
@ -110,8 +108,8 @@ enum ComponentFlags
//------------------------------------------------------------------------
/** Symbolic sample size.
\see ProcessSetup, ProcessData
*/
* \see ProcessSetup, ProcessData
*/
enum SymbolicSampleSizes
{
kSample32, ///< 32-bit precision
@ -119,27 +117,33 @@ enum SymbolicSampleSizes
};
//------------------------------------------------------------------------
/** Processing mode informs the plug-in about the context and at which frequency the process call is called.
VST3 defines 3 modes:
- kRealtime: each process call is called at a realtime frequency (defined by [numSamples of ProcessData] / samplerate).
The plug-in should always try to process as fast as possible in order to let enough time slice to other plug-ins.
- kPrefetch: each process call could be called at a variable frequency (jitter, slower / faster than realtime),
the plug-in should process at the same quality level than realtime, plug-in must not slow down to realtime
(e.g. disk streaming)!
The host should avoid to process in kPrefetch mode such sampler based plug-in.
- kOffline: each process call could be faster than realtime or slower, higher quality than realtime could be used.
plug-ins using disk streaming should be sure that they have enough time in the process call for streaming,
if needed by slowing down to realtime or slower.
.
Note about Process Modes switching:
- Switching between kRealtime and kPrefetch process modes are done in realtime thread without need of calling
IAudioProcessor::setupProcessing, the plug-in should check in process call the member processMode of ProcessData
in order to know in which mode it is processed.
- Switching between kRealtime (or kPrefetch) and kOffline requires that the host calls IAudioProcessor::setupProcessing
in order to inform the plug-in about this mode change.
.
\see ProcessSetup, ProcessData
*/
/** Processing mode informs the plug-in about the context and at which frequency the process call is
* called.
* .
* VST3 defines 3 modes:
*
* - kRealtime: each process call is called at a realtime frequency (defined by [numSamples of
* ProcessData] / samplerate). The plug-in should always try to process as fast as possible in order
* to let enough time slice to other plug-ins.
*
* - kPrefetch: each process call could be called at a variable frequency (jitter, slower /
* faster than realtime), the plug-in should process at the same quality level than realtime,
* plug-in must not slow down to realtime (e.g. disk streaming)! The host should avoid to process in
* kPrefetch mode such sampler based plug-in.
*
* - kOffline: each process call could be faster than realtime or slower, higher quality than
* realtime could be used. plug-ins using disk streaming should be sure that they have enough time
* in the process call for streaming, if needed by slowing down to realtime or slower.
* .
* Note about Process Modes switching:
* - Switching between kRealtime and kPrefetch process modes are done in realtime thread without
* need of calling IAudioProcessor::setupProcessing, the plug-in should check in process call the
* member processMode of ProcessData in order to know in which mode it is processed.
* - Switching between kRealtime (or kPrefetch) and kOffline requires that the host calls
* IAudioProcessor::setupProcessing in order to inform the plug-in about this mode change.
* .
* \see ProcessSetup, ProcessData
*/
enum ProcessModes
{
kRealtime, ///< realtime processing
@ -151,22 +155,22 @@ enum ProcessModes
/** kNoTail
*
* to be returned by getTailSamples when no tail is wanted
\see IAudioProcessor::getTailSamples
*/
* \see IAudioProcessor::getTailSamples
*/
static const uint32 kNoTail = 0;
//------------------------------------------------------------------------
/** kInfiniteTail
*
* to be returned by getTailSamples when infinite tail is wanted
\see IAudioProcessor::getTailSamples
* \see IAudioProcessor::getTailSamples
*/
static const uint32 kInfiniteTail = kMaxInt32u;
//------------------------------------------------------------------------
/** Audio processing setup.
\see IAudioProcessor::setupProcessing
*/
* \see IAudioProcessor::setupProcessing
*/
struct ProcessSetup
{
//------------------------------------------------------------------------
@ -180,16 +184,18 @@ struct ProcessSetup
//------------------------------------------------------------------------
/** Processing buffers of an audio bus.
This structure contains the processing buffer for each channel of an audio bus.
- The number of channels (numChannels) must always match the current bus arrangement.
It could be set to value '0' when the host wants to flush the parameters (when the plug-in is not processed).
- The size of the channel buffer array must always match the number of channels. So the host
must always supply an array for the channel buffers, regardless if the
bus is active or not. However, if an audio bus is currently inactive, the actual sample
buffer addresses are safe to be null.
- The number of channels (numChannels) must always match the current bus arrangement. It could be
set to value '0' when the host wants to flush the parameters (when the plug-in is not processed).
- The size of the channel buffer array must always match the number of channels. So the host must
always supply an array for the channel buffers, regardless if the bus is active or not. However, if
an audio bus is currently inactive, the actual sample buffer addresses are safe to be null.
- The silence flag is set when every sample of the according buffer has the value '0'. It is
intended to be used as help for optimizations allowing a plug-in to reduce processing activities.
But even if this flag is set for a channel, the channel buffers must still point to valid memory!
This flag is optional. A host is free to support it or not.
intended to be used as help for optimizations allowing a plug-in to reduce processing activities.
But even if this flag is set for a channel, the channel buffers must still point to valid memory!
This flag is optional. A host is free to support it or not.
.
\see ProcessData
*/
@ -210,11 +216,11 @@ struct AudioBusBuffers
//------------------------------------------------------------------------
/** Any data needed in audio processing.
The host prepares AudioBusBuffers for each input/output bus,
regardless of the bus activation state. Bus buffer indices always match
with bus indices used in IComponent::getBusInfo of media type kAudio.
\see AudioBusBuffers, IParameterChanges, IEventList, ProcessContext, IProcessContextRequirements
*/
* The host prepares AudioBusBuffers for each input/output bus,
* regardless of the bus activation state. Bus buffer indices always match
* with bus indices used in IComponent::getBusInfo of media type kAudio.
* \see AudioBusBuffers, IParameterChanges, IEventList, ProcessContext, IProcessContextRequirements
*/
struct ProcessData
{
ProcessData ()
@ -265,71 +271,92 @@ class IAudioProcessor : public FUnknown
public:
//------------------------------------------------------------------------
/** Try to set (host => plug-in) a wanted arrangement for inputs and outputs.
The host should always deliver the same number of input and output busses than the plug-in
needs (see \ref IComponent::getBusCount). The plug-in has 3 possibilities to react on this
setBusArrangements call:\n
1. The plug-in accepts these arrangements, then it should modify, if needed, its busses to match
these new arrangements (later on asked by the host with IComponent::getBusInfo () or
IAudioProcessor::getBusArrangement ()) and then should return kResultTrue.\n
2. The plug-in does not accept or support these requested arrangements for all
inputs/outputs or just for some or only one bus, but the plug-in can try to adapt its current
arrangements according to the requested ones (requested arrangements for kMain busses should be
handled with more priority than the ones for kAux busses), then it should modify its busses arrangements
and should return kResultFalse.\n
3. Same than the point 2 above the plug-in does not support these requested arrangements
but the plug-in cannot find corresponding arrangements, the plug-in could keep its current arrangement
or fall back to a default arrangement by modifying its busses arrangements and should return kResultFalse.\n
\param inputs pointer to an array of /ref SpeakerArrangement
\param numIns number of /ref SpeakerArrangement in inputs array
\param outputs pointer to an array of /ref SpeakerArrangement
\param numOuts number of /ref SpeakerArrangement in outputs array
Returns kResultTrue when Arrangements is supported and is the current one, else returns kResultFalse. */
virtual tresult PLUGIN_API setBusArrangements (SpeakerArrangement* inputs, int32 numIns,
SpeakerArrangement* outputs, int32 numOuts) = 0;
* The host should always deliver the same number of input and output busses than the plug-in
* needs (see \ref IComponent::getBusCount). The plug-in has 3 possibilities to react on this
* setBusArrangements call:\n
*
* 1. The plug-in accepts these arrangements, then it should modify, if needed, its busses to
* match these new arrangements (later on asked by the host with IComponent::getBusInfo () or
* IAudioProcessor::getBusArrangement ()) and then should return kResultTrue.\n
*
* 2. The plug-in does not accept or support these requested arrangements for all
* inputs/outputs or just for some or only one bus, but the plug-in can try to adapt its
* current arrangements according to the requested ones (requested arrangements for kMain busses
* should be handled with more priority than the ones for kAux busses), then it should modify
* its busses arrangements and should return kResultFalse.\n
*
* 3. Same than the point 2 above the plug-in does not support these requested arrangements but
* the plug-in cannot find corresponding arrangements, the plug-in could keep its current
* arrangement or fall back to a default arrangement by modifying its busses arrangements and
* should return kResultFalse.\n
*
* \param inputs pointer to an array of \ref SpeakerArrangement
* \param numIns number of \ref SpeakerArrangement in inputs array
* \param outputs pointer to an array of \ref SpeakerArrangement
* \param numOuts number of \ref SpeakerArrangement in outputs array
* Returns kResultTrue when Arrangements is supported and is the current one, else returns
* kResultFalse.
*
* \note [UI-thread & (Initialized | Connected | Setup Done)] */
virtual tresult PLUGIN_API setBusArrangements (SpeakerArrangement* inputs /*in*/,
int32 numIns /*in*/,
SpeakerArrangement* outputs /*in*/,
int32 numOuts /*in*/) = 0;
/** Gets the bus arrangement for a given direction (input/output) and index.
Note: IComponent::getBusInfo () and IAudioProcessor::getBusArrangement () should be always return the same
information about the busses arrangements. */
virtual tresult PLUGIN_API getBusArrangement (BusDirection dir, int32 index, SpeakerArrangement& arr) = 0;
* Note: IComponent::getBusInfo () and IAudioProcessor::getBusArrangement () should be always
* return the same information about the busses arrangements.
* \note [UI-thread & (Initialized | Connected | Setup Done | Activated | Processing] */
virtual tresult PLUGIN_API getBusArrangement (BusDirection dir /*in*/, int32 index /*in*/,
SpeakerArrangement& arr /*inout*/) = 0;
/** Asks if a given sample size is supported see \ref SymbolicSampleSizes. */
virtual tresult PLUGIN_API canProcessSampleSize (int32 symbolicSampleSize) = 0;
/** Asks if a given sample size is supported see \ref SymbolicSampleSizes.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API canProcessSampleSize (int32 symbolicSampleSize /*in*/) = 0;
/** Gets the current Latency in samples.
The returned value defines the group delay or the latency of the plug-in. For example, if the plug-in internally needs
to look in advance (like compressors) 512 samples then this plug-in should report 512 as latency.
If during the use of the plug-in this latency change, the plug-in has to inform the host by
using IComponentHandler::restartComponent (kLatencyChanged), this could lead to audio playback interruption
because the host has to recompute its internal mixer delay compensation.
Note that for player live recording this latency should be zero or small. */
* The returned value defines the group delay or the latency of the plug-in. For example, if
* the plug-in internally needs to look in advance (like compressors) 512 samples then this
* plug-in should report 512 as latency. If during the use of the plug-in this latency change,
* the plug-in has to inform the host by using IComponentHandler::restartComponent
* (kLatencyChanged), this could lead to audio playback interruption because the host has to
* recompute its internal mixer delay compensation. Note that for player live recording this
* latency should be zero or small.
* \note [UI-thread & Setup Done] */
virtual uint32 PLUGIN_API getLatencySamples () = 0;
/** Called in disable state (setActive not called with true) before setProcessing is called and processing will begin. */
virtual tresult PLUGIN_API setupProcessing (ProcessSetup& setup) = 0;
/** Called in disable state (setActive not called with true) before setProcessing is called and
* processing will begin.
* \note [UI-thread & (Initialized | Connected)]] */
virtual tresult PLUGIN_API setupProcessing (ProcessSetup& setup /*in*/) = 0;
/** Informs the plug-in about the processing state. This will be called before any process calls
start with true and after with false.
Note that setProcessing (false) may be called after setProcessing (true) without any process
calls.
Note this function could be called in the UI or in Processing Thread, thats why the plug-in
should only light operation (no memory allocation or big setup reconfiguration),
this could be used to reset some buffers (like Delay line or Reverb).
The host has to be sure that it is called only when the plug-in is enable (setActive (true)
was called). */
virtual tresult PLUGIN_API setProcessing (TBool state) = 0;
* start with true and after with false.
* Note that setProcessing (false) may be called after setProcessing (true) without any process
* calls.
* Note this function could be called in the UI or in Processing Thread, thats why the plug-in
* should only light operation (no memory allocation or big setup reconfiguration),
* this could be used to reset some buffers (like Delay line or Reverb).
* The host has to be sure that it is called only when the plug-in is enable (setActive (true)
* was called).
* \note [(UI-thread or processing-thread) & Activated] */
virtual tresult PLUGIN_API setProcessing (TBool state /*in*/) = 0;
/** The Process call, where all information (parameter changes, event, audio buffer) are passed. */
virtual tresult PLUGIN_API process (ProcessData& data) = 0;
/** The Process call, where all information (parameter changes, event, audio buffer) are passed.
* \note [processing-thread & Processing] */
virtual tresult PLUGIN_API process (ProcessData& data /*in*/) = 0;
/** Gets tail size in samples. For example, if the plug-in is a Reverb plug-in and it knows that
the maximum length of the Reverb is 2sec, then it has to return in getTailSamples()
(in VST2 it was getGetTailSize ()): 2*sampleRate.
This information could be used by host for offline processing, process optimization and
downmix (avoiding signal cut (clicks)).
It should return:
- kNoTail when no tail
- x * sampleRate when x Sec tail.
- kInfiniteTail when infinite tail. */
* the maximum length of the Reverb is 2sec, then it has to return in getTailSamples ()
* (in VST2 it was getGetTailSize ()): 2*sampleRate.
* This information could be used by host for offline processing, process optimization and
* downmix (avoiding signal cut (clicks)).
* It should return:
* - kNoTail when no tail
* - x * sampleRate when x Sec tail.
* - kInfiniteTail when infinite tail.
*
* \note [UI-thread & Setup Done] */
virtual uint32 PLUGIN_API getTailSamples () = 0;
//------------------------------------------------------------------------
@ -347,20 +374,22 @@ DECLARE_CLASS_IID (IAudioProcessor, 0x42043F99, 0xB7DA453C, 0xA569E79D, 0x9AAEC3
- [optional]
Inform the plug-in about how long from the moment of generation/acquiring (from file or from Input)
it will take for its input to arrive, and how long it will take for its output to be presented (to output or to speaker).
it will take for its input to arrive, and how long it will take for its output to be presented (to
output or to speaker).
Note for Input Presentation Latency: when reading from file, the first plug-in will have an input presentation latency set to zero.
When monitoring audio input from an audio device, the initial input latency is the input latency of the audio device itself.
Note for Input Presentation Latency: when reading from file, the first plug-in will have an input
presentation latency set to zero. When monitoring audio input from an audio device, the initial
input latency is the input latency of the audio device itself.
Note for Output Presentation Latency: when writing to a file, the last plug-in will have an output presentation latency set to zero.
When the output of this plug-in is connected to an audio device, the initial output latency is the output
latency of the audio device itself.
Note for Output Presentation Latency: when writing to a file, the last plug-in will have an output
presentation latency set to zero. When the output of this plug-in is connected to an audio device,
the initial output latency is the output latency of the audio device itself.
A value of zero either means no latency or an unknown latency.
Each plug-in adding a latency (returning a none zero value for IAudioProcessor::getLatencySamples) will modify the input
presentation latency of the next plug-ins in the mixer routing graph and will modify the output presentation latency
of the previous plug-ins.
Each plug-in adding a latency (returning a none zero value for IAudioProcessor::getLatencySamples)
will modify the input presentation latency of the next plug-ins in the mixer routing graph and will
modify the output presentation latency of the previous plug-ins.
\n
\image html "iaudiopresentationlatency_usage.png"
@ -371,11 +400,14 @@ of the previous plug-ins.
class IAudioPresentationLatency : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Informs the plug-in about the Audio Presentation Latency in samples for a given direction (kInput/kOutput) and bus index. */
virtual tresult PLUGIN_API setAudioPresentationLatencySamples (BusDirection dir, int32 busIndex, uint32 latencyInSamples) = 0;
//------------------------------------------------------------------------
/** Informs the plug-in about the Audio Presentation Latency in samples for a given direction
* (kInput/kOutput) and bus index.
* \note [UI-thread & Activated] */
virtual tresult PLUGIN_API setAudioPresentationLatencySamples (
BusDirection dir /*in*/, int32 busIndex /*in*/, uint32 latencyInSamples /*in*/) = 0;
//------------------------------------------------------------------------
//------------------------------------------------------------------------
static const FUID iid;
};
@ -388,18 +420,19 @@ DECLARE_CLASS_IID (IAudioPresentationLatency, 0x309ECE78, 0xEB7D4fae, 0x8B2225D9
- [extends IAudioProcessor]
- [released: 3.7.0]
- [mandatory]
To get accurate process context information (Vst::ProcessContext), it is now required to implement this interface and
return the desired bit mask of flags which your audio effect needs. If you do not implement this
interface, you may not get any information at all of the process function.
The host asks for this information once between initialize and setActive. It cannot be changed afterwards.
To get accurate process context information (Vst::ProcessContext), it is now required to implement
this interface and return the desired bit mask of flags which your audio effect needs. If you do not
implement this interface, you may not get any information at all of the process function!
The host asks for this information once between initialize and setActive (in Setup Done). It cannot
be changed afterwards.
This gives the host the opportunity to better optimize the audio process graph when it knows which
plug-ins need which information.
Plug-Ins built with an earlier SDK version (< 3.7) will still get the old information, but the information
may not be as accurate as when using this interface.
Plug-ins built with an earlier SDK version (< 3.7) will still get the old information, but the
information may not be as accurate as when using this interface.
*/
class IProcessContextRequirements : public FUnknown
{
@ -418,7 +451,11 @@ public:
kNeedFrameRate = 1 << 9, // kSmpteValid
kNeedTransportState = 1 << 10, // kPlaying, kCycleActive, kRecording
};
/** Allows the host to ask the plug-in what is really needed for the process context information
* (Vst::ProcessContext).
* \note [UI-thread & Setup Done] */
virtual uint32 PLUGIN_API getProcessContextRequirements () = 0;
//------------------------------------------------------------------------
static const FUID iid;
};

View file

@ -40,7 +40,7 @@ class IAutomationState : public FUnknown
{
public:
//------------------------------------------------------------------------
enum AutomationStates
enum AutomationStates : int32
{
kNoAutomation = 0, ///< Not Read and not Write
kReadState = 1 << 0, ///< Read state
@ -49,8 +49,9 @@ public:
kReadWriteState = kReadState | kWriteState, ///< Read and Write enable
};
/** Sets the current Automation state. */
virtual tresult PLUGIN_API setAutomationState (int32 state) = 0;
/** Sets the current Automation state.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API setAutomationState (int32 state /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -77,7 +77,14 @@ tresult PLUGIN_API MyPlugin::setChannelContextInfos (IAttributeList* list)
{
...
}
// get Channel RuntimeID
int64 runtimeId;
if (list->getInt (ChannelContext::kChannelRuntimeIDKey, runtimeId) == kResultTrue)
{
...
}
// get Channel Index
int64 index;
if (list->getInt (ChannelContext::kChannelIndexKey, index) == kResultTrue)
@ -148,8 +155,9 @@ tresult PLUGIN_API MyPlugin::setChannelContextInfos (IAttributeList* list)
class IInfoListener : public FUnknown
{
public:
/** Receive the channel context infos from host. */
virtual tresult PLUGIN_API setChannelContextInfos (IAttributeList* list) = 0;
/** Receive the channel context infos from host.
* \note [UI-thread & (Initialized | Connected | Setup Done | Activated | Processing)] */
virtual tresult PLUGIN_API setChannelContextInfos (IAttributeList* list /*in*/) = 0;
static const FUID iid;
};
@ -170,22 +178,34 @@ enum ChannelPluginLocation
//------------------------------------------------------------------------
// Colors
//------------------------------------------------------------------------
/** \defgroup vst3typedef VST 3 Data Types */
/*@{*/
/** \ingroup vst3typedef */
/**@{*/
//------------------------------------------------------------------------
/** ARGB (Alpha-Red-Green-Blue) */
typedef uint32 ColorSpec;
typedef uint8 ColorComponent;
/*@}*/
/**@}*/
/** Returns the Blue part of the given ColorSpec */
inline ColorComponent GetBlue (ColorSpec cs) {return (ColorComponent)(cs & 0x000000FF); }
inline ColorComponent GetBlue (ColorSpec cs)
{
return (ColorComponent) (cs & 0x000000FF);
}
/** Returns the Green part of the given ColorSpec */
inline ColorComponent GetGreen (ColorSpec cs) {return (ColorComponent)((cs >> 8) & 0x000000FF); }
inline ColorComponent GetGreen (ColorSpec cs)
{
return (ColorComponent) ((cs >> 8) & 0x000000FF);
}
/** Returns the Red part of the given ColorSpec */
inline ColorComponent GetRed (ColorSpec cs) {return (ColorComponent)((cs >> 16) & 0x000000FF); }
inline ColorComponent GetRed (ColorSpec cs)
{
return (ColorComponent) ((cs >> 16) & 0x000000FF);
}
/** Returns the Alpha part of the given ColorSpec */
inline ColorComponent GetAlpha (ColorSpec cs) {return (ColorComponent)((cs >> 24) & 0x000000FF); }
inline ColorComponent GetAlpha (ColorSpec cs)
{
return (ColorComponent) ((cs >> 24) & 0x000000FF);
}
//------------------------------------------------------------------------
/** Keys used as AttrID (Attribute ID) in the return IAttributeList of
@ -197,6 +217,10 @@ const CString kChannelUIDKey = "channel uid";
/** integer (int64) [optional]: number of characters in kChannelUIDKey */
const CString kChannelUIDLengthKey = "channel uid length";
/** integer (int64) [optional]: runtime id to identify a channel (may change when reloading project)
*/
const CString kChannelRuntimeIDKey = "channel runtime id";
/** string (TChar) [optional]: name of the channel like displayed in the mixer */
const CString kChannelNameKey = "channel name";
@ -206,26 +230,33 @@ const CString kChannelNameLengthKey = "channel name length";
/** color (ColorSpec) [optional]: used color for the channel in mixer or track */
const CString kChannelColorKey = "channel color";
/** integer (int64) [optional]: index of the channel in a channel index namespace, start with 1 not * 0! */
/** integer (int64) [optional]: index of the channel in a channel index namespace,
* start with 1 not 0! */
const CString kChannelIndexKey = "channel index";
/** integer (int64) [optional]: define the order of the current used index namespace, start with 1 not 0!
For example:
index namespace is "Input" -> order 1,
index namespace is "Channel" -> order 2,
index namespace is "Output" -> order 3 */
/** integer (int64) [optional]: define the order of the current used index namespace,
* start with 1 not 0!
* For example:
* index namespace is "Input" -> order 1,
* index namespace is "Channel" -> order 2,
* index namespace is "Output" -> order 3
*/
const CString kChannelIndexNamespaceOrderKey = "channel index namespace order";
/** string (TChar) [optional]: name of the channel index namespace for example "Input", "Output", "Channel", ... */
/** string (TChar) [optional]: name of the channel index namespace
* for example "Input", "Output","Channel", ...
*/
const CString kChannelIndexNamespaceKey = "channel index namespace";
/** integer (int64) [optional]: number of characters in kChannelIndexNamespaceKey */
const CString kChannelIndexNamespaceLengthKey = "channel index namespace length";
const CString kChannelIndexNamespaceLengthKey = "channel index namespace length";
/** PNG image representation as binary [optional] */
const CString kChannelImageKey = "channel image";
const CString kChannelImageKey = "channel image";
/** integer (int64) [optional]: routing position of the plug-in in the channel (see ChannelPluginLocation) */
/** integer (int64) [optional]: routing position of the plug-in in the channel
* (see ChannelPluginLocation)
*/
const CString kChannelPluginLocationKey = "channel plugin location";
//------------------------------------------------------------------------

View file

@ -58,7 +58,7 @@ The kMain busses have to place before any others kAux busses.
See also: IComponent::getBusInfo, IComponent::activateBus
*/
/*@{*/
/**@{*/
//------------------------------------------------------------------------
/** Bus media types */
@ -115,7 +115,7 @@ struct BusInfo
};
};
/*@}*/
/**@}*/
//------------------------------------------------------------------------
/** I/O modes */
@ -159,37 +159,49 @@ class IComponent : public IPluginBase
{
public:
//------------------------------------------------------------------------
/** Called before initializing the component to get information about the controller class. */
virtual tresult PLUGIN_API getControllerClassId (TUID classId) = 0;
/** Called before initializing the component to get information about the controller class.
* \note [UI-thread & Created] */
virtual tresult PLUGIN_API getControllerClassId (TUID classId /*out*/) = 0;
/** Called before 'initialize' to set the component usage (optional). See \ref IoModes */
virtual tresult PLUGIN_API setIoMode (IoMode mode) = 0;
/** Called before 'initialize' to set the component usage (optional). See \ref IoModes.
* \note [UI-thread & Created] */
virtual tresult PLUGIN_API setIoMode (IoMode mode /*in*/) = 0;
/** Called after the plug-in is initialized. See \ref MediaTypes, BusDirections */
virtual int32 PLUGIN_API getBusCount (MediaType type, BusDirection dir) = 0;
/** Called after the plug-in is initialized. See \ref MediaTypes, BusDirections.
* \note [UI-thread & Initialized] */
virtual int32 PLUGIN_API getBusCount (MediaType type /*in*/, BusDirection dir /*in*/) = 0;
/** Called after the plug-in is initialized. See \ref MediaTypes, BusDirections */
virtual tresult PLUGIN_API getBusInfo (MediaType type, BusDirection dir, int32 index, BusInfo& bus /*out*/) = 0;
/** Called after the plug-in is initialized. See \ref MediaTypes, BusDirections.
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API getBusInfo (MediaType type /*in*/, BusDirection dir /*in*/,
int32 index /*in*/, BusInfo& bus /*out*/) = 0;
/** Retrieves routing information (to be implemented when more than one regular input or output bus exists).
The inInfo always refers to an input bus while the returned outInfo must refer to an output bus! */
virtual tresult PLUGIN_API getRoutingInfo (RoutingInfo& inInfo, RoutingInfo& outInfo /*out*/) = 0;
/** Retrieves routing information (to be implemented when more than one regular input or output
* bus exists). The inInfo always refers to an input bus while the returned outInfo must refer
* to an output bus!
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API getRoutingInfo (RoutingInfo& inInfo /*in*/,
RoutingInfo& outInfo /*out*/) = 0;
/** Called upon (de-)activating a bus in the host application. The plug-in should only processed
an activated bus, the host could provide less see \ref AudioBusBuffers in the process call
(see \ref IAudioProcessor::process) if last busses are not activated. An already activated bus
does not need to be reactivated after a IAudioProcessor::setBusArrangements call. */
virtual tresult PLUGIN_API activateBus (MediaType type, BusDirection dir, int32 index,
TBool state) = 0;
* an activated bus, the host could provide less see \ref AudioBusBuffers in the process call
* (see \ref IAudioProcessor::process) if last busses are not activated. An already activated
* bus does not need to be reactivated after a IAudioProcessor::setBusArrangements call.
* \note [UI-thread & Setup Done] */
virtual tresult PLUGIN_API activateBus (MediaType type /*in*/, BusDirection dir /*in*/,
int32 index /*in*/, TBool state /*in*/) = 0;
/** Activates / deactivates the component. */
virtual tresult PLUGIN_API setActive (TBool state) = 0;
/** Activates / deactivates the component.
* \note [UI-thread & Setup Done] */
virtual tresult PLUGIN_API setActive (TBool state /*in*/) = 0;
/** Sets complete state of component. */
virtual tresult PLUGIN_API setState (IBStream* state) = 0;
/** Sets complete state of component.
* \note [UI-thread & (Initialized | Connected | Setup Done | Activated | Processing)] */
virtual tresult PLUGIN_API setState (IBStream* state /*in*/) = 0;
/** Retrieves complete state of component. */
virtual tresult PLUGIN_API getState (IBStream* state) = 0;
/** Retrieves complete state of component.
* \note [UI-thread & (Initialized | Connected | Setup Done | Activated | Processing)] */
virtual tresult PLUGIN_API getState (IBStream* state /*inout*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -30,31 +30,33 @@ namespace Vst {
class IContextMenu;
//------------------------------------------------------------------------
/** Extended host callback interface Vst::IComponentHandler3 for an edit controller.
/** Extended host callback interface Vst::IComponentHandler3 for an edit controller.
\ingroup vstIHost vst350
- [host imp]
- [extends IComponentHandler]
- [released: 3.5.0]
- [optional]
A plug-in can ask the host to create a context menu for a given exported parameter ID or a generic context menu.\n
A plug-in can ask the host to create a context menu for a given exported parameter ID or a generic
context menu.\n
The host may pre-fill this context menu with specific items regarding the parameter ID like "Show automation for parameter",
"MIDI learn" etc...\n
The host may pre-fill this context menu with specific items regarding the parameter ID like "Show
automation for parameter", "MIDI learn" etc...\n
The plug-in can use the context menu in two ways :
- add its own items to the menu via the IContextMenu interface and call IContextMenu::popup(..) to create the pop-up. See the \ref IContextMenuExample.
- add its own items to the menu via the IContextMenu interface and call IContextMenu::popup(..) to
create the pop-up. See the \ref IContextMenuExample.
- extract the host menu items and add them to a context menu created by the plug-in.
\b Note: You can and should use this even if you do not add your own items to the menu as this is considered to be a big user value.
\b Note: You can and should use this even if you do not add your own items to the menu as this is
considered to be a big user value.
\sa IContextMenu
\sa IContextMenuTarget
\section IContextMenuExample Examples
- For example, Cubase adds its owned entries in the context menu opened with right-click on an exported parameter when the plug-in uses createContextMenu.
\image html "contextmenuexample.png"
\n
- For example, Cubase adds its owned entries in the context menu opened with right-click on an
exported parameter when the plug-in uses createContextMenu. \image html "contextmenuexample.png" \n
- Adding plug-in specific items to the context menu:
\code{.cpp}
@ -62,56 +64,60 @@ The plug-in can use the context menu in two ways :
class PluginContextMenuTarget : public IContextMenuTarget, public FObject
{
public:
PluginContextMenuTarget () {}
PluginContextMenuTarget () {}
virtual tresult PLUGIN_API executeMenuItem (int32 tag)
{
// this will be called if the user has executed one of the menu items of the plug-in.
// It will not be called for items of the host.
switch (tag)
{
case 1: break;
case 2: break;
}
return kResultTrue;
}
tresult PLUGIN_API executeMenuItem (int32 tag) override
{
// this will be called if the user has executed one of the menu items of the plug-in.
// It will not be called for items of the host.
switch (tag)
{
case 1: break;
case 2: break;
}
return kResultTrue;
}
OBJ_METHODS(PluginContextMenuTarget, FObject)
DEFINE_INTERFACES
DEF_INTERFACE (IContextMenuTarget)
END_DEFINE_INTERFACES (FObject)
REFCOUNT_METHODS(FObject)
OBJ_METHODS(PluginContextMenuTarget, FObject)
DEFINE_INTERFACES
DEF_INTERFACE (IContextMenuTarget)
END_DEFINE_INTERFACES (FObject)
REFCOUNT_METHODS(FObject)
};
// The following is the code to create the context menu
void popupContextMenu (IComponentHandler* componentHandler, IPlugView* view, const ParamID* paramID, UCoord x, UCoord y)
void popupContextMenu (IComponentHandler* componentHandler, IPlugView* view, const ParamID* paramID,
UCoord x, UCoord y)
{
if (componentHandler == 0 || view == 0)
return;
FUnknownPtr<IComponentHandler3> handler (componentHandler);
if (handler == 0)
return;
IContextMenu* menu = handler->createContextMenu (view, paramID);
if (menu)
{
// here you can add your entries (optional)
PluginContextMenuTarget* target = new PluginContextMenuTarget ();
IContextMenu::Item item = {0};
UString128 ("My Item 1").copyTo (item.name, 128);
item.tag = 1;
menu->addItem (item, target);
if (componentHandler == 0 || view == 0)
return;
FUnknownPtr<IComponentHandler3> handler (componentHandler);
if (handler == 0)
return;
if (IContextMenu* menu = handler->createContextMenu (view, paramID))
{
// here you can add your entries (optional)
PluginContextMenuTarget* target = new PluginContextMenuTarget ();
UString128 ("My Item 2").copyTo (item.name, 128);
item.tag = 2;
menu->addItem (item, target);
target->release ();
//--end of adding new entries
// here the the context menu will be pop-up (and it waits a user interaction)
menu->popup (x, y);
menu->release ();
}
IContextMenu::Item item = {0};
UString128 ("My Item 1").copyTo (item.name, 128);
item.tag = 1;
menu->addItem (item, target);
UString128 ("My Item 2").copyTo (item.name, 128);
item.tag = 2;
menu->addItem (item, target);
target->release ();
//--end of adding new entries
// here the the context menu will be pop-up (and it waits a user interaction)
menu->popup (x, y);
menu->release ();
}
}
\endcode
*/
@ -119,12 +125,14 @@ class IComponentHandler3 : public FUnknown
{
public:
/** Creates a host context menu for a plug-in:
- If paramID is zero, the host may create a generic context menu.
- The IPlugView object must be valid.
- The return IContextMenu object needs to be released afterwards by the plug-in.
*/
virtual IContextMenu* PLUGIN_API createContextMenu (IPlugView* plugView, const ParamID* paramID) = 0;
//------------------------------------------------------------------------
* - If paramID is zero, the host may create a generic context menu.
* - The IPlugView object must be valid.
* - The return IContextMenu object needs to be released afterwards by the plug-in.
*
* \note [UI-thread & (Initialized | Connected) & plugView] */
virtual IContextMenu* PLUGIN_API createContextMenu (IPlugView* plugView /*in*/,
const ParamID* paramID /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
};
@ -146,8 +154,9 @@ this menu item.
class IContextMenuTarget : public FUnknown
{
public:
/** Called when an menu item was executed. */
virtual tresult PLUGIN_API executeMenuItem (int32 tag) = 0;
/** Called when an menu item was executed.
* \note [UI-thread & (Initialized | Connected) & plugView] */
virtual tresult PLUGIN_API executeMenuItem (int32 tag /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
};
@ -189,22 +198,30 @@ class IContextMenu : public FUnknown
public:
typedef IContextMenuItem Item;
/** Gets the number of menu items. */
/** Gets the number of menu items.
* \note [UI-thread] */
virtual int32 PLUGIN_API getItemCount () = 0;
/** Gets a menu item and its target (target could be not assigned). */
virtual tresult PLUGIN_API getItem (int32 index, Item& item /*out*/, IContextMenuTarget** target /*out*/) = 0;
/** Gets a menu item and its target (target could be not assigned).
* \note [UI-thread] */
virtual tresult PLUGIN_API getItem (int32 index /*in*/, Item& item /*out*/,
IContextMenuTarget** target /*out*/) = 0;
/** Adds a menu item and its target. */
virtual tresult PLUGIN_API addItem (const Item& item, IContextMenuTarget* target) = 0;
/** Adds a menu item and its target.
* \note [UI-thread] */
virtual tresult PLUGIN_API addItem (const Item& item /*in*/,
IContextMenuTarget* target /*in*/) = 0;
/** Removes a menu item. */
virtual tresult PLUGIN_API removeItem (const Item& item, IContextMenuTarget* target) = 0;
/** Removes a menu item.
* \note [UI-thread] */
virtual tresult PLUGIN_API removeItem (const Item& item /*in*/,
IContextMenuTarget* target /*in*/) = 0;
/** Pop-ups the menu. Coordinates are relative to the top-left position of the plug-ins view. */
virtual tresult PLUGIN_API popup (UCoord x, UCoord y) = 0;
/** Pop-ups the menu. Coordinates are relative to the top-left position of the plug-ins view.
* \note [UI-thread] */
virtual tresult PLUGIN_API popup (UCoord x /*in*/, UCoord y /*in*/) = 0;
//------------------------------------------------------------------------
//------------------------------------------------------------------------
static const FUID iid;
};

View file

@ -30,9 +30,12 @@ namespace Vst {
class IAudioProcessor;
//------------------------------------------------------------------------
/** \ingroup vst3typedef */
/**@{*/
typedef uint32 DataExchangeQueueID;
typedef uint32 DataExchangeBlockID;
typedef uint32 DataExchangeUserContextID;
/**@}*/
//------------------------------------------------------------------------
static SMTG_CONSTEXPR DataExchangeQueueID InvalidDataExchangeQueueID = kMaxInt32;

View file

@ -60,6 +60,10 @@ struct ParameterInfo
int32 flags; ///< ParameterFlags (see below)
/** Parameter flags
*
* Note that all non defined bits are reserved for future use!
*/
enum ParameterFlags : int32
{
/** No flags wanted.
@ -215,20 +219,24 @@ class IComponentHandler : public FUnknown
public:
//------------------------------------------------------------------------
/** To be called before calling a performEdit (e.g. on mouse-click-down event).
* This must be called in the UI-Thread context! */
* This must be called in the UI-Thread context!
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API beginEdit (ParamID id /*in*/) = 0;
/** Called between beginEdit and endEdit to inform the handler that a given parameter has a new
* value. This must be called in the UI-Thread context! */
* value. This must be called in the UI-Thread context!
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API performEdit (ParamID id /*in*/,
ParamValue valueNormalized /*in*/) = 0;
/** To be called after calling a performEdit (e.g. on mouse-click-up event).
* This must be called in the UI-Thread context! */
* This must be called in the UI-Thread context!
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API endEdit (ParamID id /*in*/) = 0;
/** Instructs host to restart the component. This must be called in the UI-Thread context!
* @param[in] flags is a combination of RestartFlags */
* @param[in] flags is a combination of RestartFlags
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API restartComponent (int32 flags /*in*/) = 0;
//------------------------------------------------------------------------
@ -301,23 +309,27 @@ class IComponentHandler2 : public FUnknown
public:
//------------------------------------------------------------------------
/** Tells host that the plug-in is dirty (something besides parameters has changed since last
* save), if true the host should apply a save before quitting. */
* save), if true the host should apply a save before quitting.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API setDirty (TBool state /*in*/) = 0;
/** Tells host that it should open the plug-in editor the next time it's possible. You should
* use this instead of showing an alert and blocking the program flow (especially on loading
* projects). */
virtual tresult PLUGIN_API requestOpenEditor (FIDString name = ViewType::kEditor) = 0;
* projects).
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API requestOpenEditor (FIDString name = ViewType::kEditor /*in*/) = 0;
//------------------------------------------------------------------------
/** Starts the group editing (call before a \ref IComponentHandler::beginEdit),
* the host will keep the current timestamp at this call and will use it for all
* \ref IComponentHandler::beginEdit, \ref IComponentHandler::performEdit,
* \ref IComponentHandler::endEdit calls until a \ref finishGroupEdit (). */
* \ref IComponentHandler::endEdit calls until a \ref finishGroupEdit ().
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API startGroupEdit () = 0;
/** Finishes the group editing started by a \ref startGroupEdit (call after a \ref
* IComponentHandler::endEdit). */
* IComponentHandler::endEdit).
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API finishGroupEdit () = 0;
//------------------------------------------------------------------------
@ -354,7 +366,8 @@ class IComponentHandlerBusActivation : public FUnknown
{
public:
//------------------------------------------------------------------------
/** request the host to activate or deactivate a specific bus. */
/** request the host to activate or deactivate a specific bus.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API requestBusActivation (MediaType type /*in*/, BusDirection dir /*in*/,
int32 index /*in*/, TBool state /*in*/) = 0;
@ -372,13 +385,13 @@ DECLARE_CLASS_IID (IComponentHandlerBusActivation, 0x067D02C1, 0x5B4E274D, 0xA92
- [released: 3.7.0]
- [optional]
Allows the plug-in to request the host to create a progress for some specific tasks which take
some time. The host can visualize the progress as read-only UI elements. For example,
after loading a project where a plug-in needs to load extra
data (e.g. samples) in a background thread, this enables the host to get and visualize the current
status of the loading progress and to inform the user when the loading is finished. Note: During the
progress, the host can unload the plug-in at any time. Make sure that the plug-in supports this use
case.
Allows the plug-in to request the host to create a progress for some specific tasks which take some
time. The host can visualize the progress as read-only UI elements.
For example, after loading a project where a plug-in needs to load extra data (e.g. samples) in a
background thread, this enables the host to get and visualize the current status of the loading
progress and to inform the user when the loading is finished.
Note: During the progress, the host can unload the plug-in at any time. Make sure that the plug-in
supports this use case.
\section IProgressExample Example
@ -390,7 +403,7 @@ case.
FUnknownPtr<IProgress> progress (componentHandler);
if (progress)
progress->start (IProgress::ProgressType::UIBackgroundTask, STR ("Load Samples..."),
mProgressID);
mProgressID);
// ...
myProgressValue += incProgressStep;
@ -422,15 +435,18 @@ public:
using ID = uint64;
/** Start a new progress of a given type and optional Description. outID is as ID created by the
* host to identify this newly created progress (for update and finish method) */
* host to identify this newly created progress (for update and finish method).
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API start (ProgressType type /*in*/,
const tchar* optionalDescription /*in*/,
ID& outID /*out*/) = 0;
/** Update the progress value (normValue between [0, 1]) associated to the given id */
/** Update the progress value (normValue between [0, 1]) associated to the given id.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API update (ID id /*in*/, ParamValue normValue /*in*/) = 0;
/** Finish the progress associated to the given id */
/** Finish the progress associated to the given id.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API finish (ID id /*in*/) = 0;
//------------------------------------------------------------------------
@ -453,59 +469,72 @@ class IEditController : public IPluginBase
{
public:
//------------------------------------------------------------------------
/** Receives the component state. */
/** Receives the component state.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API setComponentState (IBStream* state /*in*/) = 0;
/** Sets the controller state. */
/** Sets the controller state.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API setState (IBStream* state /*in*/) = 0;
/** Gets the controller state. */
/** Gets the controller state.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getState (IBStream* state /*inout*/) = 0;
// parameters -------------------------
/** Returns the number of parameters exported. */
/** Returns the number of parameters exported.
* \note [UI-thread & Connected] */
virtual int32 PLUGIN_API getParameterCount () = 0;
/** Gets for a given index the parameter information. */
/** Gets for a given index the parameter information.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getParameterInfo (int32 paramIndex /*in*/,
ParameterInfo& info /*out*/) = 0;
/** Gets for a given paramID and normalized value its associated string representation. */
/** Gets for a given paramID and normalized value its associated string representation.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getParamStringByValue (ParamID id /*in*/,
ParamValue valueNormalized /*in*/,
String128 string /*out*/) = 0;
/** Gets for a given paramID and string its normalized value. */
/** Gets for a given paramID and string its normalized value.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getParamValueByString (ParamID id /*in*/, TChar* string /*in*/,
ParamValue& valueNormalized /*out*/) = 0;
/** Returns for a given paramID and a normalized value its plain representation
* (for example -6 for -6dB - see \ref vst3AutomationIntro). */
* (for example -6 for -6dB - see \ref vst3AutomationIntro).
* \note [UI-thread & Connected] */
virtual ParamValue PLUGIN_API normalizedParamToPlain (ParamID id /*in*/,
ParamValue valueNormalized /*in*/) = 0;
/** Returns for a given paramID and a plain value its normalized value. (see \ref
* vst3AutomationIntro). */
* vst3AutomationIntro).
* \note [UI-thread & Connected] */
virtual ParamValue PLUGIN_API plainParamToNormalized (ParamID id /*in*/,
ParamValue plainValue /*in*/) = 0;
/** Returns the normalized value of the parameter associated to the paramID. */
/** Returns the normalized value of the parameter associated to the paramID.
* \note [UI-thread & Connected] */
virtual ParamValue PLUGIN_API getParamNormalized (ParamID id /*in*/) = 0;
/** Sets the normalized value to the parameter associated to the paramID. The controller must
* never pass this value-change back to the host via the IComponentHandler.
* It should update the according GUI element(s) only! */
* It should update the according GUI element(s) only!
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API setParamNormalized (ParamID id /*in*/, ParamValue value /*in*/) = 0;
// handler ----------------------------
/** Gets from host a handler which allows the Plugin-in to communicate with the host.
* Note: This is mandatory if the host is using the IEditController! */
* \note This is mandatory if the host is using the IEditController!
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API setComponentHandler (IComponentHandler* handler /*in*/) = 0;
// view -------------------------------
/** Creates the editor view of the plug-in, currently only "editor" is supported, see \ref
* ViewType. The life time of the editor view will never exceed the life time of this controller
* instance. */
* instance.
* \note [UI-thread & Connected] */
virtual IPlugView* PLUGIN_API createView (FIDString name /*in*/) = 0;
//------------------------------------------------------------------------
@ -515,12 +544,11 @@ public:
DECLARE_CLASS_IID (IEditController, 0xDCD7BBE3, 0x7742448D, 0xA874AACC, 0x979C759E)
//------------------------------------------------------------------------
/** \defgroup vst3typedef VST 3 Data Types */
/*@{*/
//------------------------------------------------------------------------
/** \ingroup vst3typedef */
/**@{*/
/** Knob Mode Type */
using KnobMode = int32;
/*@}*/
/**@}*/
//------------------------------------------------------------------------
/** Knob Mode */
@ -548,17 +576,20 @@ class IEditController2 : public FUnknown
{
public:
/** Host could set the Knob Mode for the plug-in. Return kResultFalse means not supported mode.
* \see KnobModes. */
* \see KnobModes.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API setKnobMode (KnobMode mode /*in*/) = 0;
/** Host could ask to open the plug-in help (could be: opening a PDF document or link to a web
* page). The host could call it with onlyCheck set to true for testing support of open Help.
* Return kResultFalse means not supported function. */
* Return kResultFalse means not supported function.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API openHelp (TBool onlyCheck /*in*/) = 0;
/** Host could ask to open the plug-in about box.
* The host could call it with onlyCheck set to true for testing support of open AboutBox.
* Return kResultFalse means not supported function. */
* Return kResultFalse means not supported function.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API openAboutBox (TBool onlyCheck /*in*/) = 0;
//------------------------------------------------------------------------
@ -598,8 +629,8 @@ class MyEditController: public EditControllerEx1, public IMidiMapping
//...
//---IMidiMapping---------------------------
tresult PLUGIN_API getMidiControllerAssignment (int32 busIndex, int16 channel,
CtrlNumber midiControllerNumber,
ParamID& id) override;
CtrlNumber midiControllerNumber,
ParamID& id) override;
//---Interface---------
OBJ_METHODS (MyEditController, EditControllerEx1)
DEFINE_INTERFACES
@ -611,9 +642,9 @@ class MyEditController: public EditControllerEx1, public IMidiMapping
//--------------------------------------
// in myeditcontroller.cpp
tresult PLUGIN_API MyEditController::getMidiControllerAssignment (int32 busIndex,
int16 midiChannel,
int16 midiChannel,
CtrlNumber midiControllerNumber,
ParamID& tag)
ParamID& tag)
{
// for my first Event bus and for MIDI channel 0 and for MIDI CC Volume only
if (busIndex == 0 && midiChannel == 0 && midiControllerNumber == kCtrlVolume)
@ -624,7 +655,6 @@ tresult PLUGIN_API MyEditController::getMidiControllerAssignment (int32 busIndex
return kResultFalse;
}
\endcode
*/
class IMidiMapping : public FUnknown
{
@ -636,7 +666,8 @@ public:
* @param[in] midiControllerNumber - see \ref ControllerNumbers for expected values (could be
* bigger than 127)
* @param[out] id - return the associated ParamID to the given midiControllerNumber
*/
*
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getMidiControllerAssignment (int32 busIndex /*in*/,
int16 channel /*in*/,
CtrlNumber midiControllerNumber /*in*/,
@ -678,10 +709,12 @@ class IEditControllerHostEditing : public FUnknown
{
public:
/** Called before a setParamNormalized sequence, a endEditFromHost will be call at the end of
* the editing action. */
* the editing action.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API beginEditFromHost (ParamID paramID /*in*/) = 0;
/** Called after a beginEditFromHost and a sequence of setParamNormalized. */
/** Called after a beginEditFromHost and a sequence of setParamNormalized.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API endEditFromHost (ParamID paramID /*in*/) = 0;
//------------------------------------------------------------------------
@ -703,7 +736,8 @@ class IComponentHandlerSystemTime : public FUnknown
{
public:
//------------------------------------------------------------------------
/** get the current systemTime (the same as the one used in ProcessContext::systemTime). */
/** get the current systemTime (the same as the one used in ProcessContext::systemTime).
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getSystemTime (int64& systemTime /*out*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -155,7 +155,7 @@ struct Event
kUserReserved2 = 1 << 15 ///< reserved for user (for internal use)
};
/** Event Types - used for Event::type */
/** Event Types - used for Event::type */
enum EventTypes
{
kNoteOnEvent = 0, ///< is \ref NoteOnEvent
@ -201,7 +201,7 @@ public:
virtual int32 PLUGIN_API getEventCount () = 0;
/** Gets parameter by index. */
virtual tresult PLUGIN_API getEvent (int32 index, Event& e /*out*/) = 0;
virtual tresult PLUGIN_API getEvent (int32 index /*in*/, Event& e /*out*/) = 0;
/** Adds a new event. */
virtual tresult PLUGIN_API addEvent (Event& e /*in*/) = 0;

View file

@ -36,10 +36,12 @@ class IHostApplication : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Gets host application name. */
/** Gets host application name.
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API getName (String128 name) = 0;
/** Creates host object (e.g. Vst::IMessage). */
/** Creates host object (for example: Vst::IMessage).
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API createInstance (TUID cid, TUID _iid, void** obj) = 0;
//------------------------------------------------------------------------

View file

@ -65,7 +65,8 @@ DECLARE_CLASS_IID (IMessage, 0x936F033B, 0xC6C047DB, 0xBB0882F8, 0x13C1E613)
- [mandatory]
This interface is used for the communication of separate components.
Note that some hosts will place a proxy object between the components so that they are not directly connected.
Note that some hosts will place a proxy object between the components so that they are not directly
connected.
\see \ref vst3Communication
*/
@ -73,14 +74,17 @@ class IConnectionPoint : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Connects this instance with another connection point. */
virtual tresult PLUGIN_API connect (IConnectionPoint* other) = 0;
/** Connects this instance with another connection point.
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API connect (IConnectionPoint* other /*in*/) = 0;
/** Disconnects a given connection point from this. */
virtual tresult PLUGIN_API disconnect (IConnectionPoint* other) = 0;
/** Disconnects a given connection point from this.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API disconnect (IConnectionPoint* other /*in*/) = 0;
/** Called when a message has been sent from the connection point to this. */
virtual tresult PLUGIN_API notify (IMessage* message) = 0;
/** Called when a message has been sent from the connection point to this.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API notify (IMessage* message /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -42,18 +42,18 @@ Use this if you want to implement custom MIDI-Learn functionality in your plug-i
// in MyController class declaration
class MyController : public Vst::EditController, public Vst::IMidiLearn
{
// ...
//--- IMidiLearn ---------------------------------
tresult PLUGIN_API onLiveMIDIControllerInput (int32 busIndex, int16 channel,
CtrlNumber midiCC) SMTG_OVERRIDE;
// ...
// ...
//--- IMidiLearn ---------------------------------
tresult PLUGIN_API onLiveMIDIControllerInput (int32 busIndex, int16 channel,
CtrlNumber midiCC) SMTG_OVERRIDE;
// ...
OBJ_METHODS (MyController, Vst::EditController)
DEFINE_INTERFACES
// ...
DEF_INTERFACE (Vst::IMidiLearn)
END_DEFINE_INTERFACES (Vst::EditController)
//...
OBJ_METHODS (MyController, Vst::EditController)
DEFINE_INTERFACES
// ...
DEF_INTERFACE (Vst::IMidiLearn)
END_DEFINE_INTERFACES (Vst::EditController)
//...
}
//------------------------------------------------
@ -61,38 +61,40 @@ class MyController : public Vst::EditController, public Vst::IMidiLearn
#include "pluginterfaces/vst/ivstmidilearn.h
namespace Steinberg {
namespace Vst {
DEF_CLASS_IID (IMidiLearn)
}
namespace Vst {
DEF_CLASS_IID (IMidiLearn)
}
}
//------------------------------------------------------------------------
tresult PLUGIN_API MyController::onLiveMIDIControllerInput (int32 busIndex,
int16 channel, CtrlNumber midiCC)
tresult PLUGIN_API MyController::onLiveMIDIControllerInput (int32 busIndex,
int16 channel, CtrlNumber midiCC)
{
// if we are not in doMIDILearn (triggered by a UI button for example)
// or wrong channel then return
if (!doMIDILearn || busIndex != 0 || channel != 0 || midiLearnParamID == InvalidParamID)
return kResultFalse;
// if we are not in doMIDILearn (triggered by a UI button for example)
// or wrong channel then return
if (!doMIDILearn || busIndex != 0 || channel != 0 || midiLearnParamID == InvalidParamID)
return kResultFalse;
// adapt our internal MIDICC -> parameterID mapping
midiCCMapping[midiCC] = midiLearnParamID;
// adapt our internal MIDICC -> parameterID mapping
midiCCMapping[midiCC] = midiLearnParamID;
// new mapping then inform the host that our MIDI assignment has changed
if (auto componentHandler = getComponentHandler ())
{
componentHandler->restartComponent (kMidiCCAssignmentChanged);
}
return kResultTrue;
// new mapping then inform the host that our MIDI assignment has changed
if (auto componentHandler = getComponentHandler ())
{
componentHandler->restartComponent (kMidiCCAssignmentChanged);
}
return kResultTrue;
}
\endcode
*/
class IMidiLearn : public FUnknown
{
public:
/** Called on live input MIDI-CC change associated to a given bus index and MIDI channel */
virtual tresult PLUGIN_API onLiveMIDIControllerInput (int32 busIndex, int16 channel,
CtrlNumber midiCC) = 0;
/** Called on live input MIDI-CC change associated to a given bus index and MIDI channel.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API onLiveMIDIControllerInput (int32 busIndex /*in*/,
int16 channel /*in*/,
CtrlNumber midiCC /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
@ -100,7 +102,6 @@ public:
DECLARE_CLASS_IID (IMidiLearn, 0x6B2449CC, 0x419740B5, 0xAB3C79DA, 0xC5FE5C86)
//------------------------------------------------------------------------
} // namespace Vst
} // namespace Steinberg

View file

@ -28,14 +28,13 @@ namespace Steinberg {
namespace Vst {
//------------------------------------------------------------------------
/** \defgroup vst3typedef VST 3 Data Types */
/*@{*/
//------------------------------------------------------------------------
/** \ingroup vst3typedef */
/**@{*/
/** Note Expression Types */
typedef uint32 NoteExpressionTypeID;
/** Note Expression Value */
typedef double NoteExpressionValue;
/*@}*/
/**@}*/
//------------------------------------------------------------------------
/** NoteExpressionTypeIDs describes the type of the note expression.
@ -64,9 +63,10 @@ enum NoteExpressionTypeIDs : uint32
//------------------------------------------------------------------------
/** Description of a Note Expression Type
This structure is part of the NoteExpressionTypeInfo structure, it describes for given NoteExpressionTypeID its default value
(for example 0.5 for a kTuningTypeID (kIsBipolar: centered)), its minimum and maximum (for predefined NoteExpressionTypeID the full range is predefined too)
and a stepCount when the given NoteExpressionTypeID is limited to discrete values (like on/off state).
This structure is part of the NoteExpressionTypeInfo structure, it describes for given
NoteExpressionTypeID its default value (for example 0.5 for a kTuningTypeID (kIsBipolar: centered)),
its minimum and maximum (for predefined NoteExpressionTypeID the full range is predefined too) and a
stepCount when the given NoteExpressionTypeID is limited to discrete values (like on/off state).
\see NoteExpressionTypeInfo
*/
struct NoteExpressionValueDescription
@ -83,11 +83,12 @@ struct NoteExpressionValueDescription
//------------------------------------------------------------------------
/** Note Expression Value event. Used in \ref Event (union)
A note expression event affects one single playing note (referring its noteId).
This kind of event is send from host to the plug-in like other events (NoteOnEvent, NoteOffEvent,...) in \ref ProcessData during the process call.
Note expression events for a specific noteId can only occur after a NoteOnEvent. The host must take care that the event list (\ref IEventList) is properly sorted.
Expression events are always absolute normalized values [0.0, 1.0].
The predefined types have a predefined mapping of the normalized values (see \ref NoteExpressionTypeIDs)
\sa INoteExpressionController
This kind of event is send from host to the plug-in like other events (NoteOnEvent,
NoteOffEvent,...) in \ref ProcessData during the process call. Note expression events for a specific
noteId can only occur after a NoteOnEvent. The host must take care that the event list (\ref
IEventList) is properly sorted. Expression events are always absolute normalized values [0.0, 1.0].
The predefined types have a predefined mapping of the normalized values (see \ref
NoteExpressionTypeIDs) \sa INoteExpressionController
*/
struct NoteExpressionValueEvent
{
@ -144,20 +145,22 @@ struct NoteExpressionTypeInfo
};
//------------------------------------------------------------------------
/** Extended plug-in interface IEditController for note expression event support: Vst::INoteExpressionController
/** Extended plug-in interface IEditController for note expression event support:
Vst::INoteExpressionController
\ingroup vstIPlug vst350
- [plug imp]
- [extends IEditController]
- [released: 3.5.0]
- [optional]
With this plug-in interface, the host can retrieve all necessary note expression information supported by the plug-in.
Note expression information (\ref NoteExpressionTypeInfo) are specific for given channel and event bus.
With this plug-in interface, the host can retrieve all necessary note expression information
supported by the plug-in. Note expression information (\ref NoteExpressionTypeInfo) are specific for
given channel and event bus.
Note that there is only one NoteExpressionTypeID per given channel of an event bus.
The method getNoteExpressionStringByValue allows conversion from a normalized value to a string representation
and the getNoteExpressionValueByString method from a string to a normalized value.
The method getNoteExpressionStringByValue allows conversion from a normalized value to a string
representation and the getNoteExpressionValueByString method from a string to a normalized value.
When the note expression state changes (for example when switching presets) the plug-in needs
to inform the host about it via \ref IComponentHandler::restartComponent (kNoteExpressionChanged).
@ -165,19 +168,30 @@ to inform the host about it via \ref IComponentHandler::restartComponent (kNoteE
class INoteExpressionController : public FUnknown
{
public:
/** Returns number of supported note change types for event bus index and channel. */
virtual int32 PLUGIN_API getNoteExpressionCount (int32 busIndex, int16 channel) = 0;
/** Returns number of supported note change types for event bus index and channel.
* \note [UI-thread & Connected] */
virtual int32 PLUGIN_API getNoteExpressionCount (int32 busIndex /*in*/,
int16 channel /*in*/) = 0;
/** Returns note change type info. */
virtual tresult PLUGIN_API getNoteExpressionInfo (int32 busIndex, int16 channel, int32 noteExpressionIndex, NoteExpressionTypeInfo& info /*out*/) = 0;
/** Returns note change type info.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getNoteExpressionInfo (int32 busIndex /*in*/, int16 channel /*in*/,
int32 noteExpressionIndex /*in*/,
NoteExpressionTypeInfo& info /*out*/) = 0;
/** Gets a user readable representation of the normalized note change value. */
virtual tresult PLUGIN_API getNoteExpressionStringByValue (int32 busIndex, int16 channel, NoteExpressionTypeID id, NoteExpressionValue valueNormalized /*in*/, String128 string /*out*/) = 0;
/** Gets a user readable representation of the normalized note change value.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getNoteExpressionStringByValue (
int32 busIndex /*in*/, int16 channel /*in*/, NoteExpressionTypeID id /*in*/,
NoteExpressionValue valueNormalized /*in*/, String128 string /*out*/) = 0;
/** Converts the user readable representation to the normalized note change value. */
virtual tresult PLUGIN_API getNoteExpressionValueByString (int32 busIndex, int16 channel, NoteExpressionTypeID id, const TChar* string /*in*/, NoteExpressionValue& valueNormalized /*out*/) = 0;
/** Converts the user readable representation to the normalized note change value.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getNoteExpressionValueByString (
int32 busIndex /*in*/, int16 channel /*in*/, NoteExpressionTypeID id /*in*/,
const TChar* string /*in*/, NoteExpressionValue& valueNormalized /*out*/) = 0;
//------------------------------------------------------------------------
//------------------------------------------------------------------------
static const FUID iid;
};
@ -196,6 +210,7 @@ enum KeyswitchTypeIDs : uint32
kKeyRangeTypeID ///< key should be maintained pressed for playing
};
/** \ingroup vst3typedef */
typedef uint32 KeyswitchTypeID;
//------------------------------------------------------------------------
@ -227,20 +242,25 @@ struct KeyswitchInfo
- [released: 3.5.0]
- [optional]
When a (instrument) plug-in supports such interface, the host could get from the plug-in the current set
of used key switches (megatrig/articulation) for a given channel of a event bus and then automatically use them (like in Cubase 6) to
create VST Expression Map (allowing to associated symbol to a given articulation / key switch).
When a (instrument) plug-in supports such interface, the host could get from the plug-in the current
set of used key switches (megatrig/articulation) for a given channel of a event bus and then
automatically use them (like in Cubase 6) to create VST Expression Map (allowing to associated
symbol to a given articulation / key switch).
*/
class IKeyswitchController : public FUnknown
{
public:
/** Returns number of supported key switches for event bus index and channel. */
virtual int32 PLUGIN_API getKeyswitchCount (int32 busIndex, int16 channel) = 0;
/** Returns number of supported key switches for event bus index and channel.
* \note [UI-thread & Connected] */
virtual int32 PLUGIN_API getKeyswitchCount (int32 busIndex /*in*/, int16 channel /*in*/) = 0;
/** Returns key switch info. */
virtual tresult PLUGIN_API getKeyswitchInfo (int32 busIndex, int16 channel, int32 keySwitchIndex, KeyswitchInfo& info /*out*/) = 0;
/** Returns key switch info.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getKeyswitchInfo (int32 busIndex /*in*/, int16 channel /*in*/,
int32 keySwitchIndex /*in*/,
KeyswitchInfo& info /*out*/) = 0;
//------------------------------------------------------------------------
//------------------------------------------------------------------------
static const FUID iid;
};

View file

@ -92,10 +92,12 @@ public:
virtual int32 PLUGIN_API getPointCount () = 0;
/** Gets the value and offset at a given index. */
virtual tresult PLUGIN_API getPoint (int32 index, int32& sampleOffset /*out*/, ParamValue& value /*out*/) = 0;
virtual tresult PLUGIN_API getPoint (int32 index /*in*/, int32& sampleOffset /*out*/,
ParamValue& value /*out*/) = 0;
/** Adds a new value at the end of the queue, its index is returned. */
virtual tresult PLUGIN_API addPoint (int32 sampleOffset, ParamValue value, int32& index /*out*/) = 0;
virtual tresult PLUGIN_API addPoint (int32 sampleOffset /*in*/, ParamValue value /*in*/,
int32& index /*out*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
@ -124,11 +126,12 @@ public:
virtual int32 PLUGIN_API getParameterCount () = 0;
/** Returns the queue at a given index. */
virtual IParamValueQueue* PLUGIN_API getParameterData (int32 index) = 0;
virtual IParamValueQueue* PLUGIN_API getParameterData (int32 index /*in*/) = 0;
/** Adds a new parameter queue with a given ID at the end of the list,
returns it and its index in the parameter changes list. */
virtual IParamValueQueue* PLUGIN_API addParameterData (const ParamID& id, int32& index /*out*/) = 0;
virtual IParamValueQueue* PLUGIN_API addParameterData (const ParamID& id /*in*/,
int32& index /*out*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -73,28 +73,28 @@ controls, such as the wet-dry mix knob or Randomize button.
// here an example of how a VST3 plug-in could support this IParameterFunctionName interface.
// we need to define somewhere the iids:
in MyController class declaration
// in MyController class declaration
class MyController : public Vst::EditController, public Vst::IParameterFunctionName
{
...
// ...
tresult PLUGIN_API getParameterIDFromFunctionName (UnitID unitID, FIDString functionName,
Vst::ParamID& paramID) override;
...
Vst::ParamID& paramID) override;
// ...
OBJ_METHODS (MyController, Vst::EditController)
DEFINE_INTERFACES
...
// ...
DEF_INTERFACE (Vst::IParameterFunctionName)
END_DEFINE_INTERFACES (Vst::EditController)
DELEGATE_REFCOUNT (Vst::EditController)
...
// ...
}
#include "ivstparameterfunctionname.h"
namespace Steinberg {
namespace Vst {
DEF_CLASS_IID (IParameterFunctionName)
}
namespace Vst {
DEF_CLASS_IID (IParameterFunctionName)
}
}
//------------------------------------------------------------------------
@ -112,13 +112,13 @@ functionName, Vst::ParamID& paramID)
}
//--- a host implementation example: --------------------
...
// ...
FUnknownPtr<Vst::IParameterFunctionName> functionName (mEditController->getIEditController ());
if (functionName)
{
Vst::ParamID paramID;
if (functionName->getParameterIDFromFunctionName (kRootUnitId,
Vst::FunctionNameType::kCompGainReduction, paramID) == kResultTrue)
Vst::FunctionNameType::kCompGainReduction, paramID) == kResultTrue)
{
// paramID could be cached for performance issue
ParamValue norm = mEditController->getIEditController ()->getParamNormalized (paramID);
@ -131,12 +131,15 @@ if (functionName)
class IParameterFunctionName : public FUnknown
{
public:
//------------------------------------------------------------------------
//------------------------------------------------------------------------
/** Gets for the given unitID the associated paramID to a function Name.
Returns kResultFalse when no found parameter (paramID is set to kNoParamId in this case). */
virtual tresult PLUGIN_API getParameterIDFromFunctionName (UnitID unitID, FIDString functionName, ParamID& paramID) = 0;
* Returns kResultFalse when no found parameter (paramID is set to kNoParamId in this case).
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getParameterIDFromFunctionName (UnitID unitID /*in*/,
FIDString functionName /*in*/,
ParamID& paramID /*inout*/) = 0;
//------------------------------------------------------------------------
//------------------------------------------------------------------------
static const FUID iid;
};

View file

@ -27,12 +27,11 @@ namespace Steinberg {
namespace Vst {
//------------------------------------------------------------------------
/** \defgroup vst3typedef VST 3 Data Types */
/*@{*/
//------------------------------------------------------------------------
/** \ingroup vst3typedef */
/**@{*/
/** Physical UI Type */
typedef uint32 PhysicalUITypeID;
/*@}*/
/**@}*/
//------------------------------------------------------------------------
/** PhysicalUITypeIDs describes the type of Physical UI (PUI) which could be associated to a note
@ -150,9 +149,10 @@ class INoteExpressionPhysicalUIMapping : public FUnknown
{
public:
/** Fills the list of mapped [physical UI (in) - note expression (out)] for a given bus index
* and channel. */
virtual tresult PLUGIN_API getPhysicalUIMapping (int32 busIndex, int16 channel,
PhysicalUIMapList& list) = 0;
* and channel.
* \note [UI-thread & Connected] */
virtual tresult PLUGIN_API getPhysicalUIMapping (int32 busIndex /*in*/, int16 channel /*in*/,
PhysicalUIMapList& list /*inout*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -45,7 +45,8 @@ class IParameterFinder: public FUnknown
{
public:
//------------------------------------------------------------------------
/** Find out which parameter in plug-in view is at given position (relative to plug-in view). */
/** Find out which parameter in plug-in view is at given position (relative to plug-in view).
* \note [UI-thread & (Initialized | Connected) & plugView] */
virtual tresult PLUGIN_API findParameter (int32 xPos, int32 yPos, ParamID& resultTag /*out*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -28,12 +28,11 @@ namespace Steinberg {
namespace Vst {
// ------------------------------------------------------------------------
/** \defgroup vst3typedef VST 3 Data Types */
/*@{*/
//------------------------------------------------------------------------
/** \ingroup vst3typedef */
/**@{*/
/** Prefetchable Support Type */
typedef uint32 PrefetchableSupport;
/*@}*/
/**@}*/
/** Prefetchable Support Enum */
enum ePrefetchableSupport
@ -81,7 +80,8 @@ class IPrefetchableSupport : public FUnknown
public:
//------------------------------------------------------------------------
/** retrieve the current prefetch support. Use IComponentHandler::restartComponent
(kPrefetchableSupportChanged) to inform the host that this support has changed. */
* (kPrefetchableSupportChanged) to inform the host that this support has changed.
* \note [UI-thread & (Initialized | Connected | Setup Done | Activated | Processing)] */
virtual tresult PLUGIN_API getPrefetchableSupport (PrefetchableSupport& prefetchable /*out*/) = 0;
//------------------------------------------------------------------------

View file

@ -51,14 +51,16 @@ public:
* plug-ins).
* The retrieved paramID should match the one it replaces, maintaining the same
* behavior during automation playback. Called in UI-Thread context.
*
* @param[in] pluginToReplaceUID - TUID of plug-in (processor) that will be replaced
* @param[in] oldParamID - paramID (or index for VST 2 plug-ins) to be replaced
* @param[out] newParamID - contains the associated paramID to be used
*
* @return kResultTrue if a compatible parameter is available (newParamID has the appropriate
* value, it could be the same than oldParamID), or kResultFalse if no compatible parameter is
* available (newParamID is undefined)
*/
* available (newParamID is undefined).
*
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API getCompatibleParamID (const TUID pluginToReplaceUID /*in*/,
ParamID oldParamID /*in*/,
ParamID& newParamID /*out*/) = 0;
@ -68,7 +70,6 @@ public:
DECLARE_CLASS_IID (IRemapParamID, 0x2B88021E, 0x6286B646, 0xB49DF76A, 0x5663061C)
//------------------------------------------------------------------------
} // namespace Vst
} // namespace Steinberg

View file

@ -180,9 +180,10 @@ Here an example of what should be passed in the stream of getXmlRepresentationSt
class IXmlRepresentationController : public FUnknown
{
public:
/** Retrieves a stream containing a XmlRepresentation for a wanted representation info */
/** Retrieves a stream containing a XmlRepresentation for a wanted representation info.
* \note [UI-thread & Initialized] */
virtual tresult PLUGIN_API getXmlRepresentationStream (RepresentationInfo& info /*in*/,
IBStream* stream /*out*/) = 0;
IBStream* stream /*inout*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -53,7 +53,6 @@ namespace Vst {
* test (see ITest).
* You get this interface as the context argument in the ITestFactory::createTests method.
*/
//------------------------------------------------------------------------
class ITestPlugProvider : public FUnknown
{
public:
@ -71,12 +70,12 @@ public:
*/
virtual IEditController* PLUGIN_API getController () = 0;
/** release the component and/or controller */
virtual tresult PLUGIN_API releasePlugIn (IComponent* component,
IEditController* controller) = 0;
virtual tresult PLUGIN_API releasePlugIn (IComponent* component /*in*/,
IEditController* controller /*in*/) = 0;
/** get the sub categories of the plug-in */
virtual tresult PLUGIN_API getSubCategories (IStringResult& result) const = 0;
virtual tresult PLUGIN_API getSubCategories (IStringResult& result /*out*/) const = 0;
/** get the component UID of the plug-in */
virtual tresult PLUGIN_API getComponentUID (FUID& uid) const = 0;
virtual tresult PLUGIN_API getComponentUID (FUID& uid /*out*/) const = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -62,7 +62,7 @@ struct ProgramListInfo
//------------------------------------------------------------------------
/** Special programIndex value for IUnitHandler::notifyProgramListChange */
static const int32 kAllProgramInvalid = -1; ///< all program information is invalid
static const int32 kAllProgramInvalid = -1; ///< all program information is invalid
//------------------------------------------------------------------------
/** Host callback for unit support: Vst::IUnitHandler
@ -81,13 +81,19 @@ class IUnitHandler : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Notify host when a module is selected in plug-in GUI. */
/** Notify host when a module is selected in plug-in GUI.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API notifyUnitSelection (UnitID unitId) = 0;
/** Tell host that the plug-in controller changed a program list (rename, load, PitchName changes).
\param listId is the specified program list ID to inform.
\param programIndex : when kAllProgramInvalid, all program information is invalid, otherwise only the program of given index. */
virtual tresult PLUGIN_API notifyProgramListChange (ProgramListID listId, int32 programIndex) = 0;
/** Tell host that the plug-in controller changed a program list (rename, load, PitchName
* changes).
* \param listId is the specified program list ID to inform.
* \param programIndex: when kAllProgramInvalid, all program information is invalid, otherwise
* only the program of given index.
*
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API notifyProgramListChange (ProgramListID listId,
int32 programIndex) = 0;
//------------------------------------------------------------------------
static const FUID iid;
@ -116,7 +122,8 @@ class IUnitHandler2 : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Tell host that assignment Unit-Bus defined by IUnitInfo::getUnitByBus has changed. */
/** Tell host that assignment Unit-Bus defined by IUnitInfo::getUnitByBus has changed.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API notifyUnitByBusChange () = 0;
//------------------------------------------------------------------------
@ -145,52 +152,73 @@ class IUnitInfo : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Returns the flat count of units. */
/** Returns the flat count of units.
* \note [UI-thread & (Initialized | Connected)] */
virtual int32 PLUGIN_API getUnitCount () = 0;
/** Gets UnitInfo for a given index in the flat list of unit. */
virtual tresult PLUGIN_API getUnitInfo (int32 unitIndex, UnitInfo& info /*out*/) = 0;
/** Gets UnitInfo for a given index in the flat list of unit.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getUnitInfo (int32 unitIndex, UnitInfo& info /*inout*/) = 0;
/** Component intern program structure. */
/** Gets the count of Program List. */
//--- Component intern program structure ----------------
/** Gets the count of Program List.
* \note [UI-thread & (Initialized | Connected)] */
virtual int32 PLUGIN_API getProgramListCount () = 0;
/** Gets for a given index the Program List Info. */
virtual tresult PLUGIN_API getProgramListInfo (int32 listIndex, ProgramListInfo& info /*out*/) = 0;
/** Gets for a given index the Program List Info.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getProgramListInfo (int32 listIndex,
ProgramListInfo& info /*inout*/) = 0;
/** Gets for a given program list ID and program index its program name. */
virtual tresult PLUGIN_API getProgramName (ProgramListID listId, int32 programIndex, String128 name /*out*/) = 0;
/** Gets for a given program list ID and program index its program name.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getProgramName (ProgramListID listId, int32 programIndex,
String128 name /*inout*/) = 0;
/** Gets for a given program list ID, program index and attributeId the associated attribute value. */
/** Gets for a given program list ID, program index and attributeId the associated attribute
* value.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getProgramInfo (ProgramListID listId, int32 programIndex,
CString attributeId /*in*/, String128 attributeValue /*out*/) = 0;
CString attributeId /*in*/,
String128 attributeValue /*inout*/) = 0;
/** Returns kResultTrue if the given program index of a given program list ID supports PitchNames. */
/** Returns kResultTrue if the given program index of a given program list ID supports
* PitchNames.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API hasProgramPitchNames (ProgramListID listId, int32 programIndex) = 0;
/** Gets the PitchName for a given program list ID, program index and pitch.
If PitchNames are changed the plug-in should inform the host with IUnitHandler::notifyProgramListChange. */
* If PitchNames are changed the plug-in should inform the host with
* IUnitHandler::notifyProgramListChange.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getProgramPitchName (ProgramListID listId, int32 programIndex,
int16 midiPitch, String128 name /*out*/) = 0;
int16 midiPitch, String128 name /*inout*/) = 0;
// units selection --------------------
/** Gets the current selected unit. */
//--- units selection --------------------
/** Gets the current selected unit.
* \note [UI-thread & (Initialized | Connected)] */
virtual UnitID PLUGIN_API getSelectedUnit () = 0;
/** Sets a new selected unit. */
/** Sets a new selected unit.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API selectUnit (UnitID unitId) = 0;
/** Gets the according unit if there is an unambiguous relation between a channel or a bus and a unit.
This method mainly is intended to find out which unit is related to a given MIDI input channel. */
/** Gets the according unit if there is an unambiguous relation between a channel or a bus and a
* unit. This method mainly is intended to find out which unit is related to a given MIDI input
* channel.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getUnitByBus (MediaType type, BusDirection dir, int32 busIndex,
int32 channel, UnitID& unitId /*out*/) = 0;
int32 channel, UnitID& unitId /*inout*/) = 0;
/** Receives a preset data stream.
- If the component supports program list data (IProgramListData), the destination of the data
stream is the program specified by list-Id and program index (first and second parameter)
- If the component supports unit data (IUnitData), the destination is the unit specified by the first
parameter - in this case parameter programIndex is < 0). */
virtual tresult PLUGIN_API setUnitProgramData (int32 listOrUnitId, int32 programIndex, IBStream* data) = 0;
* - If the component supports program list data (IProgramListData), the destination of the data
* stream is the program specified by list-Id and program index (first and second parameter)
* - If the component supports unit data (IUnitData), the destination is the unit specified by
* the first parameter - in this case parameter programIndex is < 0).
*
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API setUnitProgramData (int32 listOrUnitId, int32 programIndex,
IBStream* data /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
@ -215,14 +243,19 @@ class IProgramListData : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Returns kResultTrue if the given Program List ID supports Program Data. */
/** Returns kResultTrue if the given Program List ID supports Program Data.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API programDataSupported (ProgramListID listId) = 0;
/** Gets for a given program list ID and program index the program Data. */
virtual tresult PLUGIN_API getProgramData (ProgramListID listId, int32 programIndex, IBStream* data) = 0;
/** Gets for a given program list ID and program index the program Data.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getProgramData (ProgramListID listId, int32 programIndex,
IBStream* data /*inout*/) = 0;
/** Sets for a given program list ID and program index a program Data. */
virtual tresult PLUGIN_API setProgramData (ProgramListID listId, int32 programIndex, IBStream* data) = 0;
/** Sets for a given program list ID and program index a program Data.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API setProgramData (ProgramListID listId, int32 programIndex,
IBStream* data /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;
@ -247,14 +280,17 @@ class IUnitData : public FUnknown
{
public:
//------------------------------------------------------------------------
/** Returns kResultTrue if the specified unit supports export and import of preset data. */
/** Returns kResultTrue if the specified unit supports export and import of preset data.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API unitDataSupported (UnitID unitID) = 0;
/** Gets the preset data for the specified unit. */
virtual tresult PLUGIN_API getUnitData (UnitID unitId, IBStream* data) = 0;
/** Gets the preset data for the specified unit.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API getUnitData (UnitID unitId, IBStream* data /*inout*/) = 0;
/** Sets the preset data for the specified unit. */
virtual tresult PLUGIN_API setUnitData (UnitID unitId, IBStream* data) = 0;
/** Sets the preset data for the specified unit.
* \note [UI-thread & (Initialized | Connected)] */
virtual tresult PLUGIN_API setUnitData (UnitID unitId, IBStream* data /*in*/) = 0;
//------------------------------------------------------------------------
static const FUID iid;

View file

@ -35,8 +35,8 @@ const SpeakerArrangement kStereo = kSpeakerL | kSpeakerR; // => hex: 0x03 / bina
//------------------------------------------------------------------------
/** Speaker Definitions.
\ingroup speakerArrangements */
//------------------------------------------------------------------------
* \ingroup speakerArrangements
*/
/**@{*/
const Speaker kSpeakerL = 1 << 0; ///< Left (L)
const Speaker kSpeakerR = 1 << 1; ///< Right (R)
@ -115,9 +115,10 @@ namespace SpeakerArr
{
//------------------------------------------------------------------------
/** Speaker Arrangement Definitions.
* for example: 5.0.5.3 for 5x Middle + 0x LFE + 5x Top + 3x Bottom
\ingroup speakerArrangements */
/*@{*/
* for example: 5.0.5.3 for 5x Middle + 0x LFE + 5x Top + 3x Bottom
* \ingroup speakerArrangements
*/
/**@{*/
const SpeakerArrangement kEmpty = 0; ///< empty arrangement
const SpeakerArrangement kMono = kSpeakerM; ///< M
const SpeakerArrangement kStereo = kSpeakerL | kSpeakerR; ///< L R
@ -443,8 +444,9 @@ const SpeakerArrangement k50_4_4 = kSpeakerL | kSpeakerR | kSpeakerC | kSpeakerL
//------------------------------------------------------------------------
/** Speaker Arrangement String Representation.
\ingroup speakerArrangements */
/*@{*/
* \ingroup speakerArrangements
*/
/**@{*/
const CString kStringEmpty = "";
const CString kStringMono = "Mono";
const CString kStringStereo = "Stereo";
@ -552,12 +554,13 @@ const CString kStringAmbi4thOrder = "4OA";
const CString kStringAmbi5thOrder = "5OA";
const CString kStringAmbi6thOrder = "6OA";
const CString kStringAmbi7thOrder = "7OA";
/*@}*/
/**@}*/
//------------------------------------------------------------------------
/** Speaker Arrangement String Representation with Speakers Name.
\ingroup speakerArrangements */
/*@{*/
* \ingroup speakerArrangements
*/
/**@{*/
const CString kStringMonoS = "M";
const CString kStringStereoS = "L R";
const CString kStringStereoWideS = "Lw Rw";
@ -659,12 +662,13 @@ const CString kStringAmbi4thOrderS = "0..24";
const CString kStringAmbi5thOrderS = "0..35";
const CString kStringAmbi6thOrderS = "0..48";
const CString kStringAmbi7thOrderS = "0..63";
/*@}*/
/**@}*/
//------------------------------------------------------------------------
/** Returns number of channels used in speaker arrangement.
\ingroup speakerArrangements */
/*@{*/
* \ingroup speakerArrangements
*/
/**@{*/
inline int32 getChannelCount (SpeakerArrangement arr)
{
int32 count = 0;
@ -679,7 +683,9 @@ inline int32 getChannelCount (SpeakerArrangement arr)
//------------------------------------------------------------------------
/** Returns the index of a given speaker in a speaker arrangement (-1 if speaker is not part of the
* arrangement). */
* arrangement).
* \ingroup speakerArrangements
*/
inline int32 getSpeakerIndex (Speaker speaker, SpeakerArrangement arrangement)
{
// check if speaker is present in arrangement
@ -699,7 +705,10 @@ inline int32 getSpeakerIndex (Speaker speaker, SpeakerArrangement arrangement)
}
//------------------------------------------------------------------------
/** Returns the speaker for a given index in a speaker arrangement (return 0 when out of range). */
/** Returns the speaker for a given index in a speaker arrangement
* Return 0 when out of range.
* \ingroup speakerArrangements
*/
inline Speaker getSpeaker (const SpeakerArrangement& arr, int32 index)
{
SpeakerArrangement arrTmp = arr;
@ -713,7 +722,7 @@ inline Speaker getSpeaker (const SpeakerArrangement& arr, int32 index)
pos++;
if (index2 == index)
return (Speaker)1 << pos;
arrTmp = arrTmp >> 1;
}
return 0;
@ -721,14 +730,18 @@ inline Speaker getSpeaker (const SpeakerArrangement& arr, int32 index)
//------------------------------------------------------------------------
/** Returns true if arrSubSet is a subset speaker of arr (means each speaker of arrSubSet is
* included in arr). */
* included in arr).
* \ingroup speakerArrangements
*/
inline bool isSubsetOf (const SpeakerArrangement& arrSubSet, const SpeakerArrangement& arr)
{
return (arrSubSet == (arrSubSet & arr));
}
//------------------------------------------------------------------------
/** Returns true if arrangement is a Auro configuration. */
/** Returns true if arrangement is a Auro configuration.
* \ingroup speakerArrangements
*/
inline bool isAuro (const SpeakerArrangement& arr)
{
if (arr == k90 || arr == k91 || arr == k100 || arr == k101 || arr == k110 || arr == k111 ||
@ -740,7 +753,9 @@ inline bool isAuro (const SpeakerArrangement& arr)
}
//------------------------------------------------------------------------
/** Returns true if arrangement contains top (upper layer) speakers */
/** Returns true if arrangement contains top (upper layer) speakers
* \ingroup speakerArrangements
*/
inline bool hasTopSpeakers (const SpeakerArrangement& arr)
{
if (arr & kSpeakerTc || arr & kSpeakerTfl || arr & kSpeakerTfc || arr & kSpeakerTfr ||
@ -751,18 +766,21 @@ inline bool hasTopSpeakers (const SpeakerArrangement& arr)
}
//------------------------------------------------------------------------
/** Returns true if arrangement contains bottom (lower layer) speakers */
/** Returns true if arrangement contains bottom (lower layer) speakers
* \ingroup speakerArrangements
*/
inline bool hasBottomSpeakers (const SpeakerArrangement& arr)
{
if (arr & kSpeakerBfl || arr & kSpeakerBfc || arr & kSpeakerBfr ||
arr & kSpeakerBsl || arr & kSpeakerBsr ||
arr & kSpeakerBrr || arr & kSpeakerBrl || arr & kSpeakerBrc)
if (arr & kSpeakerBfl || arr & kSpeakerBfc || arr & kSpeakerBfr || arr & kSpeakerBsl ||
arr & kSpeakerBsr || arr & kSpeakerBrr || arr & kSpeakerBrl || arr & kSpeakerBrc)
return true;
return false;
}
//------------------------------------------------------------------------
/** Returns true if arrangement contains middle layer (at ears level) speakers */
/** Returns true if arrangement contains middle layer (at ears level) speakers
* \ingroup speakerArrangements
*/
inline bool hasMiddleSpeakers (const SpeakerArrangement& arr)
{
if (arr & kSpeakerL || arr & kSpeakerR || arr & kSpeakerC || arr & kSpeakerLs ||
@ -775,7 +793,9 @@ inline bool hasMiddleSpeakers (const SpeakerArrangement& arr)
}
//------------------------------------------------------------------------
/** Returns true if arrangement contains LFE speakers */
/** Returns true if arrangement contains LFE speakers
* \ingroup speakerArrangements
*/
inline bool hasLfe (const SpeakerArrangement& arr)
{
if (arr & kSpeakerLfe || arr & kSpeakerLfe2)
@ -784,7 +804,9 @@ inline bool hasLfe (const SpeakerArrangement& arr)
}
//------------------------------------------------------------------------
/** Returns true if arrangement is a 3D configuration ((top or bottom) and middle) */
/** Returns true if arrangement is a 3D configuration ((top or bottom) and middle)
* \ingroup speakerArrangements
*/
inline bool is3D (const SpeakerArrangement& arr)
{
bool top = hasTopSpeakers (arr);
@ -797,7 +819,9 @@ inline bool is3D (const SpeakerArrangement& arr)
}
//------------------------------------------------------------------------
/** Returns true if arrangement is a Ambisonic configuration. */
/** Returns true if arrangement is a Ambisonic configuration.
* \ingroup speakerArrangements
*/
inline bool isAmbisonics (const SpeakerArrangement& arr)
{
if (arr == kAmbi1stOrderACN || arr == kAmbi2cdOrderACN || arr == kAmbi3rdOrderACN ||
@ -809,9 +833,11 @@ inline bool isAmbisonics (const SpeakerArrangement& arr)
return false;
}
//------------------------------------------------------------------------
/** Converts a speaker of a Ambisonic order 1 to 4 to a Ambisonic order 7 (5 to 7) (return 0 when out of range).*/
/** Converts a speaker of a Ambisonic order 1 to 4 to a Ambisonic order 7 (5 to 7)
* Return 0 when out of range.
* \ingroup speakerArrangements
*/
inline Speaker convertSpeaker_Ambi_1234Order_to_Ambi567Order (Speaker speaker_1234_order)
{
int32 idx = getSpeakerIndex (speaker_1234_order, kAmbi4thOrderACN);
@ -821,7 +847,10 @@ inline Speaker convertSpeaker_Ambi_1234Order_to_Ambi567Order (Speaker speaker_12
}
//------------------------------------------------------------------------
/** Converts a speaker of a Ambisonic order 5 to 7 to a Ambisonic order 4 (1 to 4) (return 0 when out of range).*/
/** Converts a speaker of a Ambisonic order 5 to 7 to a Ambisonic order 4 (1 to 4).
* Return 0 when out of range.
* \ingroup speakerArrangements
*/
inline Speaker convertSpeaker_Ambi_567Order_to_Ambi1234Order (Speaker speaker_567_order)
{
int32 idx = getSpeakerIndex (speaker_567_order, kAmbi7thOrderACN);
@ -832,7 +861,9 @@ inline Speaker convertSpeaker_Ambi_567Order_to_Ambi1234Order (Speaker speaker_56
//------------------------------------------------------------------------
/** Returns the speaker arrangement associated to a string representation.
Returns kEmpty if no associated arrangement is known. */
* Returns kEmpty if no associated arrangement is known.
* \ingroup speakerArrangements
*/
inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
{
if (!strcmp8 (arrStr, kStringMono))
@ -858,7 +889,7 @@ inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
if (!strcmp8 (arrStr, kStringStereoBF))
return kStereoBF;
if (!strcmp8 (arrStr, kStringCineFront))
return kCineFront;
return kCineFront;
if (!strcmp8 (arrStr, kString30Cine))
return k30Cine;
if (!strcmp8 (arrStr, kString30Music))
@ -916,7 +947,7 @@ inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
if (!strcmp8 (arrStr, kString71CineCenterHigh))
return k71CineCenterHigh;
if (!strcmp8 (arrStr, kString50_2))
return k50_2;
return k50_2;
if (!strcmp8 (arrStr, kString51_2))
return k51_2;
if (!strcmp8 (arrStr, kString50_2TopSide))
@ -926,11 +957,11 @@ inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
if (!strcmp8 (arrStr, kString71CineFullRear))
return k71CineFullRear;
if (!strcmp8 (arrStr, kString90Cine))
return k90Cine;
return k90Cine;
if (!strcmp8 (arrStr, kString91Cine))
return k91Cine;
if (!strcmp8 (arrStr, kString100Cine))
return k100Cine;
return k100Cine;
if (!strcmp8 (arrStr, kString101Cine))
return k101Cine;
if (!strcmp8 (arrStr, kString50_4))
@ -944,7 +975,7 @@ inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
if (!strcmp8 (arrStr, kString41_4_1))
return k41_4_1;
if (!strcmp8 (arrStr, kString70_2))
return k70_2;
return k70_2;
if (!strcmp8 (arrStr, kString71_2))
return k71_2;
if (!strcmp8 (arrStr, kString70_2_TF))
@ -964,7 +995,7 @@ inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
if (!strcmp8 (arrStr, kString71_6))
return k71_6;
if (!strcmp8 (arrStr, kString90_4))
return k90_4;
return k90_4;
if (!strcmp8 (arrStr, kString91_4))
return k91_4;
if (!strcmp8 (arrStr, kString90_6))
@ -1006,7 +1037,7 @@ inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
if (!strcmp8 (arrStr, kString50_4_2))
return k50_4_2;
if (!strcmp8 (arrStr, kString70_4_2))
return k70_4_2;
return k70_4_2;
if (!strcmp8 (arrStr, kString50_5_Sony))
return k50_5_Sony;
@ -1042,7 +1073,9 @@ inline SpeakerArrangement getSpeakerArrangementFromString (CString arrStr)
//------------------------------------------------------------------------
/** Returns the string representation of a given speaker arrangement.
Returns kStringEmpty if arr is unknown. */
* Returns kStringEmpty if arr is unknown.
* \ingroup speakerArrangements
*/
inline CString getSpeakerArrangementString (SpeakerArrangement arr, bool withSpeakersName)
{
switch (arr)
@ -1170,7 +1203,9 @@ inline CString getSpeakerArrangementString (SpeakerArrangement arr, bool withSpe
}
//------------------------------------------------------------------------
/** Returns a CString representation of a given speaker in a given arrangement */
/** Returns a CString representation of a given speaker in a given arrangement.
* \ingroup speakerArrangements
*/
inline CString getSpeakerShortName (const SpeakerArrangement& arr, int32 index)
{
SpeakerArrangement arrTmp = arr;
@ -1324,7 +1359,7 @@ inline CString getSpeakerShortName (const SpeakerArrangement& arr, int32 index)
return "";
}
/*@}*/
/**@}*/
//------------------------------------------------------------------------
} // namespace SpeakerArr

View file

@ -24,17 +24,19 @@ namespace Vst {
//------------------------------------------------------------------------
/** VST 3 SDK Version */
#ifndef kVstVersionString
#define kVstVersionString "VST 3.7.12" ///< SDK version for PClassInfo2
#define kVstVersionString "VST 3.7.14" ///< SDK version for PClassInfo2
#endif
#define kVstVersionMajor 3
#define kVstVersionMinor 7
#define kVstVersionSub 12
#define kVstVersionSub 14
#define VST_VERSION ((kVstVersionMajor << 16) | (kVstVersionMinor << 8) | kVstVersionSub)
// Versions History which allows to write such code:
// #if VST_VERSION >= VST_3_6_5_VERSION
#define VST_3_7_14_VERSION 0x03070E
#define VST_3_7_13_VERSION 0x03070D
#define VST_3_7_12_VERSION 0x03070C
#define VST_3_7_11_VERSION 0x03070B
#define VST_3_7_10_VERSION 0x03070A
@ -64,8 +66,10 @@ namespace Vst {
#define VST_3_0_0_VERSION 0x030000
//------------------------------------------------------------------------
/** \defgroup vst3typedef VST 3 Data Types */
/*@{*/
/** \defgroup vst3typedef VST 3 Data Types
* Data Types defined by VST 3
*/
/**@{*/
//------------------------------------------------------------------------
// String Types
//------------------------------------------------------------------------
@ -112,7 +116,7 @@ typedef double SampleRate; ///< sample rate
typedef uint64 SpeakerArrangement; ///< Bitset of speakers
typedef uint64 Speaker; ///< Bit for one speaker
/*@}*/
/**@}*/
static SMTG_CONSTEXPR const FIDString SDKVersionString = kVstVersionString;
@ -125,6 +129,8 @@ static SMTG_CONSTEXPR const uint32 SDKVersion =
// Versions History which allows to write such code:
// if constexpr (SDKVersion >= SDKVersion_3_6_5) { ... }
static SMTG_CONSTEXPR const uint32 SDKVersion_3_7_14 = VST_3_7_14_VERSION;
static SMTG_CONSTEXPR const uint32 SDKVersion_3_7_13 = VST_3_7_13_VERSION;
static SMTG_CONSTEXPR const uint32 SDKVersion_3_7_12 = VST_3_7_12_VERSION;
static SMTG_CONSTEXPR const uint32 SDKVersion_3_7_11 = VST_3_7_11_VERSION;
static SMTG_CONSTEXPR const uint32 SDKVersion_3_7_10 = VST_3_7_10_VERSION;
@ -156,4 +162,3 @@ static SMTG_CONSTEXPR const uint32 SDKVersion_3_0_0 = VST_3_0_0_VERSION;
//------------------------------------------------------------------------
} // namespace Vst
} // namespace Steinberg

View file

@ -53,8 +53,7 @@ HostApplication::HostApplication ()
//-----------------------------------------------------------------------------
tresult PLUGIN_API HostApplication::getName (String128 name)
{
return StringConvert::convert ("My VST3 HostApplication", name) ? kResultTrue :
kInternalError;
return StringConvert::convert ("My VST3 HostApplication", name) ? kResultTrue : kInternalError;
}
//-----------------------------------------------------------------------------
@ -86,7 +85,7 @@ tresult PLUGIN_API HostApplication::queryInterface (const char* _iid, void** obj
QUERY_INTERFACE (_iid, obj, FUnknown::iid, IHostApplication)
QUERY_INTERFACE (_iid, obj, IHostApplication::iid, IHostApplication)
if (mPlugInterfaceSupport && mPlugInterfaceSupport->queryInterface (iid, obj) == kResultTrue)
if (mPlugInterfaceSupport && mPlugInterfaceSupport->queryInterface (_iid, obj) == kResultTrue)
return kResultOk;
*obj = nullptr;
@ -176,8 +175,8 @@ struct HostAttributeList::Attribute
v.binaryValue = new char[sizeInBytes];
memcpy (v.binaryValue, value, sizeInBytes);
}
Attribute (Attribute&& o) { *this = std::move (o); }
Attribute& operator= (Attribute&& o)
Attribute (Attribute&& o) SMTG_NOEXCEPT { *this = std::move (o); }
Attribute& operator= (Attribute&& o) SMTG_NOEXCEPT
{
v = o.v;
size = o.size;
@ -216,7 +215,7 @@ private:
double floatValue;
TChar* stringValue;
char* binaryValue;
} v;
} v {};
uint32 size {0};
Type type {Type::kUninitialized};
};
@ -236,10 +235,7 @@ IPtr<IAttributeList> HostAttributeList::make ()
HostAttributeList::HostAttributeList () {FUNKNOWN_CTOR}
//-----------------------------------------------------------------------------
HostAttributeList::~HostAttributeList () noexcept
{
FUNKNOWN_DTOR
}
HostAttributeList::~HostAttributeList () noexcept {FUNKNOWN_DTOR}
//-----------------------------------------------------------------------------
tresult PLUGIN_API HostAttributeList::setInt (AttrID aid, int64 value)
@ -338,5 +334,6 @@ tresult PLUGIN_API HostAttributeList::getBinary (AttrID aid, const void*& data,
return kResultFalse;
}
} // Vst
} // Steinberg
//------------------------------------------------------------------------
} // namespace Vst
} // namespace Steinberg

View file

@ -182,6 +182,8 @@ public:
static SnapshotList getSnapshots (const std::string& modulePath);
/** get the path to the module info json file if it exists */
static Optional<std::string> getModuleInfoPath (const std::string& modulePath);
/** validate the bundle structure */
static bool validateBundleStructure (const std::string& path, std::string& errorDescription);
const std::string& getName () const noexcept { return name; }
const std::string& getPath () const noexcept { return path; }

View file

@ -167,8 +167,8 @@ public:
if (!filesystem::is_directory (modulePath))
return {};
stem.replace_extension (".so");
modulePath /= stem;
modulePath += ".so";
return Optional<Path> (std::move (modulePath));
}
@ -367,6 +367,45 @@ Optional<std::string> Module::getModuleInfoPath (const std::string& modulePath)
return {};
}
//------------------------------------------------------------------------
bool Module::validateBundleStructure (const std::string& modulePath, std::string& errorDescription)
{
filesystem::path path (modulePath);
auto moduleName = path.filename ();
path /= "Contents";
if (filesystem::exists (path) == false)
{
errorDescription = "Expecting 'Contents' as first subfolder.";
return false;
}
auto machine = getCurrentMachineName ();
if (!machine)
{
errorDescription = "Could not get the current machine name.";
return false;
}
path /= *machine + "-linux";
if (filesystem::exists (path) == false)
{
errorDescription = "Expecting '" + *machine + "-linux' as architecture subfolder.";
return false;
}
moduleName.replace_extension (".so");
path /= moduleName;
if (filesystem::exists (path) == false)
{
errorDescription = "Shared library name is not equal to bundle folder name. Must be '" +
moduleName.string () + "'.";
return false;
}
return true;
}
//------------------------------------------------------------------------
} // Hosting
} // VST3

View file

@ -8,7 +8,7 @@
//
//-----------------------------------------------------------------------------
// LICENSE
// (c) 2024, Steinberg Media Technologies GmbH, All Rights Reserved
// (c) 2025, Steinberg Media Technologies GmbH, All Rights Reserved
//-----------------------------------------------------------------------------
// Redistribution and use in source and binary forms, with or without modification,
// are permitted provided that the following conditions are met:
@ -176,12 +176,13 @@ public:
namespace StringConvert = Steinberg::Vst::StringConvert;
filesystem::path p (inPath);
auto filename = p.filename ();
p /= "Contents";
p /= archString;
p /= filename;
auto wideStr = StringConvert::convert (p.string ());
HINSTANCE instance = LoadLibraryW (reinterpret_cast<LPCWSTR> (wideStr.data ()));
const std::wstring wString = p.generic_wstring ();
HINSTANCE instance = LoadLibraryW (reinterpret_cast<LPCWSTR> (wString.data ()));
#if SMTG_CPU_ARM_64EC
if (instance == nullptr)
instance = loadAsPackage (inPath, errorDescription, architectureArm64XString);
@ -214,7 +215,7 @@ public:
//--- -----------------------------------------------------------------------
bool load (const std::string& inPath, std::string& errorDescription) override
{
// filesystem::u8path is deprecated in C++20
// filesystem::u8path is deprecated in C++20
#if SMTG_CPP20
const filesystem::path tmp (inPath);
#else
@ -288,7 +289,8 @@ bool openVST3Package (const filesystem::path& p, const char* archString,
path /= "Contents";
path /= archString;
path /= p.filename ();
auto hFile = CreateFileW (reinterpret_cast<LPCWSTR> (path.c_str ()), GENERIC_READ,
const std::wstring wString = path.generic_wstring ();
auto hFile = CreateFileW (reinterpret_cast<LPCWSTR> (wString.data ()), GENERIC_READ,
FILE_SHARE_READ, nullptr, OPEN_EXISTING, 0, nullptr);
if (hFile != INVALID_HANDLE_VALUE)
{
@ -323,11 +325,11 @@ bool isFolderSymbolicLink (const filesystem::path& p)
if (/*filesystem::exists (p) &&*/ filesystem::is_symlink (p))
return true;
#else
std::wstring wString = p.generic_wstring ();
auto attrib = GetFileAttributesW (reinterpret_cast<LPCWSTR> (wString.c_str ()));
const std::wstring wString = p.generic_wstring ();
auto attrib = GetFileAttributesW (reinterpret_cast<LPCWSTR> (wString.data ()));
if (attrib & FILE_ATTRIBUTE_REPARSE_POINT)
{
auto hFile = CreateFileW (reinterpret_cast<LPCWSTR> (wString.c_str ()), GENERIC_READ,
auto hFile = CreateFileW (reinterpret_cast<LPCWSTR> (wString.data ()), GENERIC_READ,
FILE_SHARE_READ, nullptr, OPEN_EXISTING, 0, nullptr);
if (hFile == INVALID_HANDLE_VALUE)
return true;
@ -428,7 +430,14 @@ void findFilesWithExt (const filesystem::path& path, const std::string& ext,
filesystem::path result;
if (checkVST3Package (finalPath, &result))
{
addToPathList (pathList, result.generic_string ());
#if SMTG_CPP20
std::u8string u8str = result.generic_u8string ();
std::string str;
str.assign (std::begin (u8str), std::end (u8str));
addToPathList (pathList, str);
#else
addToPathList (pathList, result.generic_u8string ());
#endif
continue;
}
}
@ -439,7 +448,16 @@ void findFilesWithExt (const filesystem::path& path, const std::string& ext,
findFilesWithExt (finalPath, ext, pathList, recursive);
}
else if (cpExt == ext)
addToPathList (pathList, finalPath.generic_string ());
{
#if SMTG_CPP20
std::u8string u8str = finalPath.generic_u8string ();
std::string str;
str.assign (std::begin (u8str), std::end (u8str));
addToPathList (pathList, str);
#else
addToPathList (pathList, finalPath.generic_u8string ());
#endif
}
#else
const auto& cp = p.path ();
const auto& cpExt = cp.extension ();
@ -510,7 +528,12 @@ void findModules (const filesystem::path& path, Module::PathList& pathList)
Optional<filesystem::path> getContentsDirectoryFromModuleExecutablePath (
const std::string& modulePath)
{
// filesystem::u8path is deprecated in C++20
#if SMTG_CPP20
filesystem::path path (modulePath);
#else
filesystem::path path = filesystem::u8path (modulePath);
#endif
path = path.parent_path ();
if (path.filename () != architectureString)
@ -550,7 +573,12 @@ Module::PathList Module::getModulePaths ()
PathList list;
if (auto knownFolder = getKnownFolder (FOLDERID_UserProgramFilesCommon))
{
// filesystem::u8path is deprecated in C++20
#if SMTG_CPP20
filesystem::path path (*knownFolder);
#else
filesystem::path path = filesystem::u8path (*knownFolder);
#endif
path.append ("VST3");
#if LOG_ENABLE
std::cout << "Check folder: " << path << "\n";
@ -560,7 +588,12 @@ Module::PathList Module::getModulePaths ()
if (auto knownFolder = getKnownFolder (FOLDERID_ProgramFilesCommon))
{
// filesystem::u8path is deprecated in C++20
#if SMTG_CPP20
filesystem::path path (*knownFolder);
#else
filesystem::path path = filesystem::u8path (*knownFolder);
#endif
path.append ("VST3");
#if LOG_ENABLE
std::cout << "Check folder: " << path << "\n";
@ -572,7 +605,13 @@ Module::PathList Module::getModulePaths ()
WCHAR modulePath[kIPPathNameMax];
GetModuleFileNameW (nullptr, modulePath, kIPPathNameMax);
auto appPath = StringConvert::convert (Steinberg::wscast (modulePath));
// filesystem::u8path is deprecated in C++20
#if SMTG_CPP20
filesystem::path path (appPath);
#else
filesystem::path path = filesystem::u8path (appPath);
#endif
path = path.parent_path ();
path = path.append ("VST3");
#if LOG_ENABLE
@ -607,6 +646,48 @@ Optional<std::string> Module::getModuleInfoPath (const std::string& modulePath)
return {};
}
//------------------------------------------------------------------------
bool Module::validateBundleStructure (const std::string& modulePath, std::string& errorDescription)
{
try
{
auto path = getContentsDirectoryFromModuleExecutablePath (modulePath);
if (!path)
{
filesystem::path p;
if (!checkVST3Package ({modulePath}, &p))
{
errorDescription = "Not a bundle: '" + modulePath + "'.";
return false;
}
p = p.parent_path ();
p = p.parent_path ();
path = Optional<filesystem::path> {p};
}
if (path->filename () != "Contents")
{
errorDescription = "Unexpected directory name, should be 'Contents' but is '" +
path->filename ().string () + "'.";
return false;
}
auto bundlePath = path->parent_path ();
*path /= architectureString;
*path /= bundlePath.filename ();
if (std::filesystem::exists (*path) == false)
{
errorDescription = "Shared library name is not equal to bundle folder name. Must be '" +
bundlePath.filename ().string () + "'.";
return false;
}
return true;
}
catch (const std::exception& exc)
{
errorDescription = exc.what ();
return false;
}
}
//------------------------------------------------------------------------
Module::SnapshotList Module::getSnapshots (const std::string& modulePath)
{
@ -632,7 +713,12 @@ Module::SnapshotList Module::getSnapshots (const std::string& modulePath)
findFilesWithExt (*path, ".png", pngList, false);
for (auto& png : pngList)
{
filesystem::path p (png);
// filesystem::u8path is deprecated in C++20
#if SMTG_CPP20
const filesystem::path p (png);
#else
const filesystem::path p = filesystem::u8path (png);
#endif
auto filename = p.filename ().generic_string ();
auto uid = Snapshot::decodeUID (filename);
if (!uid)

View file

@ -41,7 +41,7 @@
#include "pluginterfaces/vst/ivstaudioprocessor.h"
#include <string>
#if SMTG_CPP_17
#if defined(SMTG_CPP_17) && SMTG_CPP_17
#include <string_view>
#endif
#include <vector>
@ -67,7 +67,7 @@ public:
/** Activates the bus. */
void setActive (TBool state) { active = state; }
#if SMTG_CPP_17
#if defined(SMTG_CPP_17) && SMTG_CPP_17
/** Sets a new name for this bus. */
void setName (std::u16string_view newName) { name = newName; }
#else

View file

@ -12,24 +12,24 @@
//-----------------------------------------------------------------------------
// Redistribution and use in source and binary forms, with or without modification,
// are permitted provided that the following conditions are met:
//
// * Redistributions of source code must retain the above copyright notice,
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
// * Neither the name of the Steinberg Media Technologies nor the names of its
// contributors may be used to endorse or promote products derived from this
// contributors may be used to endorse or promote products derived from this
// software without specific prior written permission.
//
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
// INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
// INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
// OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
// OF THE POSSIBILITY OF SUCH DAMAGE.
//-----------------------------------------------------------------------------
@ -212,5 +212,7 @@ tresult getSpeakerChannelIndex (SpeakerArrangement arrangement, uint64 speaker,
channel = SpeakerArr::getSpeakerIndex (speaker, arrangement);
return (channel < 0) == true ? kResultFalse : kResultTrue;
}
//------------------------------------------------------------------------
} // namespace Vst
} // namespace Steinberg

View file

@ -514,7 +514,7 @@ void Unit::setName (const String128 newName)
// ProgramList implementation
//------------------------------------------------------------------------
ProgramList::ProgramList (const String128 name, ProgramListID listId, UnitID unitId)
: unitId (unitId), parameter (nullptr)
: unitId (unitId)
{
UString128 (name).copyTo (info.name, 128);
info.id = listId;
@ -526,7 +526,6 @@ ProgramList::ProgramList (const ProgramList& programList)
: info (programList.info)
, unitId (programList.unitId)
, programNames (programList.programNames)
, parameter (nullptr)
{
}
@ -536,9 +535,28 @@ int32 ProgramList::addProgram (const String128 name)
++info.programCount;
programNames.emplace_back (name);
programInfos.emplace_back ();
if (parameter)
{
static_cast<StringListParameter*> (parameter)->appendString (name);
}
return static_cast<int32> (programNames.size ()) - 1;
}
//------------------------------------------------------------------------
void ProgramList::clearPrograms ()
{
info.programCount = 0;
programNames.clear ();
programInfos.clear ();
if (parameter)
{
static_cast<StringListParameter*> (parameter)->clear ();
}
}
//------------------------------------------------------------------------
bool ProgramList::setProgramInfo (int32 programIndex, CString attributeId, const String128 value)
{

View file

@ -238,17 +238,20 @@ public:
/** Creates and returns the program parameter. */
virtual Parameter* getParameter ();
/** Clear all programs. */
virtual void clearPrograms ();
OBJ_METHODS (ProgramList, FObject)
//------------------------------------------------------------------------
protected:
using StringMap = std::map<std::string, std::u16string>;
using StringVector = std::vector<std::u16string>;
using ProgramInfoVector = std::vector<StringMap>;
ProgramListInfo info;
ProgramListInfo info {};
UnitID unitId;
StringVector programNames;
ProgramInfoVector programInfos;
Parameter* parameter;
Parameter* parameter {nullptr};
};
//------------------------------------------------------------------------

View file

@ -297,6 +297,15 @@ bool StringListParameter::replaceString (int32 index, const String128 string)
return true;
}
//------------------------------------------------------------------------
void StringListParameter::clear ()
{
for (auto& string : strings)
std::free (string);
strings.clear ();
info.stepCount = -1;
}
//------------------------------------------------------------------------
void StringListParameter::toString (ParamValue _valueNormalized, String128 string) const
{

View file

@ -165,6 +165,9 @@ public:
/** Replaces the string at index. Index must be between 0 and stepCount+1 */
virtual bool replaceString (int32 index, const String128 string);
/** clear all added String */
virtual void clear ();
/** Converts a normalized value to a string. */
void toString (ParamValue _valueNormalized, String128 string) const SMTG_OVERRIDE;
/** Converts a string to a normalized value. */

View file

@ -543,7 +543,7 @@ bool PresetFile::restoreControllerState (IEditController* editController)
if (e)
{
auto readOnlyBStream = owned (new ReadOnlyBStream (stream, e->offset, e->size));
return verify (editController->setState (readOnlyBStream));
return verify (editController->setState (readOnlyBStream)) || e->size == 0;
}
return false;
}