diff --git a/ArduinoOSC/ArduinoOSCCommon.h b/ArduinoOSC/ArduinoOSCCommon.h index 37187b4..961f1dd 100644 --- a/ArduinoOSC/ArduinoOSCCommon.h +++ b/ArduinoOSC/ArduinoOSCCommon.h @@ -66,6 +66,45 @@ namespace osc { #endif } + bool unsubscribe(const uint16_t port, const String& addr) { +#if defined(ARDUINOOSC_ENABLE_WIFI) && (defined(ESP_PLATFORM) || defined(ARDUINO_ARCH_RP2040)) + if (WiFi.getMode() != WIFI_OFF) + return OscServerManager::getInstance().unsubscribe(port, addr); + else { + LOG_ERROR(F("WiFi is not enabled. Unsubscribing OSC failed.")); + return false; + } +#else + return OscServerManager::getInstance().unsubscribe(port, addr); +#endif + } + + bool unsubscribe(const uint16_t port) { +#if defined(ARDUINOOSC_ENABLE_WIFI) && (defined(ESP_PLATFORM) || defined(ARDUINO_ARCH_RP2040)) + if (WiFi.getMode() != WIFI_OFF) + return OscServerManager::getInstance().unsubscribe(port); + else { + LOG_ERROR(F("WiFi is not enabled. Unsubscribing OSC failed.")); + return false; + } +#else + return OscServerManager::getInstance().unsubscribe(port); +#endif + } + + bool unsubscribe() { +#if defined(ARDUINOOSC_ENABLE_WIFI) && (defined(ESP_PLATFORM) || defined(ARDUINO_ARCH_RP2040)) + if (WiFi.getMode() != WIFI_OFF) + return OscServerManager::getInstance().unsubscribeAll(); + else { + LOG_ERROR(F("WiFi is not enabled. Unsubscribing OSC failed.")); + return false; + } +#else + return OscServerManager::getInstance().unsubscribeAll(); +#endif + } + void parse() { #if defined(ARDUINOOSC_ENABLE_WIFI) && (defined(ESP_PLATFORM) || defined(ARDUINO_ARCH_RP2040)) if (this->isWiFiConnected() || this->isWiFiModeAP()) { diff --git a/ArduinoOSC/OSCServer.h b/ArduinoOSC/OSCServer.h index b927825..48a9e05 100644 --- a/ArduinoOSC/OSCServer.h +++ b/ArduinoOSC/OSCServer.h @@ -204,6 +204,23 @@ namespace osc { callbacks.insert({addr, ref}); } + bool unsubscribe(const String& addr) { + auto it = callbacks.find(addr); + if (it != callbacks.end()) { + callbacks.erase(it); + return true; + } + return false; + } + + bool unsubscribeAll() { + if (!callbacks.empty()) { + callbacks.clear(); + return true; + } + return false; + } + bool parse() { auto stream = UdpMapManager::getInstance().getUdp(port); const size_t size = stream->parsePacket(); @@ -263,6 +280,32 @@ namespace osc { getServer(port).subscribe(addr, std::forward(ts)...); } + bool unsubscribe(const uint16_t port, const String& addr) { + auto it = server_map.find(port); + if (it != server_map.end()) { + return it->second->unsubscribe(addr); + } + return false; + } + + bool unsubscribe(const uint16_t port) { + auto it = server_map.find(port); + if (it != server_map.end()) { + return it->second->unsubscribeAll(); + } + return false; + } + + bool unsubscribeAll() { + if (!server_map.empty()) { + for (auto& m : server_map) { + m.second->unsubscribeAll(); + } + return true; + } + return false; + } + void parse() { for (auto& m : server_map) m.second->parse(); diff --git a/README.md b/README.md index a97ee43..3a4c542 100644 --- a/README.md +++ b/README.md @@ -249,6 +249,131 @@ You can see the debug log when you insert following line before include `Arduino #include ``` +## APIs + +### Main Class (`OscWiFi` / `OscEther`) + +#### Subscribing to OSC Messages + +```cpp +// Subscribe a value to an OSC message +OscWiFi.subscribe(const uint16_t port, const String& addr, T& value); +// Subscribe multiple values to an OSC message +OscWiFi.subscribe(const uint16_t port, const String& addr, T1& v1, T2& v2, ...); +// Subscribe a lambda to an OSC message with arguments +OscWiFi.subscribe(const uint16_t port, const String& addr, [](T1 arg1, T2 arg2, ...) { ... }); +// Subscribe a lambda to an OSC message with OscMessage argument +OscWiFi.subscribe(const uint16_t port, const String& addr, [](const OscMessage& msg) { ... }); +// Subscribe a function to an OSC message +OscWiFi.subscribe(const uint16_t port, const String& addr, onOscReceived); +``` + +#### Unsubscribing from OSC Messages + +```cpp +// Unsubscribe from a specific address on a port +OscWiFi.unsubscribe(const uint16_t port, const String& addr); +// Unsubscribe from all addresses on a port +OscWiFi.unsubscribe(const uint16_t port); +// Unsubscribe from all addresses on all ports +OscWiFi.unsubscribe(); +``` + +#### Sending OSC Messages + +```cpp +// Send an OSC message with arguments +OscWiFi.send(const String& ip, const uint16_t port, const String& addr, T1 arg1, T2 arg2, ...); +``` + +#### Publishing OSC Messages + +```cpp +// Publish a value periodically +OscWiFi.publish(const String& ip, const uint16_t port, const String& addr, T& value) + ->setFrameRate(float fps); +// Publish multiple values periodically +OscWiFi.publish(const String& ip, const uint16_t port, const String& addr, T1& v1, T2& v2, ...) + ->setIntervalMsec(float ms); +// Publish function results periodically +OscWiFi.publish(const String& ip, const uint16_t port, const String& addr, &func1, &func2) + ->setIntervalSec(float sec); +``` + +#### OSC Bundle Support + +```cpp +// Create and send OSC bundles +OscWiFi.begin_bundle(const TimeTag& tt = TimeTag::immediate()); +OscWiFi.add_bundle(const String& addr, T1 arg1, T2 arg2, ...); +OscWiFi.end_bundle(); +OscWiFi.send_bundle(const String& ip, const uint16_t port); +``` + +#### Update Functions + +```cpp +// Parse incoming OSC messages (server) +OscWiFi.parse(); +// Parse incoming OSC messages and publish outgoing messages (server + client) +OscWiFi.update(); +// Send published OSC messages (client) +OscWiFi.post(); +``` + +### OscMessage + +#### Argument Getters + +```cpp +msg.arg(const uint8_t index); // Get argument as type T +msg.getArgAsInt32(const size_t i); +msg.getArgAsInt64(const size_t i); +msg.getArgAsFloat(const size_t i); +msg.getArgAsDouble(const size_t i); +msg.getArgAsString(const size_t i); +msg.getArgAsBlob(const size_t i); +msg.getArgAsBool(const size_t i); +``` + +#### Type Checkers + +```cpp +msg.isBool(const size_t i); +msg.isInt32(const size_t i); +msg.isInt64(const size_t i); +msg.isFloat(const size_t i); +msg.isDouble(const size_t i); +msg.isStr(const size_t i); +msg.isBlob(const size_t i); +``` + +#### Message Information + +```cpp +msg.address(); // Get OSC address +msg.size(); // Get number of arguments +msg.typeTags(); // Get type tag string +msg.remoteIP(); // Get sender's IP address +msg.remotePort(); // Get sender's port +msg.match(const String& pattern); // Check if address matches pattern +``` + +### Manual Packet Handling (for boards with limited memory) + +```cpp +// Server for receiving +OscEtherServer server(recv_port); +if (server.parse()) { + const OscMessage* msg = server.message(); + // Process message... +} + +// Client for sending +OscEtherClient client; +client.send(host, send_port, "/addr", arg1, arg2); +``` + ## Dependent Libraries - [ArxTypeTraits](https://github.com/hideakitai/ArxTypeTraits) diff --git a/library.json b/library.json index 08e3d63..2804cf3 100644 --- a/library.json +++ b/library.json @@ -1,24 +1,24 @@ { - "name": "ArduinoOSC", - "keywords": "osc,wifi,ethernet,udp", - "description": "OSC subscriber / publisher for Arduino", - "repository": { - "type": "git", - "url": "https://github.com/hideakitai/ArduinoOSC.git" - }, - "authors": { - "name": "Hideaki Tai", - "url": "https://github.com/hideakitai", - "maintainer": true - }, - "version": "0.5.2", - "license": "MIT", - "frameworks": "arduino", - "platforms": "*", - "dependencies": { - "hideakitai/ArxContainer": ">=0.6.0", - "hideakitai/ArxSmartPtr": "*", - "hideakitai/ArxTypeTraits": "*", - "hideakitai/DebugLog": ">=0.8.1" - } + "name": "ArduinoOSC", + "keywords": "osc,wifi,ethernet,udp", + "description": "OSC subscriber / publisher for Arduino", + "repository": { + "type": "git", + "url": "https://github.com/hideakitai/ArduinoOSC.git" + }, + "authors": { + "name": "Hideaki Tai", + "url": "https://github.com/hideakitai", + "maintainer": true + }, + "version": "0.6.0", + "license": "MIT", + "frameworks": "arduino", + "platforms": "*", + "dependencies": { + "hideakitai/ArxContainer": ">=0.6.0", + "hideakitai/ArxSmartPtr": "*", + "hideakitai/ArxTypeTraits": "*", + "hideakitai/DebugLog": ">=0.8.1" + } } diff --git a/library.properties b/library.properties index 9a8ad0b..cc4686d 100644 --- a/library.properties +++ b/library.properties @@ -1,5 +1,5 @@ name=ArduinoOSC -version=0.5.2 +version=0.6.0 author=hideakitai maintainer=hideakitai sentence=OSC subscriber / publisher for Arduino