Partie 1: Yet another internet radio!

Lors d'un apprentissage quelconque, il y a toujours une (ou plusieurs) étape(s) incontournables. Elles sont “pédagogiquement” essentielles pour valider une base qui servira de fondation pour l'épisode suivant.

En informatique par exemple, le célèbre Hello World sera probablement notre première ligne pour appendre à coder, avant de passer aux tableaux, aux suites, aux fonctions ... Pour ceux qui se demandent d'ailleurs d'où vient cette célèbre chaîne de caractère, la page Wikipedia à ce sujet apporte quelques éléments de réponse (datant de 1978) !

En couture, oui bon ... OK ... En couture, la tendance 2020 c'est de faire son masque... Point barre... Quelle année de merde.

La suite.

En électronique donc, il y a aussi des incontournables forcément. Surtout après avoir fait clignoter sa première LED. Un petit pas pour l'homme...

Ce mois-ci, je me suis mis en tête de revisiter un standard ... Fabriquer une machine à son pour mes longues journée de travail à la maison.

Une radio Internet, c'est un peu comme une recette de grand-mère... Chacun le fait à sa façon (environ 12 500 000 résultats).

Comme à l'habitude sur ce blog, je préfère raconter une démarche et donner des idées, plutôt que déballer un plan à suivre à la lettre.

Je reste persuadé que le meilleur apprentissage, c'est de creuser, fouiner, casser, réparer ... plutôt que de suivre un mode d'emploi.

Pour démarrer il faut un (vague) objectif

Mon idée de départ c'est donc de trouver une radio vintage et de remplacer son matériel par quelque chose de récent qui peut jouer des streams audios. Au hasard, un Raspberry Pi Zero (qui est pour moi un des meilleurs device à ce jour) avec MPD. C'est juste incroyable tout ce que l'on peut faire tourner sur ce petit machin ... et pour 30$ en plus !

Afin de ne pas dégoûter les puristes, il convient de trouver un modèle de radio joli, mais qui n'est ni rare, ni cher. Bref un truc cheap des années 70 irait potentiellement très bien.

Du coup, après avoir perdu mon temps dans Kijiji et différents magasins j'ai fini par trouver ce shop (qui est juste hallucinant). Un véritable musée cet endroit... Le vieux monsieur qui le tient la baraque est lui aussi un monument !

Montréal ... si tu savais comment je t'aime ...

Assez marrant le moment où j'ai commencé à lui demander s'il avait un modèle brisé en stock en tentant de lui expliquer que je voulais juste un case pour mon projet... Il a faillit me jeter dehors dans la minute.

“Ici tout fonctionne Monsieur ! Je ne vends pas des radios brisées , vous me prenez pour qui ?!”

La suite était un mélange d'arménien-grec-québécois-vieux-avec-dentier. Il n'avait pas l'air content de mes questions. Pas la peine de s'étendre. J'ai juste pris le moins cher en bois.

C'est vrai qu'elle marche en plus. On est quand même assez loin de la hifi niveau son... Elle n'a pas que le look vintage... Sans regret alors pour la suite.

Démontage.

Plan technique ?

