From 9ab40052eb66f6b46142f740ed264c872b419922 Mon Sep 17 00:00:00 2001 From: Dooho Yi Date: Tue, 13 Dec 2022 02:30:27 +0900 Subject: [PATCH] init --- .gitignore | 2 + ESPOscuinoBundle/ESPOscuinoBundle.ino | 466 +++++++++++++++++++++++ ESPOscuinoMessage/ESPOscuinoMessage.ino | 479 ++++++++++++++++++++++++ pd/piano_access_radio_comm_wifi.pd | 284 ++++++++++++++ 4 files changed, 1231 insertions(+) create mode 100644 .gitignore create mode 100644 ESPOscuinoBundle/ESPOscuinoBundle.ino create mode 100644 ESPOscuinoMessage/ESPOscuinoMessage.ino create mode 100644 pd/piano_access_radio_comm_wifi.pd diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..f0fed7e --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +.DS_Store +*/.DS_Store diff --git a/ESPOscuinoBundle/ESPOscuinoBundle.ino b/ESPOscuinoBundle/ESPOscuinoBundle.ino new file mode 100644 index 0000000..8d6abf0 --- /dev/null +++ b/ESPOscuinoBundle/ESPOscuinoBundle.ino @@ -0,0 +1,466 @@ + +// UDP OSCuino over WIFI w/ ESP32 (or ESP8266? - NOT TESTED) +// system, analog and digital pin control and monitoring for Arduino +// Yotam Mann and Adrian Freed + +// +#ifdef ESP8266 +#include +#else +#include +#endif +#include + +// +#include +#include +#define BOARD_HAS_ANALOG_PULLUP +#define BOARD_HAS_CAPACITANCE_SENSING +#include + +char ssid[] = "TEEPOT"; // your network SSID (name) +char pass[] = "3333388888"; // your network password + +// A UDP instance to let us send and receive packets over UDP +WiFiUDP Udp; +const IPAddress outIp(192,168,43,13); // remote IP (not needed for receive) +const unsigned int outPort = 9999; // remote port (not needed for receive) +const unsigned int localPort = 8888; // local port to listen for UDP packets (here's where we send the packets) + +//outgoing messages +OSCBundle bundleOUT; + +//converts the pin to an osc address +char * numToOSCAddress (int pin) { + static char s[10]; + int i = 9; + + s[i--]= '\0'; + + do + { + s[i] = "0123456789"[pin % 10]; + --i; + pin /= 10; + } + while (pin && i); + + s[i] = '/'; + + return &s[i]; +} + +/** + * ROUTES + * + * these are where the routing functions go + * + */ + +/** + * DIGITAL + * + * called when address matched "/d" + * expected format: + * /d/(pin) + * /u = digitalRead with pullup + * (no value) = digitalRead without pullup + * (value) = digital write on that pin + * + */ + +void routeDigital (OSCMessage &msg, int addrOffset) { + //match input or output + for(byte pin = 0; pin < NUM_DIGITAL_PINS; pin++){ + //match against the pin number strings + int pinMatched = msg.match(numToOSCAddress(pin), addrOffset); + if(pinMatched){ + //if it has an int, then it's a digital write + if (msg.isInt(0)) { + pinMode(pin, OUTPUT); + digitalWrite(pin, (msg.getInt(0) > 0) ? HIGH : LOW); + } + //if it has an float, then it's an analog write + else if (msg.isFloat(0)) { + //TODO: only for ESP8266 - ESP32 doesn't support analogWrite in this way. + #ifdef ESP8266 + analogWrite(pin, (int)(msg.getFloat(0)*255.0f)); + #endif + } + //otherwise it's an digital read + //with a pullup? + else if (msg.fullMatch("/u", pinMatched + addrOffset)) { + //set the pullup + pinMode(pin, INPUT_PULLUP); + //setup the output address which should be /d/(pin)/u + char outputAddress[9]; + strcpy(outputAddress, "/d"); + strcat(outputAddress, numToOSCAddress(pin)); + strcat(outputAddress, "/u"); + //do the digital read and send the results + bundleOUT.add(outputAddress).add(digitalRead(pin)); + } + //else without a pullup + else { + //set the pinmode + pinMode(pin, INPUT); + //setup the output address which should be /d/(pin) + char outputAddress[6]; + strcpy(outputAddress, "/d"); + strcat(outputAddress, numToOSCAddress(pin)); + //do the digital read and send the results + bundleOUT.add(outputAddress).add(digitalRead(pin)); + } + } + } +} + +/** + * ANALOG + * + * called when the address matches "/a" + * + * format: + * /a/(pin) + * /u = analogRead with pullup + * (no value) = analogRead without pullup + * (digital value) = digital write on that pin + * (float value) = analogWrite on that pin + * + **/ + +void routeAnalog (OSCMessage &msg, int addrOffset) { + //iterate through all the analog pins + for (byte pin = 0; pin < NUM_ANALOG_INPUTS; pin++) { + //match against the pin number strings + int pinMatched = msg.match(numToOSCAddress(pin), addrOffset); + if (pinMatched) { + //if it has an int, then it's a digital write + if (msg.isInt(0)) { + pinMode(analogInputToDigitalPin(pin), OUTPUT); + digitalWrite(analogInputToDigitalPin(pin), (msg.getInt(0) > 0)? HIGH: LOW); + } + //if it has an float, then it's an analog write + else if(msg.isFloat(0)) { + //TODO: only for ESP8266 - ESP32 doesn't support analogWrite in this way. + #ifdef ESP8266 + analogWrite(pin, (int)(msg.getFloat(0)*255.0f)); + #endif + } +#ifdef BOARD_HAS_ANALOG_PULLUP + //with a pullup? + else if (msg.fullMatch("/u", pinMatched + addrOffset)){ + //set the pullup + pinMode(analogInputToDigitalPin(pin), INPUT_PULLUP); + + //setup the output address which should be /a/(pin)/u + char outputAddress[9]; + strcpy(outputAddress, "/a"); + strcat(outputAddress, numToOSCAddress(pin)); + strcat(outputAddress,"/u"); + // strcat(outputAddress,"/u"); + //do the analog read and send the results + bundleOUT.add(outputAddress).add((int32_t)analogRead(pin)); + } +#endif + //else without a pullup + else { + //set the pinmode + pinMode(analogInputToDigitalPin(pin), INPUT); + + //setup the output address which should be /a/(pin) + char outputAddress[6]; + strcpy(outputAddress, "/a"); + strcat(outputAddress, numToOSCAddress(pin)); + //do the analog read and send the results + bundleOUT.add(outputAddress).add((int32_t)analogRead(pin)); + } + } + } +} + +#ifdef BOARD_HAS_TONE + +/** + * TONE + * + * square wave output "/tone" + * + * format: + * /tone/pin + * + * (digital value) (float value) = freqency in Hz + * (no value) disable tone + * + **/ + +void routeTone (OSCMessage &msg, int addrOffset) +{ + //iterate through all the analog pins + for (byte pin = 0; pin < NUM_DIGITAL_PINS; pin++) { + //match against the pin number strings + int pinMatched = msg.match(numToOSCAddress(pin), addrOffset); + if (pinMatched) { + unsigned int frequency = 0; + //if it has an int, then it's an integers frequency in Hz + if (msg.isInt(0)) { + frequency = msg.getInt(0); + } + //otherwise it's a floating point frequency in Hz + else if(msg.isFloat(0)) { + frequency = msg.getFloat(0); + } + else { + noTone(pin); + } + if (frequency > 0) { + if(msg.isInt(1)) { + tone(pin, frequency, msg.getInt(1)); + } + else { + tone(pin, frequency); + } + } + } + } +} + +#endif + +#ifdef BOARD_HAS_CAPACITANCE_SENSING +#define NTPINS 2 +const int cpins[NTPINS] = { 4, 15 }; +void routeTouch (OSCMessage &msg, int addrOffset) +{ + for (int i = 0; i < NTPINS; ++i) + { + const char *name = numToOSCAddress(cpins[i]); + int pinMatched = msg.match(name, addrOffset); + if (pinMatched) + { + char outputAddress[9]; + strcpy(outputAddress, "/c"); + strcat(outputAddress, name); + bundleOUT.add(outputAddress).add(touchRead(cpins[i])); + } + } +} +#endif + + +#ifdef BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT + +#if defined(__MK20DX128__) || defined(__MK20DX256__) || defined(__MKL26Z64__) +float getSupplyVoltage() +{ + int val = analogRead(39); + return val>0? (1.20f*1023/val):0.0f; +} +#else +// power supply measurement on some Arduinos +float getSupplyVoltage(){ + // powersupply + int result; + // Read 1.1V reference against AVcc +#if defined(__AVR_ATmega32U4__) || defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) + ADMUX = _BV(REFS0) | _BV(MUX4) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1); +#elif defined (__AVR_ATtiny24__) || defined(__AVR_ATtiny44__) || defined(__AVR_ATtiny84__) + ADMUX = _BV(MUX5) | _BV(MUX0); +#elif defined (__AVR_ATtiny25__) || defined(__AVR_ATtiny45__) || defined(__AVR_ATtiny85__) + ADMUX = _BV(MUX3) | _BV(MUX2); +#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__) || defined(__AVR_ATmega1280__) + ADMUX = 0x40| _BV(MUX4) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1) ; + ADCSRB = 0; +#else + ADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1); +#endif + delayMicroseconds(300); // wait for Vref to settle + ADCSRA |= _BV(ADSC); // Convert + while (bit_is_set(ADCSRA,ADSC)); + result = ADCL; + result |= ADCH<<8; + + float supplyvoltage = 1.1264f *1023 / result; + return supplyvoltage; +} +#endif + +#endif + + +#ifdef BOARD_HAS_DIE_TEMPERATURE_SENSOR + +#if defined(__MK20DX128__) || defined(__MK20DX256__) || defined(__MKL26Z64__) +float getTemperature() +{ + analogReference(INTERNAL); + delay(1); + int val = analogRead(38); // seems to be flakey + analogReference(DEFAULT); + + return val; //need to compute something here to get to degrees C +} +#else +// temperature +float getTemperature() { + int result; +#if defined(__AVR_ATmega32U4__) + ADMUX = _BV(REFS1) | _BV(REFS0) | _BV(MUX2) | _BV(MUX1) | _BV(MUX0); + ADCSRB = _BV(MUX5); +#else + ADMUX = _BV(REFS1) | _BV(REFS0) | _BV(MUX3); +#endif + delayMicroseconds(200); // wait for Vref to settle + ADCSRA |= _BV(ADSC); // Convert + while (bit_is_set(ADCSRA,ADSC)); + result = ADCL; + result |= ADCH<<8; + + analogReference(DEFAULT); + + return result/1023.0f; +} +#endif + +#endif + + +/** + * SYSTEM MESSAGES + * + * expected format: + * /s + * /m = microseconds + * /d = number of digital pins + * /a = number of analog pins + * /l integer = set the led + * /t = temperature + * /s = power supply voltage + */ +// +void routeSystem (OSCMessage &msg, int addrOffset) { + +#ifdef BOARD_HAS_DIE_TEMPERATURE_SENSOR + if (msg.fullMatch("/t", addrOffset)){ + bundleOUT.add("/s/t").add(getTemperature()); + } +#endif + +#ifdef BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT + if (msg.fullMatch("/s", addrOffset)){ + bundleOUT.add("/s/s").add(getSupplyVoltage()); + } +#endif + + if (msg.fullMatch("/m", addrOffset)){ + bundleOUT.add("/s/m").add((int32_t)micros()); + } + + if (msg.fullMatch("/d", addrOffset)){ + bundleOUT.add("/s/d").add(NUM_DIGITAL_PINS); + } + + if (msg.fullMatch("/a", addrOffset)){ + bundleOUT.add("/s/a").add(NUM_ANALOG_INPUTS); + } + + if (msg.fullMatch("/l", addrOffset)){ + if (msg.isInt(0)) { + int i = msg.getInt(0); + pinMode(LED_BUILTIN, OUTPUT); + digitalWrite(LED_BUILTIN, (i > 0) ? HIGH: LOW); + bundleOUT.add("/s/l").add(i); + } + } +} + +/** + * MAIN METHODS + * + * setup and loop, bundle receiving/sending, initial routing + */ +void setup() { + + // + pinMode(LED_BUILTIN, OUTPUT); + + // + Serial.begin(115200); + + // Connect to WiFi network + Serial.println(); + Serial.println(); + Serial.print("Connecting to "); + Serial.println(ssid); + WiFi.begin(ssid, pass); + + while (WiFi.status() != WL_CONNECTED) { + delay(500); + Serial.print("."); + } + Serial.println(""); + + Serial.println("WiFi connected"); + Serial.println("IP address: "); + Serial.println(WiFi.localIP()); + + Serial.println("Starting UDP"); + Udp.begin(localPort); + Serial.print("Local port: "); +#ifdef ESP32 + Serial.println(localPort); +#else + Serial.println(Udp.localPort()); +#endif + +#ifdef BOARD_HAS_ANALOG_PULLUP + Serial.println("=== BOARD_HAS_ANALOG_PULLUP ==="); +#endif +#ifdef BOARD_HAS_TONE + Serial.println("=== BOARD_HAS_TONE ==="); +#endif +#ifdef BOARD_HAS_CAPACITANCE_SENSING + Serial.println("=== BOARD_HAS_CAPACITANCE_SENSING ==="); +#endif +#ifdef BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT + Serial.println("=== BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT ==="); +#endif +#ifdef BOARD_HAS_DIE_TEMPERATURE_SENSOR + Serial.println("=== BOARD_HAS_DIE_TEMPERATURE_SENSOR ==="); +#endif + +} + +//reads and routes the incoming messages +void loop(){ + OSCBundle bundleIN; + int size; + + if( (size = Udp.parsePacket()) > 0) + { + while(size--) { + bundleIN.fill(Udp.read()); + } + if(!bundleIN.hasError()) + { + bundleIN.route("/s", routeSystem); + bundleIN.route("/a", routeAnalog); + bundleIN.route("/d", routeDigital); +#ifdef BOARD_HAS_TONE + bundleIN.route("/tone", routeTone); +#endif + +#ifdef BOARD_HAS_CAPACITANCE_SENSING + bundleIN.route("/c", routeTouch); +#endif + } + + // send the response bundle back to where the request came from + Udp.beginPacket(Udp.remoteIP(),outPort); + bundleOUT.send(Udp); + Udp.endPacket(); + + // empty the bundle ready to use for new messages + bundleOUT.empty(); + } +} diff --git a/ESPOscuinoMessage/ESPOscuinoMessage.ino b/ESPOscuinoMessage/ESPOscuinoMessage.ino new file mode 100644 index 0000000..89f8f2d --- /dev/null +++ b/ESPOscuinoMessage/ESPOscuinoMessage.ino @@ -0,0 +1,479 @@ + +// UDP OSCuino over WIFI w/ ESP32 (or ESP8266? - NOT TESTED) +// system, analog and digital pin control and monitoring for Arduino +// Yotam Mann and Adrian Freed + +// +#ifdef ESP8266 +#include +#else +#include +#endif +#include + +// +#include +#include +#define BOARD_HAS_ANALOG_PULLUP +#define BOARD_HAS_CAPACITANCE_SENSING +#include +#include + +char ssid[] = "TEEPOT"; // your network SSID (name) +char pass[] = "3333388888"; // your network password + +// A UDP instance to let us send and receive packets over UDP +WiFiUDP Udp; +const IPAddress outIp(192,168,43,13); // remote IP (not needed for receive) +const unsigned int outPort = 9999; // remote port (not needed for receive) +const unsigned int localPort = 8888; // local port to listen for UDP packets (here's where we send the packets) + +//converts the pin to an osc address +char * numToOSCAddress (int pin) { + static char s[10]; + int i = 9; + + s[i--]= '\0'; + + do + { + s[i] = "0123456789"[pin % 10]; + --i; + pin /= 10; + } + while (pin && i); + + s[i] = '/'; + + return &s[i]; +} + +/** + * ROUTES + * + * these are where the routing functions go + * + */ + +/** + * DIGITAL + * + * called when address matched "/d" + * expected format: + * /d/(pin) + * /u = digitalRead with pullup + * (no value) = digitalRead without pullup + * (value) = digital write on that pin + * + */ + +void routeDigital (OSCMessage &msg, int addrOffset) { + //match input or output + for(byte pin = 0; pin < NUM_DIGITAL_PINS; pin++){ + //match against the pin number strings + int pinMatched = msg.match(numToOSCAddress(pin), addrOffset); + if(pinMatched){ + //if it has an int, then it's a digital write + if (msg.isInt(0)) { + pinMode(pin, OUTPUT); + digitalWrite(pin, (msg.getInt(0) > 0) ? HIGH : LOW); + } + //if it has an float, then it's an analog write + else if (msg.isFloat(0)) { + //TODO: only for ESP8266 - ESP32 doesn't support analogWrite in this way. + #ifdef ESP8266 + analogWrite(pin, (int)(msg.getFloat(0)*255.0f)); + #endif + } + //otherwise it's an digital read + //with a pullup? + else if (msg.fullMatch("/u", pinMatched + addrOffset)) { + //set the pullup + pinMode(pin, INPUT_PULLUP); + //setup the output address which should be /d/(pin)/u + char outputAddress[9]; + strcpy(outputAddress, "/d"); + strcat(outputAddress, numToOSCAddress(pin)); + strcat(outputAddress, "/u"); + //do the digital read and send the results + { + OSCMessage msgOut(outputAddress); msgOut.add(digitalRead(pin)); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + } + //else without a pullup + else { + //set the pinmode + pinMode(pin, INPUT); + //setup the output address which should be /d/(pin) + char outputAddress[6]; + strcpy(outputAddress, "/d"); + strcat(outputAddress, numToOSCAddress(pin)); + //do the digital read and send the results + { + OSCMessage msgOut(outputAddress); msgOut.add(digitalRead(pin)); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + } + } + } +} + +/** + * ANALOG + * + * called when the address matches "/a" + * + * format: + * /a/(pin) + * /u = analogRead with pullup + * (no value) = analogRead without pullup + * (digital value) = digital write on that pin + * (float value) = analogWrite on that pin + * + **/ + +void routeAnalog (OSCMessage &msg, int addrOffset) { + //iterate through all the analog pins + for (byte pin = 0; pin < NUM_ANALOG_INPUTS; pin++) { + //match against the pin number strings + int pinMatched = msg.match(numToOSCAddress(pin), addrOffset); + if (pinMatched) { + //if it has an int, then it's a digital write + if (msg.isInt(0)) { + pinMode(analogInputToDigitalPin(pin), OUTPUT); + digitalWrite(analogInputToDigitalPin(pin), (msg.getInt(0) > 0)? HIGH: LOW); + } + //if it has an float, then it's an analog write + else if(msg.isFloat(0)) { + //TODO: only for ESP8266 - ESP32 doesn't support analogWrite in this way. + #ifdef ESP8266 + analogWrite(pin, (int)(msg.getFloat(0)*255.0f)); + #endif + } +#ifdef BOARD_HAS_ANALOG_PULLUP + //with a pullup? + else if (msg.fullMatch("/u", pinMatched + addrOffset)){ + //set the pullup + pinMode(analogInputToDigitalPin(pin), INPUT_PULLUP); + + //setup the output address which should be /a/(pin)/u + char outputAddress[9]; + strcpy(outputAddress, "/a"); + strcat(outputAddress, numToOSCAddress(pin)); + strcat(outputAddress,"/u"); + // strcat(outputAddress,"/u"); + //do the analog read and send the results + { + OSCMessage msgOut(outputAddress); msgOut.add((int32_t)analogRead(pin)); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + } +#endif + //else without a pullup + else { + //set the pinmode + pinMode(analogInputToDigitalPin(pin), INPUT); + + //setup the output address which should be /a/(pin) + char outputAddress[6]; + strcpy(outputAddress, "/a"); + strcat(outputAddress, numToOSCAddress(pin)); + //do the analog read and send the results + { + OSCMessage msgOut(outputAddress); msgOut.add((int32_t)analogRead(pin)); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + } + } + } +} + +#ifdef BOARD_HAS_TONE + +/** + * TONE + * + * square wave output "/tone" + * + * format: + * /tone/pin + * + * (digital value) (float value) = freqency in Hz + * (no value) disable tone + * + **/ + +void routeTone (OSCMessage &msg, int addrOffset) +{ + //iterate through all the analog pins + for (byte pin = 0; pin < NUM_DIGITAL_PINS; pin++) { + //match against the pin number strings + int pinMatched = msg.match(numToOSCAddress(pin), addrOffset); + if (pinMatched) { + unsigned int frequency = 0; + //if it has an int, then it's an integers frequency in Hz + if (msg.isInt(0)) { + frequency = msg.getInt(0); + } + //otherwise it's a floating point frequency in Hz + else if(msg.isFloat(0)) { + frequency = msg.getFloat(0); + } + else { + noTone(pin); + } + if (frequency > 0) { + if(msg.isInt(1)) { + tone(pin, frequency, msg.getInt(1)); + } + else { + tone(pin, frequency); + } + } + } + } +} + +#endif + +#ifdef BOARD_HAS_CAPACITANCE_SENSING +#define NTPINS 2 +const int cpins[NTPINS] = { 4, 15 }; +void routeTouch (OSCMessage &msg, int addrOffset) +{ + for (int i = 0; i < NTPINS; ++i) + { + const char *name = numToOSCAddress(cpins[i]); + int pinMatched = msg.match(name, addrOffset); + if (pinMatched) + { + char outputAddress[9]; + strcpy(outputAddress, "/c"); + strcat(outputAddress, name); + { + OSCMessage msgOut(outputAddress); msgOut.add(touchRead(cpins[i])); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + } + } +} +#endif + + +#ifdef BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT + +#if defined(__MK20DX128__) || defined(__MK20DX256__) || defined(__MKL26Z64__) +float getSupplyVoltage() +{ + int val = analogRead(39); + return val>0? (1.20f*1023/val):0.0f; +} +#else +// power supply measurement on some Arduinos +float getSupplyVoltage(){ + // powersupply + int result; + // Read 1.1V reference against AVcc +#if defined(__AVR_ATmega32U4__) || defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) + ADMUX = _BV(REFS0) | _BV(MUX4) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1); +#elif defined (__AVR_ATtiny24__) || defined(__AVR_ATtiny44__) || defined(__AVR_ATtiny84__) + ADMUX = _BV(MUX5) | _BV(MUX0); +#elif defined (__AVR_ATtiny25__) || defined(__AVR_ATtiny45__) || defined(__AVR_ATtiny85__) + ADMUX = _BV(MUX3) | _BV(MUX2); +#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__) || defined(__AVR_ATmega1280__) + ADMUX = 0x40| _BV(MUX4) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1) ; + ADCSRB = 0; +#else + ADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1); +#endif + delayMicroseconds(300); // wait for Vref to settle + ADCSRA |= _BV(ADSC); // Convert + while (bit_is_set(ADCSRA,ADSC)); + result = ADCL; + result |= ADCH<<8; + + float supplyvoltage = 1.1264f *1023 / result; + return supplyvoltage; +} +#endif + +#endif + + +#ifdef BOARD_HAS_DIE_TEMPERATURE_SENSOR + +#if defined(__MK20DX128__) || defined(__MK20DX256__) || defined(__MKL26Z64__) +float getTemperature() +{ + analogReference(INTERNAL); + delay(1); + int val = analogRead(38); // seems to be flakey + analogReference(DEFAULT); + + return val; //need to compute something here to get to degrees C +} +#else +// temperature +float getTemperature() { + int result; +#if defined(__AVR_ATmega32U4__) + ADMUX = _BV(REFS1) | _BV(REFS0) | _BV(MUX2) | _BV(MUX1) | _BV(MUX0); + ADCSRB = _BV(MUX5); +#else + ADMUX = _BV(REFS1) | _BV(REFS0) | _BV(MUX3); +#endif + delayMicroseconds(200); // wait for Vref to settle + ADCSRA |= _BV(ADSC); // Convert + while (bit_is_set(ADCSRA,ADSC)); + result = ADCL; + result |= ADCH<<8; + + analogReference(DEFAULT); + + return result/1023.0f; +} +#endif + +#endif + + +/** + * SYSTEM MESSAGES + * + * expected format: + * /s + * /m = microseconds + * /d = number of digital pins + * /a = number of analog pins + * /l integer = set the led + * /t = temperature + * /s = power supply voltage + */ +// +void routeSystem (OSCMessage &msg, int addrOffset) { + +#ifdef BOARD_HAS_DIE_TEMPERATURE_SENSOR + if (msg.fullMatch("/t", addrOffset)) { + OSCMessage msgOut("/s/t"); msgOut.add(getTemperature()); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } +#endif + +#ifdef BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT + if (msg.fullMatch("/s", addrOffset)){ + OSCMessage msgOut("/s/s"); msgOut.add(getSupplyVoltage()); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } +#endif + + if (msg.fullMatch("/m", addrOffset)){ + OSCMessage msgOut("/s/m"); msgOut.add((int32_t)micros()); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + + if (msg.fullMatch("/d", addrOffset)){ + OSCMessage msgOut("/s/d"); msgOut.add(NUM_DIGITAL_PINS); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + + if (msg.fullMatch("/a", addrOffset)){ + OSCMessage msgOut("/s/a"); msgOut.add(NUM_ANALOG_INPUTS); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + + if (msg.fullMatch("/l", addrOffset)){ + if (msg.isInt(0)) { + int i = msg.getInt(0); + pinMode(LED_BUILTIN, OUTPUT); + digitalWrite(LED_BUILTIN, (i > 0) ? HIGH: LOW); + { + OSCMessage msgOut("/s/l"); msgOut.add(i); + Udp.beginPacket(Udp.remoteIP(),outPort); msgOut.send(Udp); Udp.endPacket(); + } + } + } +} + +/** + * MAIN METHODS + * + * setup and loop, bundle receiving/sending, initial routing + */ +void setup() { + + // + pinMode(LED_BUILTIN, OUTPUT); + + // + Serial.begin(115200); + + // Connect to WiFi network + Serial.println(); + Serial.println(); + Serial.print("Connecting to "); + Serial.println(ssid); + WiFi.begin(ssid, pass); + + while (WiFi.status() != WL_CONNECTED) { + delay(500); + Serial.print("."); + } + Serial.println(""); + + Serial.println("WiFi connected"); + Serial.println("IP address: "); + Serial.println(WiFi.localIP()); + + Serial.println("Starting UDP"); + Udp.begin(localPort); + Serial.print("Local port: "); +#ifdef ESP32 + Serial.println(localPort); +#else + Serial.println(Udp.localPort()); +#endif + +#ifdef BOARD_HAS_ANALOG_PULLUP + Serial.println("=== BOARD_HAS_ANALOG_PULLUP ==="); +#endif +#ifdef BOARD_HAS_TONE + Serial.println("=== BOARD_HAS_TONE ==="); +#endif +#ifdef BOARD_HAS_CAPACITANCE_SENSING + Serial.println("=== BOARD_HAS_CAPACITANCE_SENSING ==="); +#endif +#ifdef BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT + Serial.println("=== BOARD_HAS_DIE_POWER_SUPPLY_MEASUREMENT ==="); +#endif +#ifdef BOARD_HAS_DIE_TEMPERATURE_SENSOR + Serial.println("=== BOARD_HAS_DIE_TEMPERATURE_SENSOR ==="); +#endif + +} + +//reads and routes the incoming messages +void loop(){ + OSCMessage msg; + int size; + + if( (size = Udp.parsePacket()) > 0) + { + while(size--) { + msg.fill(Udp.read()); + } + if(!msg.hasError()) + { + msg.route("/s", routeSystem); + msg.route("/a", routeAnalog); + msg.route("/d", routeDigital); +#ifdef BOARD_HAS_TONE + msg.route("/tone", routeTone); +#endif + +#ifdef BOARD_HAS_CAPACITANCE_SENSING + msg.route("/c", routeTouch); +#endif + } + } +} diff --git a/pd/piano_access_radio_comm_wifi.pd b/pd/piano_access_radio_comm_wifi.pd new file mode 100644 index 0000000..4cc0c48 --- /dev/null +++ b/pd/piano_access_radio_comm_wifi.pd @@ -0,0 +1,284 @@ +#N canvas 656 158 711 192 10; +#X obj 117 100 packOSC; +#X obj 117 75 r OSC; +#X obj 420 102 unpackOSC; +#X obj 420 123 routeOSC /hello; +#X obj 420 144 s HELLO; +#X obj 34 140 print OSC; +#X obj 34 113 spigot; +#X obj 67 87 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 #000000 +0 1; +#X obj 337 117 spigot; +#X obj 386 102 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 337 144 print HELLO; +#X obj 117 142 tgl 15 0 empty empty connected? 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 420 81 udpreceive 9999; +#X obj 117 121 udpsend; +#X obj 545 19 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 545 60 s OSC; +#X text 103 24 * a wireless "field synth" - based on 'udp' protocol +over wifi, f 63; +#N canvas 564 340 874 489 oscuino 0; +#X obj 163 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 183 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 204 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 225 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 246 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 267 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 288 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 308 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 329 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 350 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 371 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 392 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 413 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 434 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 454 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 475 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 496 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 517 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 538 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 559 258 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 708 321 vsl 15 128 0 100 0 0 empty empty empty 0 -9 0 10 #fcfcfc +#000000 #000000 0 1; +#X obj 766 321 vsl 15 128 0 100 0 0 empty empty empty 0 -9 0 10 #fcfcfc +#000000 #000000 0 1; +#X text 689 122 System message responses; +#X text 350 289 Analog Values; +#X text 21 288 Analog Values with Pullups Enabled; +#N canvas 0 50 450 278 (subpatch) 0; +#X array AnalogArray 16 float 2; +#X coords 0 1023 16 0 200 140 1 0 0; +#X restore 18 20 graph; +#X obj 327 78 mrpeach/routeOSC /a /d /s /c; +#X obj 163 216 mrpeach/routeOSC /1 /2 /3 /4 /5 /6 /7 /8 /9 /10 /11 +/12 /13 /14 /15 /16 /17 /18 /19 /20, f 70; +#X obj 694 140 cyclone/prepend set; +#X obj 742 13 cyclone/prepend set; +#N canvas 0 94 450 300 fillArray 0; +#X obj 60 223 send AnalogArray; +#X obj 60 194 cyclone/funnel 16; +#X obj 60 120 inlet; +#X obj 60 142 routeOSC /1 /2 /3 /4 /5 /6 /7 /8 /9 /10 /11 /12 /13 /14 +/15 /16, f 54; +#X connect 1 0 0 0; +#X connect 2 0 3 0; +#X connect 3 0 1 0; +#X connect 3 1 1 1; +#X connect 3 2 1 2; +#X connect 3 3 1 3; +#X connect 3 4 1 4; +#X connect 3 5 1 5; +#X connect 3 6 1 6; +#X connect 3 7 1 7; +#X connect 3 8 1 8; +#X connect 3 9 1 9; +#X connect 3 10 1 10; +#X connect 3 11 1 11; +#X connect 3 12 1 12; +#X connect 3 13 1 13; +#X connect 3 14 1 14; +#X connect 3 15 1 15; +#X restore 342 422 pd fillArray; +#X msg 742 33; +#X text 205 198 Digital pins state; +#X obj 327 23 inlet; +#X msg 694 163 /m 8.45495e+08; +#X text 707 242 Touch Pins on ESP32; +#X obj 21 306 routeOSC /0/u /1/u /2/u /3/u /4/u /5/u /6/u /7/u /8/u +/9/u /10/u /11/u /12/u /13/u /14/u /15/u, f 54; +#X obj 353 306 routeOSC /1 /2 /3 /4 /5 /6 /7 /8 /9 /10 /11 /12 /13 +/14 /15 /16, f 54; +#X floatatom 21 344 5 0 0 0 - - - 0; +#X floatatom 41 370 5 0 0 0 - - - 0; +#X floatatom 61 344 5 0 0 0 - - - 0; +#X floatatom 81 370 5 0 0 0 - - - 0; +#X floatatom 101 344 5 0 0 0 - - - 0; +#X floatatom 121 370 5 0 0 0 - - - 0; +#X floatatom 141 344 5 0 0 0 - - - 0; +#X floatatom 161 370 5 0 0 0 - - - 0; +#X floatatom 181 344 5 0 0 0 - - - 0; +#X floatatom 201 370 5 0 0 0 - - - 0; +#X floatatom 221 344 5 0 0 0 - - - 0; +#X floatatom 241 370 5 0 0 0 - - - 0; +#X floatatom 261 344 5 0 0 0 - - - 0; +#X floatatom 281 370 5 0 0 0 - - - 0; +#X floatatom 301 344 5 0 0 0 - - - 0; +#X floatatom 321 370 5 0 0 0 - - - 0; +#X floatatom 353 344 5 0 0 0 - - - 0; +#X floatatom 373 370 5 0 0 0 - - - 0; +#X floatatom 393 344 5 0 0 0 - - - 0; +#X floatatom 413 370 5 0 0 0 - - - 0; +#X floatatom 433 344 5 0 0 0 - - - 0; +#X floatatom 453 370 5 0 0 0 - - - 0; +#X floatatom 473 344 5 0 0 0 - - - 0; +#X floatatom 493 370 5 0 0 0 - - - 0; +#X floatatom 513 344 5 0 0 0 - - - 0; +#X floatatom 533 370 5 0 0 0 - - - 0; +#X floatatom 553 344 5 0 0 0 - - - 0; +#X floatatom 573 370 5 0 0 0 - - - 0; +#X floatatom 593 344 5 0 0 0 - - - 0; +#X floatatom 613 370 5 0 0 0 - - - 0; +#X floatatom 633 344 5 0 0 0 - - - 0; +#X floatatom 653 370 5 0 0 0 - - - 0; +#X floatatom 708 293 5 0 0 0 - - - 0; +#X obj 708 266 routeOSC /4 /15, f 20; +#X floatatom 766 293 5 0 0 0 - - - 0; +#X connect 26 0 36 0; +#X connect 26 1 27 0; +#X connect 26 2 28 0; +#X connect 26 3 71 0; +#X connect 26 4 29 0; +#X connect 27 0 0 0; +#X connect 27 1 1 0; +#X connect 27 2 2 0; +#X connect 27 3 3 0; +#X connect 27 4 4 0; +#X connect 27 5 5 0; +#X connect 27 6 6 0; +#X connect 27 7 7 0; +#X connect 27 8 8 0; +#X connect 27 9 9 0; +#X connect 27 10 10 0; +#X connect 27 11 11 0; +#X connect 27 12 12 0; +#X connect 27 13 13 0; +#X connect 27 14 14 0; +#X connect 27 15 15 0; +#X connect 27 16 16 0; +#X connect 27 17 17 0; +#X connect 27 18 18 0; +#X connect 27 19 19 0; +#X connect 28 0 34 0; +#X connect 29 0 31 0; +#X connect 33 0 26 0; +#X connect 36 0 38 0; +#X connect 36 1 39 0; +#X connect 36 2 40 0; +#X connect 36 3 41 0; +#X connect 36 4 42 0; +#X connect 36 5 43 0; +#X connect 36 6 44 0; +#X connect 36 7 45 0; +#X connect 36 8 46 0; +#X connect 36 9 47 0; +#X connect 36 10 48 0; +#X connect 36 11 49 0; +#X connect 36 12 50 0; +#X connect 36 13 51 0; +#X connect 36 14 52 0; +#X connect 36 15 53 0; +#X connect 36 16 30 0; +#X connect 36 16 37 0; +#X connect 37 0 54 0; +#X connect 37 1 55 0; +#X connect 37 2 56 0; +#X connect 37 3 57 0; +#X connect 37 4 58 0; +#X connect 37 5 59 0; +#X connect 37 6 60 0; +#X connect 37 7 61 0; +#X connect 37 8 62 0; +#X connect 37 9 63 0; +#X connect 37 10 64 0; +#X connect 37 11 65 0; +#X connect 37 12 66 0; +#X connect 37 13 67 0; +#X connect 37 14 68 0; +#X connect 37 15 69 0; +#X connect 70 0 20 0; +#X connect 71 0 70 0; +#X connect 71 1 72 0; +#X connect 72 0 21 0; +#X restore 505 154 pd oscuino; +#N canvas 625 25 810 190 oscuino 0; +#X msg 512 30 /s/a; +#X msg 469 30 /s/d; +#X msg 575 30 /s/m; +#X msg 359 65 /d/[1-3]; +#X obj 146 36 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X msg 679 115 /c/*; +#X msg 283 64 /a/*/u; +#X text 290 48 Pull up; +#X text 467 10 How many pins?; +#X text 575 9 How many milliseconds ?; +#X text 65 32 LED; +#X obj 146 61 metro 60; +#X obj 679 74 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 679 94 metro 60; +#X text 165 34 Retrieve analog value each 60ms, f 15; +#X text 356 22 get digital pins 1 to 3 status, f 11; +#X obj 381 146 outlet; +#X msg 62 84 /s/l \$1; +#X obj 62 58 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 #000000 +0 1; +#X text 634 60 get ESP32 Touch each 60ms; +#X msg 146 84 /a/*; +#X connect 0 0 16 0; +#X connect 1 0 16 0; +#X connect 2 0 16 0; +#X connect 3 0 16 0; +#X connect 4 0 11 0; +#X connect 5 0 16 0; +#X connect 6 0 16 0; +#X connect 11 0 20 0; +#X connect 12 0 13 0; +#X connect 13 0 5 0; +#X connect 17 0 16 0; +#X connect 18 0 17 0; +#X connect 20 0 16 0; +#X restore 21 28 pd oscuino; +#X msg 216 114 disconnect; +#X msg 167 75 connect 192.168.43.85 8888; +#X msg 545 39 /s/l \$1; +#X obj 637 83 tgl 15 0 empty empty empty 17 7 0 10 #fcfcfc #000000 +#000000 0 1; +#X obj 637 103 metro 60; +#X obj 637 145 s OSC; +#X msg 637 124 /c/*; +#X connect 0 0 13 0; +#X connect 1 0 0 0; +#X connect 1 0 6 0; +#X connect 2 0 3 0; +#X connect 2 0 17 0; +#X connect 3 0 4 0; +#X connect 3 0 8 0; +#X connect 6 0 5 0; +#X connect 7 0 6 1; +#X connect 8 0 10 0; +#X connect 9 0 8 1; +#X connect 12 0 2 0; +#X connect 13 0 11 0; +#X connect 14 0 21 0; +#X connect 18 0 0 0; +#X connect 19 0 13 0; +#X connect 20 0 13 0; +#X connect 21 0 15 0; +#X connect 22 0 23 0; +#X connect 23 0 25 0; +#X connect 25 0 24 0;