0

Using the Amp100 Beta with Sonos Amp button panel and Serial Interactions with Arduino

Hello,

I didn't find much to read on using the interactions, so I thought I would share this little project, if someone else would like to try it. I've been putting the HiFiBerry Amp100 with DSP addon board into an old broken Sonos Amp case. Using HiFiBerryOS with Spofify Connect and DSP Peak Filters to increase the bass, I now have great sound. Still haven't tried room compensation, but it is next on the list.

I wanted to use the original Sonos button panel and have mapped out the functions on the cable from the board. Counting from the bottom with the red/white cable as number 1.

1. Red/White cable - not used
2. Volume -
3. Volume +
4. Ground (-)
5. Ground (-)
6. Red LED
7. White LED
8. Amber LED
9. Green LED
10. Mute/Unmute

Connecting them to a Pro Micro is based on ATmega32U4 (a smaller Arduino Micro variant) I could use the arduino as a USB Keyboard, but this is sensitve to connecting and disconnecting the USB cable.

Here is how I connected the buttonpanel to the Pro Micro (credit for the image of the micro goes to someone on the internet). I added resistors 330ohm to each of the LED cables, since this Pro Micro with USB uses 5V, while Sonos used about 3.4 V for the button panel. 

I noticed today that the Arduino showed up as an available serial port in the interactions view, so I changed my code to use the serial interface instead, and by this I could also react to changes from the HiFiBerryOS client. So, selected and enabled the serial port /dev/ttyAMC0, from the Web UI and added interactions.

The interactions to send messages from HiFiBerryOS:

Product Startup -> Send Serial Message "HiFiBerry_Started"
Source Started -> Send Serial Message "HiFiBerry_Source_Started"
Source Stopped -> Send Serial Message "HiFiBerry_Source_Stopped"


The receive message interactions from the Pro Micro:

Serial Message Received "HiFiBerry_Mute_Unmute" -> Mute or Unmute
Serial Message Received "HiFiBerry_Volume_Up" -> Set Volume, Step volume up
Serial Message Received "HiFiBerry_Volume_Down" -> Set Volume, Step volume down

The quoted text strings are the messages sent between HiFiBerryOS and the Pro Micro. I used the LED's as follows; Red is lit on startup, and turned off when communications starts. Amber is used for warning, i.e. unkown event received on serial port. The White LED is lit when the "HiFiBerry_Started" message arrives, but in case we miss this message, it is also lit for all other events. Finally, the Green LED is lit when a source starts playing, and turned off when source stops playing.

Work in progress:

Below is the arduino code:

// No longer using Keyboard and Consumer from the HID-Project
//#include "Keyboard.h"
//#include <HID-Project.h>


const int whiteLedPin = A0; // LED connected to digital pin A0
const int amberLedPin = A1; // LED connected to digital pin A1
const int redLedPin = A2; // LED connected to digital pin A2
const int greenLedPin = A3; // LED connected to digital pin A3
const int muteButtonPin = 4; // input pin for pushbutton
const int volUpButtonPin = 5; // input pin for pushbutton
const int volDnButtonPin = 6; // input pin for pushbutton
int prevMuteButtonState = HIGH; // do not allow repeated pressed interpretations
int counter = 0; // allow volume up/down to be pressed and acted on repeatedly

String inputEvent = ""; // Incoming event from HiFiBerry
bool eventCompleted = false; // Is message fully read

void setup() {
// 4 different color LED's
pinMode(whiteLedPin, OUTPUT);
pinMode(redLedPin, OUTPUT);
pinMode(amberLedPin, OUTPUT);
pinMode(greenLedPin, OUTPUT);

// starting turn on red led
digitalWrite(redLedPin, HIGH); // not confirmed working

// 3 input buttons:
pinMode(muteButtonPin, INPUT_PULLUP);
pinMode(volUpButtonPin, INPUT_PULLUP);
pinMode(volDnButtonPin, INPUT_PULLUP);
// Serial communication
Serial.begin(9600);
inputEvent.reserve(200);
while (!Serial) {
;
}
// Initialize keyboard:
// Consumer.begin();
// Keyboard.begin();
}

void loop() {

while (Serial.available() && (eventCompleted == false) ) {
// get the new byte:
char inChar = (char)Serial.read();
// add it to the inputString:
inputEvent += inChar;
// if the incoming character is a newline, set a flag so the main loop can
// do something about it:
if (inChar == '\n') {
eventCompleted = true;
}
}

if (eventCompleted) {
if (inputEvent == "HiFiBerry_Started\n" ) {
// turn on white led
digitalWrite(whiteLedPin, HIGH); // system is working
// ready turn off red led
digitalWrite(redLedPin, LOW);
digitalWrite(amberLedPin, LOW);
}
else if (inputEvent == "HiFiBerry_Source_Started\n" ) {
// ready turn on green led
digitalWrite(greenLedPin, HIGH);
digitalWrite(amberLedPin, LOW);
digitalWrite(redLedPin, LOW);
digitalWrite(whiteLedPin, HIGH); // may have missed started, but now know is system working
} else if (inputEvent == "HiFiBerry_Source_Stopped\n" ) {
// ready turn on green led
digitalWrite(greenLedPin, LOW);
digitalWrite(amberLedPin, LOW);
digitalWrite(redLedPin, LOW);
digitalWrite(whiteLedPin, HIGH); // may have missed started, but now know is system working
} else {
digitalWrite(amberLedPin, HIGH); // we are running, but unknown was command received
digitalWrite(redLedPin, LOW);
//Serial.println(inputEvent); // useful during development
}

// clear the string:
inputEvent = "";
eventCompleted = false;
}


// is mute pressed:
int muteButtonState = digitalRead(muteButtonPin);
if ((muteButtonState != prevMuteButtonState) && (muteButtonState == LOW) ) {
// Not Supported on HiFiBerryOS
//Consumer.write(MEDIA_VOLUME_MUTE);
// Use Play/Pause instead
//Keyboard.write(KEY_ENTER);
// Use Serial Message Interactions
Serial.println("HiFiBerry_Mute_Unmute");
}
prevMuteButtonState = muteButtonState;

// is volume up pressed:
int volUpButtonState = digitalRead(volUpButtonPin);
if (volUpButtonState == LOW) {
//Consumer.write(MEDIA_VOLUME_UP);
// Use Serial Message Interactions
Serial.println("HiFiBerry_Volume_Up");
++counter;
}

// is volume down pressed:
int volDnButtonState = digitalRead(volDnButtonPin);
if (volDnButtonState == LOW) {
//Consumer.write(MEDIA_VOLUME_DOWN);
// Use Serial Message Interactions
Serial.println("HiFiBerry_Volume_Down");
++counter;
}

// Buttons are no longer pressed, so clear counter
if ( (volUpButtonState == HIGH) && (volDnButtonState == HIGH) ) {
counter = 0;
}

// D-Bounce (longer delay for first button press read)
if (counter == 1) {
delay(300);
} else {
delay(100);
}
}

 

This is the mapping for the Sonos Connect button panel which can use the same arduino program (wires slightly different). When looking at the buttons, with the connector to the left counting cable 1 from the bottom. :
1. Volume -
2. Volume +
3. White LED
4. Ground (-)
5. Amber LED
6. Ground (-)
7. Red LED
8. Green LED
9. Mute/Unmute
10. Shield

/Jens

0 comments

Please sign in to leave a comment.