Dans mon idée, je veux utiliser un microcontrôleur Arduino Nano pour gérer tout ce qui est interface physique (l'afficheur, boutons) et dédier le Raspberry Pi Zero à la gestion du son (avec MPD et son client MPC).

Les deux bidules doivent être interconnectés par un câble (sans Wifi) et pourront donc s'échanger différentes commandes via ce canal.

Par exemple, le mcu détecte l’événement quand le bouton de radio “chanson suivante” next est appuyé et il demande donc au Raspberry d’exécuter la commande mpc next.

Autre exemple; Le Raspberry lit le nom de la radio en cours de lecture et demande donc au mcu d'afficher le titre sur l'écran 2x 16 lignes en façade du boîtier.

Il en ira de même pour a peu près tout, comme la gestion du volume, les commandes play, stop, pause, etc ...

Le code du mcu sera donc écrit en langage Arduino et du côté du Pi, ça sera en Python.

Bon oui je sais. Quoi ?

On aurait pu tout faire avec juste le Raspberry ... en branchant les boutons et l'afficheur directement sur ses GPIO.

Oui mais...

Basé sur mon expérience, tout ce qui est interface physique est bien plus stable et rapide sur un mcu que sur un mini-ordinateur.

Y compris le temps de démarrage, la latence de réponse des boutons, le bruit et l'odeur (non je déconne). En tout cas, c'est important que l'expérience utilisateur soit bonne ... si on veut que le montage final soit vraiment utile ...

On ne va quand même pas avoir un afficheur LCD à vide tout le temps que monsieur Pi finisse de booter... N'est-ce pas ?

Good ! Alors on avance.

Interconnecter un Arduino et un PI

J'ai identifié 3 façons de connecter les deux ensembles:

J'ai choisi en série (donc UART). Par contre, ça sera sans utiliser les ports USB. Une fois de plus, c'est mon expérience qui m'influence... mais toi tu fais ce que veux.

Les ports USB des mcu sont fragiles et je trouve que l'on a une connectique bien plus stable en soudant sur des pins (plutôt que de mettre de la colle chaude partout).

La connexion série entre 2 devices est assez simple en théorie: Il faut juste croiser rx et tx. Donc, le rx du pi va se connecter sur le tx du mcu tandis que le tx du pi va se connecter sur le rx du mcu.

Toutefois, il y a un petit tweak dans ce cas... Il faut utiliser un petit circuit intermédiaire pour éviter de tout casser (surtout le Pi en fait).

Comment gérer la différence entre 5 V et 3.3 V

En effet, le Raspberry fonctionne en 3.3 Volts, tandis que le Arduino Nano lui fonctionne en 5 Volts. On ne peut donc pas les connecter directement.

Dans ce cas, on utilise un logic level adapter qui fait parfaitement la job de conversion des signaux dans le bon voltage. C'est très simple à mettre en place, il s'insère entre les deux et le tour est joué. Bien vérifier qu'il soit bi-directionnel car la conversion se fait dans les 2 sens de communication.

Il est évident (mais dans la vie il faut répéter) qu'il ne faut jamais brancher le port USB (que tu utilises pour coder+flasher le mcu avec ton PC) et les rx/tx vers le Pi au même moment.

Les pins série rx/tx du mcu sont bridgés avec la console série USB.

Pas de bêtise donc, on alterne la connexion tour à tour, quand on code/flashe via l'USB du PC et lorsque on teste la connexion avec le Pi.

Un peu de code !

La première étape est de vérifier la connexion série. Pour ça, on va demander à l'Arduino d'afficher son uptime sur la console série:

unsigned long time;

void setup() {
  Serial.begin(9600);
}
void loop() {
  Serial.print("Time: ");
  time = millis();

  Serial.println(time);
  delay(1000);
}

On peut vérifier la connexion depuis le Pi ...

pi@raspberrypi:~ $ screen -d /dev/ttyS0 9600
Time: 18127
Time: 19128
Time: 20127
^a^d

Putain c'est beau la techno des années 80... La suite ?

Installation du matériel

Comme afficheur sur la radio, j'utilise un LCD 2 lignes, 16 chars. Pas la peine de détailler son installation, il y a des millions de tutoriel sur le Web.

Pour les boutons c'est pareil. J'en ai prévu 5 sur la façade de la radio:

Afin de limiter le nombre de GPIO utilisé sur le mcu par les 5 boutons, j ai utilisé un Resistor_ladder. Cet article sur ce sujet est super bien fait <3

Cela permet d'avoir des niveaux analogiques différents (avec analogRead(), 1 niveau par bouton) sur 1 seule entrée analogique (A0 dans mon code).

A part de ça, rien à déclarer monsieur le douanier. La suite.

Un peu de code de (vrai) code !

L'étape suivante maintenant est de concocter un protocole de communication entre les 2 machines. On va faire simple. Oui toujours. Par les temps qui courent, la simplicité est devenu un art ...

Sur le canal série, tout ce qui envoyé par l'Arduino et qui commence par la chaîne de caractère mpc sera interprété par le Pi (donc en Python). Cela sera la commande a exécuter (process).

<arduino> mpc next
<pi> if line.startswith('mpc next') or line.startswith('mpc prev'):
          proc = subprocess.Popen(line, shell=True)
          proc.wait()

Dans l'autre sens c'est la même chose.

Tout ce qui commence par la chaîne de caractère lcd sera interprété par le mcu et affiché sur l'écran LCD.

<pi> lcd Now playing... Radio Nova
<arduino>   String str = Serial.readString();
                    message1 = param.substring(0, 17);
                    message2 = param.substring(16, 33);
                    ...
                    printlcd(message1, message2);

Quand tu liras le code, tu comprendras queprintlcd() n'existe pas nativement dans Arduino. J'ai juste fait quelques fonctions pour me faciliter la vie, mais je suis sûr que t'as pigé l'idée.

Il y a en pour gérer l'affichage “par défaut” (genre la station en cours d’écoute) et d'autre comme volume qui sont des messages temporaires. Quand tu montes le son cela affiche le niveau actuel, puis le mcu re-affiche la station en cours après une demi seconde.

Finalement, presque comme une “vraie” radio ... wow !

Pour éviter de surcharger cet article (sans fin), j'ai mis les PoC sur gist (code Arduino | code Python).

Le code final sera déposé dans l'épisode 2. A mon avis, cela sera une bonne base pour s'inspirer mais pas la peine de m'envoyer une PR... L'idée du DIY c'est aussi de se faire un méga truc sur-mesure.

Circuit audio et amplification

Pour le circuit audio, j'utilise un hat sur Pi de type Raspiaudio. Petite pièce de hardware disponible chez tous les bons dealers. Il convient de trouver un modèles qui est compatible au Pi Zero mais qui aussi ne bloque pas les GPIOs car nous en avons besoin.

On voit bien sur cette image qu'ils ont fait un breakout pour les pins du GPIOs.

Niveau speakers, j'ai utilisé un vieux système de son actif pour PC que j'ai désassemblé. Il a coûté 5$ dans le thrift store à côté de chez moi.

Vous avez probablement noté la présence du filtre passe-haut et medium qui permet d'avoir les 2 speakers par côté.

J'ai ensuite re-intégré le bordel dans le vieux boîtier radio.

Bon dans les faits, le circuit d'amplification s'est brisé dans le démontage. Je l'ai donc remplacé par un équivalent (tout en prenant soin de garder les filtres).

Après avoir valider que tout était fonctionnel sur l'établi, il est maintenant temps de passer le breadboard en prod! Oui, à la soudure ...

Dans le prochain épisode, la mise en place des PCB, l'impression 3D des façades et une mise à jour des logiciels pour supporter Spotify et une autre pour le multi-room... <3

Passez une belle journée.

^EOF

#arduino #raspberrypi