DPF

DISTRHO Plugin Framework
Log | Files | Refs | Submodules | README | LICENSE

commit d0a26d6d205ce51c450806d615c8edd3e48e7a90
parent eafa8349a9dd745a3739a78166606801c17240d2
Author: falkTX <falktx@gmail.com>
Date:   Sun, 29 Nov 2015 19:32:22 +0100

Initial support for full states

Diffstat:
Mdistrho/DistrhoPlugin.hpp | 10++++++++++
Mdistrho/src/DistrhoPluginChecks.h | 12++++++++++++
Mdistrho/src/DistrhoPluginInternal.hpp | 10++++++++++
Mdistrho/src/DistrhoPluginLV2.cpp | 14++++++++------
Mdistrho/src/DistrhoPluginLV2export.cpp | 20+++++++++++---------
Mdistrho/src/DistrhoUILV2.cpp | 10++++++----
6 files changed, 57 insertions(+), 19 deletions(-)

diff --git a/distrho/DistrhoPlugin.hpp b/distrho/DistrhoPlugin.hpp @@ -644,6 +644,16 @@ protected: virtual void loadProgram(uint32_t index) = 0; #endif +#if DISTRHO_PLUGIN_WANT_FULL_STATE + /** + Get the value of an internal state.@n + The host may call this function from any non-realtime context.@n + Must be implemented by your plugin class if DISTRHO_PLUGIN_WANT_PROGRAMS or DISTRHO_PLUGIN_WANT_FULL_STATE is enabled. + @note The use of this function breaks compatibility with the DSSI format. + */ + virtual String getState(const char* key) const = 0; +#endif + #if DISTRHO_PLUGIN_WANT_STATE /** Change an internal state @a key to @a value.@n diff --git a/distrho/src/DistrhoPluginChecks.h b/distrho/src/DistrhoPluginChecks.h @@ -73,6 +73,10 @@ # define DISTRHO_PLUGIN_WANT_STATE 0 #endif +#ifndef DISTRHO_PLUGIN_WANT_FULL_STATE +# define DISTRHO_PLUGIN_WANT_FULL_STATE 0 +#endif + #ifndef DISTRHO_PLUGIN_WANT_TIMEPOS # define DISTRHO_PLUGIN_WANT_TIMEPOS 0 #endif @@ -105,6 +109,14 @@ #endif // ----------------------------------------------------------------------- +// Enable full state if plugin exports presets + +#if DISTRHO_PLUGIN_WANT_PROGRAMS && DISTRHO_PLUGIN_WANT_STATE +# undef DISTRHO_PLUGIN_WANT_FULL_STATE +# define DISTRHO_PLUGIN_WANT_FULL_STATE 1 +#endif + +// ----------------------------------------------------------------------- // Disable UI if DGL is not available #if DISTRHO_PLUGIN_HAS_UI && ! defined(HAVE_DGL) diff --git a/distrho/src/DistrhoPluginInternal.hpp b/distrho/src/DistrhoPluginInternal.hpp @@ -385,6 +385,16 @@ public: return fData->stateDefValues[index]; } +# if DISTRHO_PLUGIN_WANT_FULL_STATE + String getState(const char* key) const + { + DISTRHO_SAFE_ASSERT_RETURN(fData != nullptr, sFallbackString); + DISTRHO_SAFE_ASSERT_RETURN(key != nullptr && key[0] != '\0', sFallbackString); + + return fPlugin->getState(key); + } +# endif + void setState(const char* const key, const char* const value) { DISTRHO_SAFE_ASSERT_RETURN(fData != nullptr,); diff --git a/distrho/src/DistrhoPluginLV2.cpp b/distrho/src/DistrhoPluginLV2.cpp @@ -40,6 +40,10 @@ # error DISTRHO_PLUGIN_URI undefined! #endif +#ifndef DISTRHO_PLUGIN_LV2_STATE_PREFIX +# define DISTRHO_PLUGIN_LV2_STATE_PREFIX "urn:distrho:" +#endif + #define DISTRHO_LV2_USE_EVENTS_IN (DISTRHO_PLUGIN_WANT_MIDI_INPUT || DISTRHO_PLUGIN_WANT_TIMEPOS || (DISTRHO_PLUGIN_WANT_STATE && DISTRHO_PLUGIN_HAS_UI)) #define DISTRHO_LV2_USE_EVENTS_OUT (DISTRHO_PLUGIN_WANT_MIDI_OUTPUT || (DISTRHO_PLUGIN_WANT_STATE && DISTRHO_PLUGIN_HAS_UI)) @@ -752,7 +756,7 @@ public: const String& key = cit->first; const String& value = cit->second; - const String urnKey("urn:distrho:" + key); + const String urnKey(DISTRHO_PLUGIN_LV2_STATE_PREFIX + key); // some hosts need +1 for the null terminator, even though the type is string store(handle, fUridMap->map(fUridMap->handle, urnKey.buffer()), value.buffer(), value.length()+1, fURIDs.atomString, LV2_STATE_IS_POD|LV2_STATE_IS_PORTABLE); @@ -769,7 +773,7 @@ public: for (uint32_t i=0, count=fPlugin.getStateCount(); i < count; ++i) { const String& key(fPlugin.getStateKey(i)); - const String urnKey("urn:distrho:" + key); + const String urnKey(DISTRHO_PLUGIN_LV2_STATE_PREFIX + key); size = 0; type = 0; @@ -909,7 +913,7 @@ private: atomLong(uridMap->map(uridMap->handle, LV2_ATOM__Long)), atomSequence(uridMap->map(uridMap->handle, LV2_ATOM__Sequence)), atomString(uridMap->map(uridMap->handle, LV2_ATOM__String)), - distrhoState(uridMap->map(uridMap->handle, "urn:distrho:keyValueState")), + distrhoState(uridMap->map(uridMap->handle, DISTRHO_PLUGIN_LV2_STATE_PREFIX "KeyValueState")), midiEvent(uridMap->map(uridMap->handle, LV2_MIDI__MidiEvent)), timePosition(uridMap->map(uridMap->handle, LV2_TIME__Position)), timeBar(uridMap->map(uridMap->handle, LV2_TIME__bar)), @@ -1161,15 +1165,13 @@ static const void* lv2_extension_data(const char* uri) #endif #if DISTRHO_PLUGIN_WANT_DIRECT_ACCESS -# define DISTRHO_DIRECT_ACCESS_URI "urn:distrho:direct-access" - struct LV2_DirectAccess_Interface { void* (*get_instance_pointer)(LV2_Handle handle); }; static const LV2_DirectAccess_Interface directaccess = { lv2_get_instance_pointer }; - if (std::strcmp(uri, DISTRHO_DIRECT_ACCESS_URI) == 0) + if (std::strcmp(uri, DISTRHO_PLUGIN_LV2_STATE_PREFIX "direct-access") == 0) return &directaccess; #endif diff --git a/distrho/src/DistrhoPluginLV2export.cpp b/distrho/src/DistrhoPluginLV2export.cpp @@ -589,7 +589,7 @@ void lv2_generate_ttl(const char* const basename) const uint32_t numParameters = plugin.getParameterCount(); const uint32_t numPrograms = plugin.getProgramCount(); -# if DISTRHO_PLUGIN_WANT_STATE +# if DISTRHO_PLUGIN_WANT_FULL_STATE const uint32_t numStates = plugin.getStateCount(); # endif @@ -608,20 +608,23 @@ void lv2_generate_ttl(const char* const basename) presetString = "<" DISTRHO_PLUGIN_URI + presetSeparator + "preset" + strBuf + ">\n"; -# if DISTRHO_PLUGIN_WANT_STATE -# warning "Exporting LV2 Presets with state not supported yet" -# if 0 +# if DISTRHO_PLUGIN_WANT_FULL_STATE for (uint32_t j=0; j<numStates; ++j) { + const String key = plugin.getStateKey(j); + const String value = plugin.getState(key); + if (j == 0) presetString += " state:state [\n"; else presetString += " [\n"; - presetString += " <urn:distrho:" + plugin.getStateKey(j) + ">\n"; - presetString += "\"\"\"\n"; - presetString += plugin.getState(j); - presetString += "\"\"\"\n"; + presetString += " <urn:distrho:" + key + ">\n"; + + if (value.length() < 10) + presetString += " \"" + value + "\" ;\n"; + else + presetString += "\"\"\"\n" + value + "\"\"\" ;\n"; if (j+1 == numStates) { @@ -635,7 +638,6 @@ void lv2_generate_ttl(const char* const basename) presetString += " ] ,\n"; } } -# endif # endif for (uint32_t j=0; j <numParameters; ++j) diff --git a/distrho/src/DistrhoUILV2.cpp b/distrho/src/DistrhoUILV2.cpp @@ -28,6 +28,10 @@ #include "lv2/lv2_kxstudio_properties.h" #include "lv2/lv2_programs.h" +#ifndef DISTRHO_PLUGIN_LV2_STATE_PREFIX +# define DISTRHO_PLUGIN_LV2_STATE_PREFIX "urn:distrho:" +#endif + START_NAMESPACE_DISTRHO // ----------------------------------------------------------------------- @@ -46,7 +50,7 @@ public: fController(controller), fWriteFunction(writeFunc), fEventTransferURID(uridMap->map(uridMap->handle, LV2_ATOM__eventTransfer)), - fKeyValueURID(uridMap->map(uridMap->handle, "urn:distrho:keyValueState")), + fKeyValueURID(uridMap->map(uridMap->handle, DISTRHO_PLUGIN_LV2_STATE_PREFIX "KeyValueState")), fWinIdWasNull(winId == 0) { if (fUiResize != nullptr && winId != 0) @@ -331,8 +335,6 @@ static LV2UI_Handle lv2ui_instantiate(const LV2UI_Descriptor*, const char* uri, void* instance = nullptr; #if DISTRHO_PLUGIN_WANT_DIRECT_ACCESS -# define DISTRHO_DIRECT_ACCESS_URI "urn:distrho:direct-access" - struct LV2_DirectAccess_Interface { void* (*get_instance_pointer)(LV2_Handle handle); }; @@ -381,7 +383,7 @@ static LV2UI_Handle lv2ui_instantiate(const LV2UI_Descriptor*, const char* uri, return nullptr; } - if (const LV2_DirectAccess_Interface* const directAccess = (const LV2_DirectAccess_Interface*)extData->data_access(DISTRHO_DIRECT_ACCESS_URI)) + if (const LV2_DirectAccess_Interface* const directAccess = (const LV2_DirectAccess_Interface*)extData->data_access(DISTRHO_PLUGIN_LV2_STATE_PREFIX "direct-access")) instance = directAccess->get_instance_pointer(instance); else instance = nullptr;