diff --git a/source/bridges-plugin/CarlaBridge.hpp b/source/bridges-plugin/CarlaBridge.hpp deleted file mode 100644 index 1a87fef9b..000000000 --- a/source/bridges-plugin/CarlaBridge.hpp +++ /dev/null @@ -1,35 +0,0 @@ -/* - * Carla Bridge - * Copyright (C) 2011-2013 Filipe Coelho - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of - * the License, or any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * For a full copy of the GNU General Public License see the doc/GPL.txt file. - */ - -#ifndef CARLA_BRIDGE_HPP_INCLUDED -#define CARLA_BRIDGE_HPP_INCLUDED - -#include "CarlaDefines.h" - -#define CARLA_BRIDGE_START_NAMESPACE namespace CarlaBridge { -#define CARLA_BRIDGE_END_NAMESPACE } -#define CARLA_BRIDGE_USE_NAMESPACE using namespace CarlaBridge; - -CARLA_BRIDGE_START_NAMESPACE - -// forward declarations of commonly used Carla-Bridge classes -class CarlaBridgeClient; -class CarlaBridgeToolkit; - -CARLA_BRIDGE_END_NAMESPACE - -#endif // CARLA_BRIDGE_HPP_INCLUDED diff --git a/source/bridges-plugin/CarlaBridgeClient.cpp b/source/bridges-plugin/CarlaBridgeClient.cpp deleted file mode 100644 index bcd58630a..000000000 --- a/source/bridges-plugin/CarlaBridgeClient.cpp +++ /dev/null @@ -1,294 +0,0 @@ -/* - * Carla Bridge Client - * Copyright (C) 2011-2013 Filipe Coelho - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of - * the License, or any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * For a full copy of the GNU General Public License see the doc/GPL.txt file. - */ - -#include "CarlaBridgeClient.hpp" - -#ifdef BUILD_BRIDGE_UI -# include "CarlaLibUtils.hpp" -#endif - -CARLA_BRIDGE_START_NAMESPACE - -// --------------------------------------------------------------------- - -CarlaBridgeClient::CarlaBridgeClient(const char* const uiTitle) - : fOsc(this), - fOscData(fOsc.getControlData()) -#ifdef BUILD_BRIDGE_UI - , fUI(CarlaBridgeToolkit::createNew(this, uiTitle)) -#endif -{ -#ifdef BUILD_BRIDGE_UI - CARLA_ASSERT(uiTitle != nullptr && uiTitle[0] != '\0'); -#endif - carla_debug("CarlaBridgeClient::CarlaBridgeClient(\"%s\")", uiTitle); - -#ifndef BUILD_BRIDGE_UI - return; (void)uiTitle; // unused -#endif -} - -CarlaBridgeClient::~CarlaBridgeClient() -{ - carla_debug("CarlaBridgeClient::~CarlaBridgeClient()"); -} - -#ifdef BUILD_BRIDGE_UI -// --------------------------------------------------------------------- -// ui initialization - -bool CarlaBridgeClient::uiInit(const char* const, const char* const) -{ - carla_debug("CarlaBridgeClient::uiInit()"); - - fUI.init(); - - return true; -} - -void CarlaBridgeClient::uiClose() -{ - carla_debug("CarlaBridgeClient::uiClose()"); - - if (isOscControlRegistered() && ! fUI.quit) - sendOscExiting(); - - fUI.close(); -} - -// --------------------------------------------------------------------- -// ui toolkit - -void CarlaBridgeClient::toolkitShow() -{ - CARLA_SAFE_ASSERT_RETURN(fUI.toolkit != nullptr,); - carla_debug("CarlaBridgeClient::toolkitShow()"); - - fUI.toolkit->show(); -} - -void CarlaBridgeClient::toolkitHide() -{ - CARLA_SAFE_ASSERT_RETURN(fUI.toolkit != nullptr,); - carla_debug("CarlaBridgeClient::toolkitHide()"); - - fUI.toolkit->hide(); -} - -void CarlaBridgeClient::toolkitResize(const int width, const int height) -{ - CARLA_SAFE_ASSERT_RETURN(fUI.toolkit != nullptr,); - carla_debug("CarlaBridgeClient::toolkitResize(%i, %i)", width, height); - - fUI.toolkit->resize(width, height); -} - -void CarlaBridgeClient::toolkitExec(const bool showGui) -{ - CARLA_SAFE_ASSERT_RETURN(fUI.toolkit != nullptr,); - carla_debug("CarlaBridgeClient::toolkitExec(%s)", bool2str(showGui)); - - fUI.toolkit->exec(showGui); -} - -void CarlaBridgeClient::toolkitQuit() -{ - carla_debug("CarlaBridgeClient::toolkitQuit()"); - - fUI.close(); -} -#endif - -// --------------------------------------------------------------------- -// osc stuff - -void CarlaBridgeClient::oscInit(const char* const url) -{ - carla_debug("CarlaBridgeClient::oscInit(\"%s\")", url); - - fOsc.init(url); -} - -bool CarlaBridgeClient::oscIdle() const -{ - fOsc.idle(); - -#ifdef BUILD_BRIDGE_UI - return ! fUI.quit; -#else - return true; -#endif -} - -void CarlaBridgeClient::oscClose() -{ - carla_debug("CarlaBridgeClient::oscClose()"); - - fOsc.close(); -} - -bool CarlaBridgeClient::isOscControlRegistered() const noexcept -{ - return fOsc.isControlRegistered(); -} - -void CarlaBridgeClient::sendOscUpdate() const -{ - carla_debug("CarlaBridgeClient::sendOscUpdate()"); - - if (fOscData.target != nullptr) - osc_send_update(fOscData, fOsc.getServerPath()); -} - -// --------------------------------------------------------------------- - -#ifdef BUILD_BRIDGE_PLUGIN -void CarlaBridgeClient::sendOscBridgeUpdate() const -{ - carla_debug("CarlaBridgeClient::sendOscBridgeUpdate()"); - - if (fOscData.target != nullptr) - osc_send_bridge_update(fOscData, fOscData.path); -} - -void CarlaBridgeClient::sendOscBridgeError(const char* const error) const -{ - carla_debug("CarlaBridgeClient::sendOscBridgeError(\"%s\")", error); - - if (fOscData.target != nullptr) - osc_send_bridge_error(fOscData, error); -} -#endif - -// --------------------------------------------------------------------- - -#ifdef BUILD_BRIDGE_UI -void CarlaBridgeClient::sendOscConfigure(const char* const key, const char* const value) const -{ - carla_debug("CarlaBridgeClient::sendOscConfigure(\"%s\", \"%s\")", key, value); - - if (fOscData.target != nullptr) - osc_send_configure(fOscData, key, value); -} - -void CarlaBridgeClient::sendOscControl(const int32_t index, const float value) const -{ - carla_debug("CarlaBridgeClient::sendOscControl(%i, %f)", index, value); - - if (fOscData.target != nullptr) - osc_send_control(fOscData, index, value); -} - -void CarlaBridgeClient::sendOscProgram(const uint32_t index) const -{ - carla_debug("CarlaBridgeClient::sendOscProgram(%i)", index); - - if (fOscData.target != nullptr) - osc_send_program(fOscData, index); -} - -void CarlaBridgeClient::sendOscMidiProgram(const uint32_t index) const -{ - carla_debug("CarlaBridgeClient::sendOscMidiProgram(%i)", index); - - if (fOscData.target != nullptr) - osc_send_midi_program(fOscData, index); -} - -void CarlaBridgeClient::sendOscMidi(const uint8_t midiBuf[4]) const -{ - carla_debug("CarlaBridgeClient::sendOscMidi(%p)", midiBuf); - - if (fOscData.target != nullptr) - osc_send_midi(fOscData, midiBuf); -} - -void CarlaBridgeClient::sendOscExiting() const -{ - carla_debug("CarlaBridgeClient::sendOscExiting()"); - - if (fOscData.target != nullptr) - osc_send_exiting(fOscData); -} - -#ifdef BRIDGE_LV2 -void CarlaBridgeClient::sendOscLv2AtomTransfer(const int32_t portIndex, const char* const atomBuf) const -{ - carla_debug("CarlaBridgeClient::sendOscLv2TransferAtom(%i, \"%s\")", portIndex, atomBuf); - - if (fOscData.target != nullptr) - osc_send_lv2_atom_transfer(fOscData, portIndex, atomBuf); -} - -void CarlaBridgeClient::sendOscLv2UridMap(const uint32_t urid, const char* const uri) const -{ - carla_debug("CarlaBridgeClient::sendOscLv2UridMap(%i, \"%s\")", urid, uri); - - if (fOscData.target != nullptr) - osc_send_lv2_urid_map(fOscData, urid, uri); -} -#endif - -// --------------------------------------------------------------------- - -void* CarlaBridgeClient::getContainerId() -{ - carla_debug("CarlaBridgeClient::getContainerId()"); - return fUI.toolkit->getContainerId(); -} - -bool CarlaBridgeClient::uiLibOpen(const char* const filename) -{ - CARLA_ASSERT(fUI.lib == nullptr); - CARLA_ASSERT(filename != nullptr); - carla_debug("CarlaBridgeClient::uiLibOpen(\"%s\")", filename); - - fUI.lib = lib_open(filename); - fUI.filename = filename; - - return (fUI.lib != nullptr); -} - -bool CarlaBridgeClient::uiLibClose() -{ - CARLA_SAFE_ASSERT_RETURN(fUI.lib != nullptr, false); - carla_debug("CarlaBridgeClient::uiLibClose()"); - - const bool closed = lib_close(fUI.lib); - fUI.lib = nullptr; - return closed; -} - -void* CarlaBridgeClient::uiLibSymbol(const char* const symbol) -{ - CARLA_SAFE_ASSERT_RETURN(fUI.lib != nullptr, nullptr); - carla_debug("CarlaBridgeClient::uiLibSymbol(\"%s\")", symbol); - - return lib_symbol(fUI.lib, symbol); -} - -const char* CarlaBridgeClient::uiLibError() -{ - carla_debug("CarlaBridgeClient::uiLibError()"); - - return lib_error(fUI.filename); -} -#endif // BUILD_BRIDGE_UI - -// --------------------------------------------------------------------- - -CARLA_BRIDGE_END_NAMESPACE diff --git a/source/bridges-plugin/CarlaBridgeClient.hpp b/source/bridges-plugin/CarlaBridgeClient.hpp deleted file mode 100644 index 30dc7f4da..000000000 --- a/source/bridges-plugin/CarlaBridgeClient.hpp +++ /dev/null @@ -1,167 +0,0 @@ -/* - * Carla Bridge Client - * Copyright (C) 2011-2013 Filipe Coelho - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of - * the License, or any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * For a full copy of the GNU General Public License see the doc/GPL.txt file. - */ - -#ifndef CARLA_BRIDGE_CLIENT_HPP_INCLUDED -#define CARLA_BRIDGE_CLIENT_HPP_INCLUDED - -#include "CarlaBridgeOsc.hpp" - -#ifdef BUILD_BRIDGE_UI -# include "CarlaBridgeToolkit.hpp" -#endif - -CARLA_BRIDGE_START_NAMESPACE - -// ----------------------------------------------------------------------- - -class CarlaBridgeClient -{ -public: - CarlaBridgeClient(const char* const uiTitle); - virtual ~CarlaBridgeClient(); - -#ifdef BUILD_BRIDGE_UI - // --------------------------------------------------------------------- - // ui initialization - - virtual bool uiInit(const char* const, const char* const); - virtual void uiIdle() {} - virtual void uiClose(); - - // --------------------------------------------------------------------- - // ui management - - virtual void* getWidget() const = 0; - virtual bool isResizable() const = 0; - virtual bool needsReparent() const = 0; - - // --------------------------------------------------------------------- - // ui processing - - virtual void setParameter(const int32_t rindex, const float value) = 0; - virtual void setProgram(const uint32_t index) = 0; - virtual void setMidiProgram(const uint32_t bank, const uint32_t program) = 0; - virtual void noteOn(const uint8_t channel, const uint8_t note, const uint8_t velo) = 0; - virtual void noteOff(const uint8_t channel, const uint8_t note) = 0; - - // --------------------------------------------------------------------- - // ui toolkit - - void toolkitShow(); - void toolkitHide(); - void toolkitResize(const int width, const int height); - void toolkitExec(const bool showGui); - void toolkitQuit(); -#endif - - // --------------------------------------------------------------------- - // osc stuff - - void oscInit(const char* const url); - bool oscIdle() const; - void oscClose(); - - bool isOscControlRegistered() const noexcept; - void sendOscUpdate() const; - -#ifdef BUILD_BRIDGE_PLUGIN - void sendOscBridgeUpdate() const; - void sendOscBridgeError(const char* const error) const; -#endif - - // --------------------------------------------------------------------- - -protected: -#ifdef BUILD_BRIDGE_UI - void sendOscConfigure(const char* const key, const char* const value) const; - void sendOscControl(const int32_t index, const float value) const; - void sendOscProgram(const uint32_t index) const; - void sendOscMidiProgram(const uint32_t index) const; - void sendOscMidi(const uint8_t midiBuf[4]) const; - void sendOscExiting() const; - -# ifdef BRIDGE_LV2 - void sendOscLv2AtomTransfer(const int32_t portIndex, const char* const atomBuf) const; - void sendOscLv2UridMap(const uint32_t urid, const char* const uri) const; -# endif - - // --------------------------------------------------------------------- - - void* getContainerId(); - bool uiLibOpen(const char* const filename); - bool uiLibClose(); - void* uiLibSymbol(const char* const symbol); - const char* uiLibError(); -#endif - - // --------------------------------------------------------------------- - -private: - CarlaBridgeOsc fOsc; - const CarlaOscData& fOscData; - -#ifdef BUILD_BRIDGE_UI - struct UI { - CarlaBridgeToolkit* const toolkit; - CarlaString filename; - void* lib; - bool quit; - - UI(CarlaBridgeToolkit* const toolkit_) - : toolkit(toolkit_), - lib(nullptr), - quit(false) - { - CARLA_ASSERT(toolkit != nullptr); - } - - ~UI() - { - delete toolkit; - } - - void init() - { - toolkit->init(); - quit = false; - } - - void close() - { - quit = true; - toolkit->quit(); - } - -# ifdef CARLA_PROPER_CPP11_SUPPORT - UI() = delete; - UI(UI&) = delete; - UI(const UI&) = delete; -# endif - - } fUI; -#else - friend class CarlaPluginClient; -#endif - - CARLA_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(CarlaBridgeClient) -}; - -// ----------------------------------------------------------------------- - -CARLA_BRIDGE_END_NAMESPACE - -#endif // CARLA_BRIDGE_CLIENT_HPP_INCLUDED diff --git a/source/bridges-plugin/CarlaBridgeOsc.cpp b/source/bridges-plugin/CarlaBridgeOsc.cpp deleted file mode 100644 index c8a9ac2fb..000000000 --- a/source/bridges-plugin/CarlaBridgeOsc.cpp +++ /dev/null @@ -1,319 +0,0 @@ -/* - * Carla Bridge OSC - * Copyright (C) 2011-2013 Filipe Coelho - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of - * the License, or any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * For a full copy of the GNU General Public License see the doc/GPL.txt file. - */ - -#include "CarlaBridgeClient.hpp" -#include "CarlaMIDI.h" - -CARLA_BRIDGE_START_NAMESPACE - -// ----------------------------------------------------------------------- - -CarlaBridgeOsc::CarlaBridgeOsc(CarlaBridgeClient* const client) - : fClient(client), - fServer(nullptr) -{ - CARLA_ASSERT(client != nullptr); - carla_debug("CarlaBridgeOsc::CarlaBridgeOsc(%p)", client); -} - -CarlaBridgeOsc::~CarlaBridgeOsc() -{ - CARLA_ASSERT(fControlData.source == nullptr); // must never be used - CARLA_ASSERT(fName.isEmpty()); - CARLA_ASSERT(fServerPath.isEmpty()); - CARLA_ASSERT(fServer == nullptr); - carla_debug("CarlaBridgeOsc::~CarlaBridgeOsc()"); -} - -void CarlaBridgeOsc::init(const char* const url) -{ - CARLA_ASSERT(fName.isEmpty()); - CARLA_ASSERT(fServerPath.isEmpty()); - CARLA_ASSERT(fServer == nullptr); - CARLA_ASSERT(url != nullptr); - carla_debug("CarlaBridgeOsc::init(\"%s\")", url); - - std::srand((uint)(uintptr_t)this); - std::srand((uint)(uintptr_t)&url); - -#ifdef BUILD_BRIDGE_PLUGIN - fName = "plug-"; - fName += CarlaString(std::rand() % 99999); -#else - fName = "ui-"; - fName += CarlaString(std::rand() % 99999); -#endif - - fServer = lo_server_new_with_proto(nullptr, LO_UDP, osc_error_handler); - - CARLA_SAFE_ASSERT_RETURN(fServer != nullptr,) - - { - char* const host = lo_url_get_hostname(url); - char* const port = lo_url_get_port(url); - fControlData.path = carla_strdup_free(lo_url_get_path(url)); - fControlData.target = lo_address_new_with_proto(LO_UDP, host, port); - - std::free(host); - std::free(port); - } - - if (char* const tmpServerPath = lo_server_get_url(fServer)) - { - fServerPath = tmpServerPath; - fServerPath += fName; - std::free(tmpServerPath); - } - -#ifdef BUILD_BRIDGE_UI - lo_server_add_method(fServer, nullptr, nullptr, osc_message_handler, this); -#endif - - CARLA_ASSERT(fName.isNotEmpty()); - CARLA_ASSERT(fServerPath.isNotEmpty()); -} - -void CarlaBridgeOsc::idle() const -{ - if (fServer == nullptr) - return; - - for (; lo_server_recv_noblock(fServer, 0) != 0;) {} -} - -void CarlaBridgeOsc::close() -{ - CARLA_ASSERT(fControlData.source == nullptr); // must never be used - CARLA_ASSERT(fName.isNotEmpty()); - CARLA_ASSERT(fServerPath.isNotEmpty()); - CARLA_ASSERT(fServer != nullptr); - carla_debug("CarlaBridgeOsc::close()"); - - fName.clear(); - - if (fServer != nullptr) - { - lo_server_del_method(fServer, nullptr, nullptr); - lo_server_free(fServer); - fServer = nullptr; - } - - fServerPath.clear(); - fControlData.clear(); - - CARLA_ASSERT(fName.isEmpty()); - CARLA_ASSERT(fServerPath.isEmpty()); - CARLA_ASSERT(fServer == nullptr); -} - -#ifdef BUILD_BRIDGE_UI -// ----------------------------------------------------------------------- - -int CarlaBridgeOsc::handleMessage(const char* const path, const int argc, const lo_arg* const* const argv, const char* const types, const lo_message msg) -{ - CARLA_SAFE_ASSERT_RETURN(fName.isNotEmpty(), 1); - CARLA_SAFE_ASSERT_RETURN(fServerPath.isNotEmpty(), 1); - CARLA_SAFE_ASSERT_RETURN(fServer != nullptr, 1); - CARLA_SAFE_ASSERT_RETURN(path != nullptr, 1); - CARLA_SAFE_ASSERT_RETURN(msg != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMessage(\"%s\", %i, %p, \"%s\", %p)", path, argc, argv, types, msg); - - const size_t nameSize(fName.length()); - - // Check if message is for this client - if (std::strlen(path) <= nameSize || std::strncmp(path+1, fName, nameSize) != 0) - { - carla_stderr("CarlaBridgeOsc::handleMessage() - message not for this client -> '%s' != '/%s/'", path, fName.buffer()); - return 1; - } - - // Get method from path - char method[32+1] = { '\0' }; - std::strncpy(method, path + (nameSize + 2), 32); - - if (method[0] == '\0') - { - carla_stderr("CarlaBridgeOsc::handleMessage(\"%s\", ...) - received message without method", path); - return 1; - } - - // Common methods - if (std::strcmp(method, "show") == 0) - return handleMsgShow(); - if (std::strcmp(method, "hide") == 0) - return handleMsgHide(); - if (std::strcmp(method, "quit") == 0) - return handleMsgQuit(); - - // UI methods - if (std::strcmp(method, "configure") == 0) - return handleMsgUiConfigure(argc, argv, types); - if (std::strcmp(method, "control") == 0) - return handleMsgUiControl(argc, argv, types); - if (std::strcmp(method, "program") == 0) - return handleMsgUiProgram(argc, argv, types); - if (std::strcmp(method, "midi-program") == 0) - return handleMsgUiMidiProgram(argc, argv, types); - if (std::strcmp(method, "midi") == 0) - return handleMsgUiMidi(argc, argv, types); - if (std::strcmp(method, "sample-rate") == 0) - return 0; // unused - -# ifdef BRIDGE_LV2 - // LV2 methods - if (std::strcmp(method, "lv2_atom_transfer") == 0) - return handleMsgLv2UiAtomTransfer(argc, argv, types); - if (std::strcmp(method, "lv2_urid_map") == 0) - return handleMsgLv2UiUridMap(argc, argv, types); -# endif - - carla_stderr("CarlaBridgeOsc::handleMessage(\"%s\", ...) - received unsupported OSC method '%s'", path, method); - return 1; -} - -int CarlaBridgeOsc::handleMsgShow() -{ - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgShow()"); - - fClient->toolkitShow(); - - return 0; -} - -int CarlaBridgeOsc::handleMsgHide() -{ - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgHide()"); - - fClient->toolkitHide(); - - return 0; -} - -int CarlaBridgeOsc::handleMsgQuit() -{ - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgQuit()"); - - fClient->toolkitQuit(); - - return 0; -} - -int CarlaBridgeOsc::handleMsgUiConfigure(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(2, "ss"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgConfigure()"); - - // nothing here for now - return 0; - - // unused - (void)argv; -} - -int CarlaBridgeOsc::handleMsgUiControl(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(2, "if"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgControl()"); - - const int32_t index = argv[0]->i; - const float value = argv[1]->f; - - CARLA_SAFE_ASSERT_RETURN(index != -1, 1); - - fClient->setParameter(index, value); - - return 0; -} - -int CarlaBridgeOsc::handleMsgUiProgram(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(1, "i"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgProgram()"); - - const int32_t index = argv[0]->i; - - CARLA_SAFE_ASSERT_RETURN(index >= 0, 1); - - fClient->setProgram(static_cast(index)); - - return 0; -} - -int CarlaBridgeOsc::handleMsgUiMidiProgram(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(2, "ii"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgMidiProgram()"); - - const int32_t bank = argv[0]->i; - const int32_t program = argv[1]->i; - - CARLA_SAFE_ASSERT_RETURN(bank >= 0, 1); - CARLA_SAFE_ASSERT_RETURN(program >= 0, 1); - - fClient->setMidiProgram(static_cast(bank), static_cast(program)); - - return 0; -} - -int CarlaBridgeOsc::handleMsgUiMidi(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(1, "m"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgMidi()"); - - const uint8_t* const data = argv[0]->m; - uint8_t status = data[1]; - uint8_t channel = status & 0x0F; - - // Fix bad note-off - if (MIDI_IS_STATUS_NOTE_ON(status) && data[3] == 0) - status -= 0x10; - - if (MIDI_IS_STATUS_NOTE_OFF(status)) - { - const uint8_t note = data[2]; - - CARLA_SAFE_ASSERT_RETURN(note < MAX_MIDI_NOTE, 1); - - fClient->noteOff(channel, note); - } - else if (MIDI_IS_STATUS_NOTE_ON(status)) - { - const uint8_t note = data[2]; - const uint8_t velo = data[3]; - - CARLA_SAFE_ASSERT_RETURN(note < MAX_MIDI_NOTE, 1); - CARLA_SAFE_ASSERT_RETURN(velo < MAX_MIDI_VALUE, 1); - - fClient->noteOn(channel, note, velo); - } - - return 0; -} - -#endif // BUILD_BRIDGE_UI - -// ----------------------------------------------------------------------- - -CARLA_BRIDGE_END_NAMESPACE diff --git a/source/bridges-plugin/CarlaBridgeOsc.hpp b/source/bridges-plugin/CarlaBridgeOsc.hpp deleted file mode 100644 index 345ab3070..000000000 --- a/source/bridges-plugin/CarlaBridgeOsc.hpp +++ /dev/null @@ -1,131 +0,0 @@ -/* - * Carla Bridge OSC - * Copyright (C) 2011-2013 Filipe Coelho - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of - * the License, or any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * For a full copy of the GNU General Public License see the doc/GPL.txt file. - */ - -#ifndef CARLA_BRIDGE_OSC_HPP_INCLUDED -#define CARLA_BRIDGE_OSC_HPP_INCLUDED - -#include "CarlaBridge.hpp" -#include "CarlaOscUtils.hpp" -#include "CarlaString.hpp" - -#define CARLA_BRIDGE_OSC_HANDLE_ARGS const int argc, const lo_arg* const* const argv, const char* const types - -#define CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(/* argc, types, */ argcToCompare, typesToCompare) \ - /* check argument count */ \ - if (argc != argcToCompare) \ - { \ - carla_stderr("CarlaBridgeOsc::%s() - argument count mismatch: %i != %i", __FUNCTION__, argc, argcToCompare); \ - return 1; \ - } \ - if (argc > 0) \ - { \ - /* check for nullness */ \ - if (types == nullptr || typesToCompare == nullptr) \ - { \ - carla_stderr("CarlaBridgeOsc::%s() - argument types are null", __FUNCTION__); \ - return 1; \ - } \ - /* check argument types */ \ - if (std::strcmp(types, typesToCompare) != 0) \ - { \ - carla_stderr("CarlaBridgeOsc::%s() - argument types mismatch: '%s' != '%s'", __FUNCTION__, types, typesToCompare); \ - return 1; \ - } \ - } - -CARLA_BRIDGE_START_NAMESPACE - -// ----------------------------------------------------------------------- - -class CarlaBridgeOsc -{ -public: - CarlaBridgeOsc(CarlaBridgeClient* const client); - ~CarlaBridgeOsc(); - - void init(const char* const url); - void idle() const; - void close(); - - // ------------------------------------------------------------------- - - bool isControlRegistered() const noexcept - { - return (fControlData.target != nullptr); - } - - const CarlaOscData& getControlData() const noexcept - { - return fControlData; - } - - const char* getServerPath() const noexcept - { - return fServerPath; - } - - // ------------------------------------------------------------------- - -private: - CarlaBridgeClient* const fClient; - - CarlaOscData fControlData; - CarlaString fName; - CarlaString fServerPath; - lo_server fServer; - -#ifdef BUILD_BRIDGE_UI - // ------------------------------------------------------------------- - - int handleMessage(const char* const path, const int argc, const lo_arg* const* const argv, const char* const types, const lo_message msg); - - int handleMsgShow(); - int handleMsgHide(); - int handleMsgQuit(); - - int handleMsgUiConfigure(CARLA_BRIDGE_OSC_HANDLE_ARGS); - int handleMsgUiControl(CARLA_BRIDGE_OSC_HANDLE_ARGS); - int handleMsgUiProgram(CARLA_BRIDGE_OSC_HANDLE_ARGS); - int handleMsgUiMidiProgram(CARLA_BRIDGE_OSC_HANDLE_ARGS); - int handleMsgUiMidi(CARLA_BRIDGE_OSC_HANDLE_ARGS); - -# ifdef BRIDGE_LV2 - int handleMsgLv2UiAtomTransfer(CARLA_BRIDGE_OSC_HANDLE_ARGS); - int handleMsgLv2UiUridMap(CARLA_BRIDGE_OSC_HANDLE_ARGS); -# endif - - // ------------------------------------------------------------------- - - static int osc_message_handler(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg, void* userData) - { - return ((CarlaBridgeOsc*)userData)->handleMessage(path, argc, argv, types, msg); - } -#endif - - static void osc_error_handler(int num, const char* msg, const char* path) - { - carla_stderr("CarlaBridgeOsc::osc_error_handler(%i, \"%s\", \"%s\")", num, msg, path); - } - - CARLA_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(CarlaBridgeOsc) -}; - -// ----------------------------------------------------------------------- - -CARLA_BRIDGE_END_NAMESPACE - -#endif // CARLA_BRIDGE_OSC_HPP_INCLUDED diff --git a/source/bridges-plugin/CarlaBridgePlugin.cpp b/source/bridges-plugin/CarlaBridgePlugin.cpp index 3f85990dc..19653c2a4 100644 --- a/source/bridges-plugin/CarlaBridgePlugin.cpp +++ b/source/bridges-plugin/CarlaBridgePlugin.cpp @@ -15,13 +15,11 @@ * For a full copy of the GNU General Public License see the doc/GPL.txt file. */ -#include "CarlaBridgeClient.hpp" - #include "CarlaEngine.hpp" #include "CarlaHost.h" #include "CarlaBackendUtils.hpp" -#include "CarlaBridgeUtils.hpp" +#include "CarlaOscUtils.hpp" #include "CarlaMIDI.h" #ifdef CARLA_OS_UNIX @@ -102,16 +100,12 @@ static void initSignalHandler() // ------------------------------------------------------------------------- -static CarlaBridge::CarlaBridgeClient* gBridgeClient = nullptr; static CarlaString gProjectFilename; static void gIdle() { carla_engine_idle(); - if (gBridgeClient != nullptr) - gBridgeClient->oscIdle(); - if (gSaveNow) { gSaveNow = false; @@ -172,19 +166,15 @@ static JUCEApplicationBase* juce_CreateApplication() { return new CarlaJuceApp() // ------------------------------------------------------------------------- -CARLA_BRIDGE_START_NAMESPACE - -// ------------------------------------------------------------------------- - -class CarlaPluginClient : public CarlaBridgeClient +class CarlaBridgePlugin { public: - CarlaPluginClient(const bool useBridge, const char* const clientName, const char* const audioBaseName, const char* const controlBaseName, const char* const timeBaseName) - : CarlaBridgeClient(nullptr), - fEngine(nullptr) + CarlaBridgePlugin(const bool useBridge, const char* const clientName, const char* const audioBaseName, const char* const controlBaseName, const char* const timeBaseName) + : fEngine(nullptr), + fOscServerThread(nullptr) { CARLA_ASSERT(clientName != nullptr && clientName[0] != '\0'); - carla_debug("CarlaPluginClient::CarlaPluginClient(%s, \"%s\", %s, %s, %s)", bool2str(useBridge), clientName, audioBaseName, controlBaseName, timeBaseName); + carla_debug("CarlaBridgePlugin::CarlaBridgePlugin(%s, \"%s\", %s, %s, %s)", bool2str(useBridge), clientName, audioBaseName, controlBaseName, timeBaseName); carla_set_engine_callback(callback, this); @@ -196,9 +186,9 @@ public: fEngine = carla_get_engine(); } - ~CarlaPluginClient() override + ~CarlaBridgePlugin() { - carla_debug("CarlaPluginClient::~CarlaPluginClient()"); + carla_debug("CarlaBridgePlugin::~CarlaBridgePlugin()"); carla_engine_close(); } @@ -208,12 +198,75 @@ public: return (fEngine != nullptr); } + // --------------------------------------------------------------------- + void oscInit(const char* const url) { - CarlaBridgeClient::oscInit(url); - fEngine->setOscBridgeData(&fOscData); + fOscServerThread = lo_server_thread_new_with_proto(nullptr, LO_UDP, osc_error_handler); + + CARLA_SAFE_ASSERT_RETURN(fOscServerThread != nullptr,) + + { + char* const host = lo_url_get_hostname(url); + char* const port = lo_url_get_port(url); + fOscControlData.path = carla_strdup_free(lo_url_get_path(url)); + fOscControlData.target = lo_address_new_with_proto(LO_UDP, host, port); + + std::free(host); + std::free(port); + } + + if (char* const tmpServerPath = lo_server_thread_get_url(fOscServerThread)) + { + std::srand((uint)(uintptr_t)this); + std::srand((uint)(uintptr_t)&url); + + CarlaString oscName("plug-" + CarlaString(std::rand() % 99999)); + + fOscServerPath = tmpServerPath; + fOscServerPath += oscName; + std::free(tmpServerPath); + } + + fEngine->setOscBridgeData(&fOscControlData); } + void oscClose() + { + fEngine->setOscBridgeData(nullptr); + + if (fOscServerThread != nullptr) + { + lo_server_thread_free(fOscServerThread); + fOscServerThread = nullptr; + } + + fOscControlData.clear(); + fOscServerPath.clear(); + } + + // --------------------------------------------------------------------- + + void sendOscUpdate() const noexcept + { + if (fOscControlData.target != nullptr) + osc_send_update(fOscControlData, fOscServerPath); + } + + void sendOscBridgeUpdate() const noexcept + { + if (fOscControlData.target != nullptr) + osc_send_bridge_update(fOscControlData, fOscControlData.path); + } + + void sendOscBridgeError(const char* const error) const noexcept + { + if (fOscControlData.target != nullptr) + osc_send_bridge_error(fOscControlData, error); + } + + // --------------------------------------------------------------------- + void exec(const bool useOsc, int argc, char* argv[]) { if (! useOsc) @@ -231,7 +284,6 @@ public: carla_stderr("Plugin preset load failed, error was:\n%s", carla_get_last_error()); } - gBridgeClient = this; gIsInitiated = true; #if defined(CARLA_OS_MAC) || defined(CARLA_OS_WIN) @@ -244,7 +296,6 @@ public: carla_msleep(25); } #endif - gBridgeClient = nullptr; carla_set_engine_about_to_close(); carla_remove_plugin(0); @@ -270,7 +321,7 @@ protected: break; case ENGINE_CALLBACK_UI_STATE_CHANGED: - if (gIsInitiated && value1 != 1 && ! isOscControlRegistered()) + if (gIsInitiated && value1 != 1 && fOscControlData.target == nullptr) gCloseNow = true; break; @@ -288,65 +339,26 @@ private: const CarlaEngine* fEngine; String fProjFilename; + CarlaOscData fOscControlData; + CarlaString fOscServerPath; + lo_server_thread fOscServerThread; + static void callback(void* ptr, EngineCallbackOpcode action, unsigned int pluginId, int value1, int value2, float value3, const char* valueStr) { - carla_debug("CarlaPluginClient::callback(%p, %i:%s, %i, %i, %i, %f, \"%s\")", ptr, action, EngineCallbackOpcode2Str(action), pluginId, value1, value2, value3, valueStr); + carla_debug("CarlaBridgePlugin::callback(%p, %i:%s, %i, %i, %i, %f, \"%s\")", ptr, action, EngineCallbackOpcode2Str(action), pluginId, value1, value2, value3, valueStr); CARLA_SAFE_ASSERT_RETURN(ptr != nullptr,); CARLA_SAFE_ASSERT_RETURN(pluginId == 0,); - return ((CarlaPluginClient*)ptr)->handleCallback(action, value1, value2, value3, valueStr); + return ((CarlaBridgePlugin*)ptr)->handleCallback(action, value1, value2, value3, valueStr); + } + + static void osc_error_handler(int num, const char* msg, const char* path) + { + carla_stderr("CarlaBridgePlugin::osc_error_handler(%i, \"%s\", \"%s\")", num, msg, path); } }; #if 0 -// ------------------------------------------------------------------------- - -int CarlaBridgeOsc::handleMsgPluginSetParameterMidiChannel(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(2, "ii"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgPluginSetParameterMidiChannel()"); - - const int32_t index = argv[0]->i; - const int32_t channel = argv[1]->i; - - CARLA_SAFE_ASSERT_RETURN(index >= 0, 0); - CARLA_SAFE_ASSERT_RETURN(channel >= 0 && channel < MAX_MIDI_CHANNELS, 0); - - carla_set_parameter_midi_channel(0, static_cast(index), static_cast(channel)); - return 0; -} - -int CarlaBridgeOsc::handleMsgPluginSetParameterMidiCC(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(2, "ii"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgPluginSetParameterMidiCC()"); - - const int32_t index = argv[0]->i; - const int32_t cc = argv[1]->i; - - CARLA_SAFE_ASSERT_RETURN(index >= 0, 0); - CARLA_SAFE_ASSERT_RETURN(cc >= 1 && cc < 0x5F, 0); - - carla_set_parameter_midi_cc(0, static_cast(index), static_cast(cc)); - return 0; -} - -int CarlaBridgeOsc::handleMsgPluginSetCustomData(CARLA_BRIDGE_OSC_HANDLE_ARGS) -{ - CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(3, "sss"); - CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1); - carla_debug("CarlaBridgeOsc::handleMsgPluginSetCustomData()"); - - const char* const type = (const char*)&argv[0]->s; - const char* const key = (const char*)&argv[1]->s; - const char* const value = (const char*)&argv[2]->s; - - carla_set_custom_data(0, type, key, value); - return 0; -} - int CarlaBridgeOsc::handleMsgPluginSetChunk(CARLA_BRIDGE_OSC_HANDLE_ARGS) { CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(1, "s"); @@ -380,14 +392,10 @@ int CarlaBridgeOsc::handleMsgPluginSetChunk(CARLA_BRIDGE_OSC_HANDLE_ARGS) } #endif -CARLA_BRIDGE_END_NAMESPACE - // ------------------------------------------------------------------------- int main(int argc, char* argv[]) { - CARLA_BRIDGE_USE_NAMESPACE; - // --------------------------------------------------------------------- // Check argument count @@ -479,11 +487,11 @@ int main(int argc, char* argv[]) } // --------------------------------------------------------------------- - // Init plugin client + // Init plugin bridge - CarlaPluginClient client(useBridge, clientName, bridgeBaseAudioName, bridgeBaseControlName, bridgeBaseTimeName); + CarlaBridgePlugin bridge(useBridge, clientName, bridgeBaseAudioName, bridgeBaseControlName, bridgeBaseTimeName); - if (! client.isOk()) + if (! bridge.isOk()) { carla_stderr("Failed to init engine, error was:\n%s", carla_get_last_error()); return 1; @@ -493,7 +501,7 @@ int main(int argc, char* argv[]) // Init OSC if (useOsc) - client.oscInit(oscUrl); + bridge.oscInit(oscUrl); // --------------------------------------------------------------------- // Listen for ctrl+c or sigint/sigterm events @@ -511,8 +519,8 @@ int main(int argc, char* argv[]) if (useOsc) { - client.sendOscUpdate(); - client.sendOscBridgeUpdate(); + bridge.sendOscUpdate(); + bridge.sendOscBridgeUpdate(); } else { @@ -525,7 +533,7 @@ int main(int argc, char* argv[]) } } - client.exec(useOsc, argc, argv); + bridge.exec(useOsc, argc, argv); } else { @@ -535,14 +543,14 @@ int main(int argc, char* argv[]) carla_stderr("Plugin failed to load, error was:\n%s", lastError); if (useOsc) - client.sendOscBridgeError(lastError); + bridge.sendOscBridgeError(lastError); } // --------------------------------------------------------------------- // Close OSC if (useOsc) - client.oscClose(); + bridge.oscClose(); return ret; } diff --git a/source/bridges-plugin/Makefile b/source/bridges-plugin/Makefile index abdb6e2a6..4449f0f94 100644 --- a/source/bridges-plugin/Makefile +++ b/source/bridges-plugin/Makefile @@ -7,9 +7,8 @@ include ../Makefile.mk # -------------------------------------------------------------- -# Common -BUILD_CXX_FLAGS += -DBUILD_BRIDGE +BUILD_CXX_FLAGS += -DBUILD_BRIDGE -DBUILD_BRIDGE_PLUGIN BUILD_CXX_FLAGS += -I. -I../backend -I../includes -I../utils -isystem ../modules BUILD_CXX_FLAGS += $(LIBLO_FLAGS) LINK_FLAGS += $(LIBLO_LIBS) @@ -17,7 +16,7 @@ LINK_FLAGS += $(LIBLO_LIBS) # -------------------------------------------------------------- # Plugin bridges -BUILD_PLUGIN_FLAGS = $(BUILD_CXX_FLAGS) -DBUILD_BRIDGE_PLUGIN +BUILD_PLUGIN_FLAGS = $(BUILD_CXX_FLAGS) BUILD_PLUGIN_FLAGS += -I../backend/engine -I../backend/plugin LINK_PLUGIN_FLAGS = $(LINK_FLAGS) @@ -106,10 +105,7 @@ win64: ../../bin/carla-bridge-win64.exe # -------------------------------------------------------------- # native -OBJS_NATIVE = \ - CarlaBridgePlugin__native.o \ - CarlaBridgeClient__native.o \ - CarlaBridgeOsc__native.o +OBJS_NATIVE = CarlaBridgePlugin__native.o # carla-engine OBJS_NATIVE += \ @@ -173,8 +169,7 @@ endif # -------------------------------------------------------------- # posix32 -OBJS_POSIX32 = CarlaBridgePlugin__posix32.o \ - CarlaBridgeClient__posix32.o CarlaBridgeOsc__posix32.o +OBJS_POSIX32 = CarlaBridgePlugin__posix32.o # carla-engine OBJS_POSIX32 += \ @@ -232,8 +227,7 @@ endif # -------------------------------------------------------------- # posix64 -OBJS_POSIX64 = CarlaBridgePlugin__posix64.o \ - CarlaBridgeClient__posix64.o CarlaBridgeOsc__posix64.o +OBJS_POSIX64 = CarlaBridgePlugin__posix64.o # carla-engine OBJS_POSIX64 += \ @@ -291,8 +285,7 @@ endif # -------------------------------------------------------------- # win32 -OBJS_WIN32 = CarlaBridgePlugin__win32.o \ - CarlaBridgeClient__win32.o CarlaBridgeOsc__win32.o +OBJS_WIN32 = CarlaBridgePlugin__win32.o # carla-engine OBJS_WIN32 += \ @@ -347,8 +340,7 @@ LIBS_WIN32 += \ # -------------------------------------------------------------- # win64 -OBJS_WIN64 = CarlaBridgePlugin__win64.o \ - CarlaBridgeClient__win64.o CarlaBridgeOsc__win64.o +OBJS_WIN64 = CarlaBridgePlugin__win64.o # carla-engine OBJS_WIN64 += \