« I2L 2024 Groupe6 » : différence entre les versions

De wiki-se.plil.fr
Aller à la navigation Aller à la recherche
 
(53 versions intermédiaires par 4 utilisateurs non affichées)
Ligne 1 : Ligne 1 :
= Proposition de système =
= Proposition de système =
Un clavier midi constitué de 12 touches permettant de produire du son, 2 touches permettant d'augmenter ou diminuer d'un octave, et un bouton permettant de gérer le volume. Un écran affiche l'octave (de 0 à 7) et le volume (de 0 à 100).
Un clavier midi constitué de 12 touches permettant de produire du son, 2 touches permettant d'augmenter ou diminuer d'une octave, et un bouton permettant de gérer le volume. Un écran affiche l'octave (de 0 à 7) et le volume (de 0 à 100).


= Contre-proposition =
= Contre-proposition =
OK pour la proposition mais il est demandé impérativement d'implanter un périphérique USB de classe MIDI.
Pour la gestion des touches en matrice voyez le projet [https://projets-se.plil.fr/mediawiki/index.php/SE4Binome2024-1].
Pour la gestion de l'écran LCD vous pouvez vous inspirer du code des groupes 3 et 4 I2L en 2023/2024.
La démonstration MIDI de la bibliothèque LUFA semble être adaptée au projet. Vous pourriez d'ailleurs ajouter une fonctionnalité de cette démonstration consistant en le changement d'instrument. Pour cela vous pouvez utiliser une combinaison de touches comme appuyer simultanément sur un bouton de changment d'octave et sur une touche du clavier.
Si vous avez accès à un imprimante 3D vous pouvez tenter la fabrication de capuchons de touche à mettre sur les boutons poussoirs KAILH, regardez par exemple [https://www.stlfinder.com/3dmodels/?search=keys+piano].


= Proposition définitive =
= Proposition définitive =


Clavier MIDI :
Clavier MIDI :
- 4x4 boutons en matrice :


- 12 boutons de touches de piano  
4x4 boutons en matrice dont
- 2 boutons pour changer d'octave
* 12 boutons de touches de piano  
- un potentiometre pour régler le son
* 2 boutons pour changer d'octave
* un potentiomètre pour régler le son
 
Un écran LCD pour afficher l'octave sur laquelle on est actuellement.


Le code doit utiliser un libraire permettant de bancher le clavier en MIDI et de le passer en USB pour le lire sur une application adaptée.
Le code doit utiliser une bibliothèque permettant de bancher le clavier en MIDI et de le passer en USB pour le lire sur une application adaptée.


= Répartition du travail =
= Répartition du travail =
Ligne 19 : Ligne 31 :
= Carte =
= Carte =


Schémas initiaux :
== Schéma initial ==
* schéma n°1 : [[File:I2L-2024-Carte-G6a.zip]]
 
* schéma n°2 : [[File:I2L-2024-Carte-G6b.zip]]
[[Fichier:I2L-2024-Carte-G6a.png|thumb]]
 
* schéma : [[File:I2L-2024-Carte-G6a.zip]]
 
<p style="clear: both; />
 
== Carte routée ==
[[Fichier:I2L-2024-Schema-G6-v0.pdf|thumb|left|Schéma de la carte]]
[[Fichier:I2L-2024-PCB-G6-v0.png|thumb|right|vue de la carte]]
 
<p style="clear: both; />
 
== Composants ==
* ATmega32u4 : disponible
* quartz GND24 : disponible
* perle ferrite MH2029-300Y : commandée
* potentiomètre écran : disponible
* potentiomètre volume : disponible
* connecteur femelle 16 contacts : commandé
* écran LCD 2 lignes : commandé
* touches KAILH BOX-BLACK : disponibles
 
=== Carte au 23/02/2025 ===
 
[[File:ISL-2024-G6-Realisation-A.jpg|thumb|center|400px|Première réalisation]]
 
=== Carte au 27/02/2025 ===
[[Fichier:ISL-2024-G6-Realisation-B.jpg|vignette|Carte avec la quasi totalité des composants insérés|centré]]


= Montage =
Non encore réalisé :
* ajouter la perle de ferrite.
 
=== Carte au 07/03/2025 ===
[[Fichier:ISL-2024-G6-Realisation-C.jpg|vignette|Carte terminée|centré]]
 
= Fontionnement =
La carte est un clavier MIDI, cela permet d'émuler un instrument sur un logiciel de MAO (Musique assistée par Ordinateur).
 
La carte possède :
 
* 18 touches de piano
* Un potentiomètre, qui peut être affecté à n'importe qu'elle fonction dans le logiciel (volume, effets...)
* Deux touches + et - permettant d'augmenter ou de diminuer l'octave (de 1 à 7). En appuyant simultanément sur les touches, le clavier bascule en mode sélection d'instrument, et les 2 boutons permettent de cycler entre les instruments.
* Un écran LCD permettant de visualiser l'instrument, le volume (ou autre fonction) actuel, l'octave actuelle.
 
 
Les instruments disponibles sont :
* Piano
* Pad (Famille de son d'un synthétiseur)
* Trompette
* Violon
* Basse
* Guitare
* Percussion
* Drums (Batterie)
 
 
 
Au niveau du clavier, l'oublie de diodes sur la matrice de boutons fait que nous ne pouvons appuyer que sur 2 boutons simultanément au maximum, sinon nous avons des boutons fantômes.
 
Nous avons également un problème électrique au niveau du potentiomètre qui va de 0V à environ 0.7V au lieu de 5V, de plus il n'est pas linéaire ce qui ne le rend pas facile à utiliser.
 
 
 
Pour tester la carte:
 
* En ligne: https://signal.vercel.app/edit, ce site permet de jouer de la musique, de tester le changement d'instrument et d'octave.
* Logiciels de MAO utilisés: Ableton, FL Studio, ce sont des logiciels payant qui permettent de tester le potentiomètre
 
Nous avons eu besoin des 2 plateformes pour tester la carte, car les sites web permettant de jouer du MIDI sont minimalistes, et acceptent les fonctions MIDI de base comme le changement d'instrument. En revanche, ils ne prennent souvent pas en compte le potentiomètre. Les logiciels de MAO eux, ont tendance à ignorer les fonctions prédéfinies par le MIDI (notamment la sélection d'instrument et des effets), car ils gèrent cela eux même, c'est pourquoi notre potentiomètre est configuré pour envoyer des données sur le canal MIDI 14, qui n'est assigné à rien. L'association du potentiomètre à une fonction se fait dans le logiciel. Nous pouvons quand même utiliser le clavier et changer les octaves.
 
 
Ressource utiles :
 
Listes des commandes disponibles dans MIDI pour le potentiomètre : https://anotherproducer.com/online-tools-for-musicians/midi-cc-list/
 
Liste des commandes MIDI non assignées : https://anotherproducer.com/online-tools-for-musicians/midi-cc-list/#undefined
 
Liste des instruments disponibles dans MIDI : https://musicordes.fr/tableau-des-128-instruments-general-midi/
 
Logiciel qui permet de voir toutes les entrées sorties MIDI d'un périphérique, utile pour programmer: https://hautetechnique.com/midi/midiview/


= Code =
= Code =
Nous avons modifié le template MIDI fournit dans la lufa pour plus de lisibilité:
A la racine nous avons le dossier lufa sur lequel nous n'avons rien modifié, et le dossier app/ avec :
*Hardware.c : Initialisation de l'usb et des entrées sorties, gestion du potentiomètre
*HD44780.c : Fonctions de l'écran LCD
*Keyboard.c : Scan et traitement de l'appui sur les boutons
*Midi.c : Envoi des commandes MIDI et gestions des octaves
*Descriptors.c : Fichier de description du périphérique (fourni avec la lufa)
*Globals.h : Définition des constantes et des struct
*main.c : Boucle principale et définition des variables globales
Quelques extraits de code:
Scan de la matrice de bouton:<syntaxhighlight lang="c">
void scanKeyboard(void) {
for(uint8_t l = 0; l < NB_LINES ; l++) {
*lines[l].port &= ~(1 << lines[l].bit);
for(uint8_t c = 0; c < NB_COLS; c++) {
int t = l * NB_COLS + c;
if(!(*cols[c].pin & (1 << cols[c].bit))) {
if(!buttonPressed[t]){
buttonPressed[t] = true;
isPressed = t;
isReleased = -1;
toProcess = true;
}
} else {
if(buttonPressed[t]){
buttonPressed[t] = false;
isReleased = t;
isPressed = -1;
toProcess = true;
}
}
}
*lines[l].port |= (1 << lines[l].bit);
}
}
</syntaxhighlight>
Nous avons créé une structure de données pour lier un bouton à une note MIDI. Par défaut le clavier est sur le 3ème octave.
Table des notes MIDI : https://computermusicresource.com/midikeys.html<syntaxhighlight lang="c">
// 60 to 71 => Octave 3 in order C, C#, D, D#, E, F, F#, G, G#, A, A#, B
// 72 TO 77 => Octave 4 up to F
NoteMIDI notes[NB_NOTES] = {
{4, 60}, {3, 61}, {1, 62}, {2, 63}, {0, 64}, {9, 65},
{8, 66}, {7, 67}, {6, 68}, {5, 69}, {14, 70}, {13, 71},
{12, 72}, {11, 73}, {10, 74}, {19, 75}, {18, 76}, {17, 77}
};
</syntaxhighlight>
Concernant le volume (potentiomètre) :<syntaxhighlight lang="c">
/* Capture the adc value */
unsigned int ad_capture(void){
    ADCSRA |= (1<<ADSC);                      // Start conversion
    while(bit_is_set(ADCSRA, ADSC));          // Wait for conversion to complete
    return ADCH;                              // Return 8-bit result (0-255)
}
/* Convert the ADC value to a volume */
uint8_t convert_volume(uint8_t volume, uint8_t maxVolume) {
return (volume * maxVolume) / MAX_POT;
}
/* In the main loop */
uint8_t newReading = ad_capture();
filteredVolume = (FILTER_WEIGHT * filteredVolume) + ((1 - FILTER_WEIGHT) * newReading); // Prevent the oscillation from sending too many messages
uint8_t newVolume = (uint8_t)filteredVolume > MAX_POT ? MAX_POT : (uint8_t)filteredVolume;
if (volume != newVolume) {
    volume = newVolume;
    lcdVolume = convert_volume(volume, MAX_VOLUME_LCD);
    midiVolume = convert_volume(volume, MAX_VOLUME_MIDI);
    MIDICommand = MIDI_COMMAND_CONTROL_CHANGE;
    HD44780_GoTo(20);
    HD44780_WriteInteger(lcdVolume, 10);
    HD44780_WriteString("  ");
}
/* Example of MIDI Command sending (Volume here) */
if (MIDICommand == MIDI_COMMAND_CONTROL_CHANGE) {
    MIDI_EventPacket_t MIDIEvent = (MIDI_EventPacket_t)
        {
            .Event    = (MIDI_EVENT(0, MIDICommand)),
            .Data1    = MIDICommand | MIDI_CHANNEL(1),
            .Data2    = 14,
            .Data3    = midiVolume
        };
    Endpoint_Write_Stream_LE(&MIDIEvent, sizeof(MIDIEvent), NULL);
    Endpoint_ClearIN();
</syntaxhighlight>
Changement d'octave ou d'instrument : <syntaxhighlight lang="c">
        if (isReleased == BUTTON_OCTAVE_UP && toProcess && currentState != WAIT_RELEASE) {
            if (mode == MODE_OCTAVE) {
                octaveUp();
                HD44780_GoTo(31);
                HD44780_WriteInteger(octave, 10);
                isReleased = -1;
            } else if (mode == MODE_INSTRUMENT) {
                if (currentInstrument < NB_INSTRUMENTS - 1) {
                    currentInstrument++;
                } else {
                    currentInstrument = 0;
                }
                MIDICommand = MIDI_COMMAND_PROGRAM_CHANGE;
                HD44780_GoTo(0);
                HD44780_WriteString("            ");
                HD44780_GoTo(0);
                HD44780_WriteString(instruments[currentInstrument].instrumentName);
               
                isReleased = -1;
            }
        }
</syntaxhighlight>
Pour charger le programme sur la carte nous avons modifié le makefile pour y ajouter 2 commandes :
* make clean: Nettoie les fichiers de build générés
* make upload: Charge le programme sur la carte


= Démonstrations =
= Démonstrations =
<gallery mode="traditional" widths="300" heights="200">
Fichier:Piano demo.mp4|Démonstration du clavier
Fichier:Octave.mov|Changement d'octave
Fichier:Instruments.mov|Changement d'instrument
Fichier:Volume.mov|Exemple de gestion de volume avec le potentiomètre
Fichier:Signal.mov|Exemple d'utilisation du potentiomètre pour changer la forme du signal (sinusoide, signal triangulaire, carré...)
Fichier: Startup.mov|Séquence de démarrage
</gallery>


= Rendus =
= Rendus =

Version actuelle datée du 25 avril 2025 à 18:20

Proposition de système

Un clavier midi constitué de 12 touches permettant de produire du son, 2 touches permettant d'augmenter ou diminuer d'une octave, et un bouton permettant de gérer le volume. Un écran affiche l'octave (de 0 à 7) et le volume (de 0 à 100).

Contre-proposition

OK pour la proposition mais il est demandé impérativement d'implanter un périphérique USB de classe MIDI.

Pour la gestion des touches en matrice voyez le projet [1].

Pour la gestion de l'écran LCD vous pouvez vous inspirer du code des groupes 3 et 4 I2L en 2023/2024.

La démonstration MIDI de la bibliothèque LUFA semble être adaptée au projet. Vous pourriez d'ailleurs ajouter une fonctionnalité de cette démonstration consistant en le changement d'instrument. Pour cela vous pouvez utiliser une combinaison de touches comme appuyer simultanément sur un bouton de changment d'octave et sur une touche du clavier.

Si vous avez accès à un imprimante 3D vous pouvez tenter la fabrication de capuchons de touche à mettre sur les boutons poussoirs KAILH, regardez par exemple [2].

Proposition définitive

Clavier MIDI :

4x4 boutons en matrice dont

  • 12 boutons de touches de piano
  • 2 boutons pour changer d'octave
  • un potentiomètre pour régler le son

Un écran LCD pour afficher l'octave sur laquelle on est actuellement.

Le code doit utiliser une bibliothèque permettant de bancher le clavier en MIDI et de le passer en USB pour le lire sur une application adaptée.

Répartition du travail

Carte

Schéma initial

I2L-2024-Carte-G6a.png

Carte routée

Schéma de la carte
vue de la carte

Composants

  • ATmega32u4 : disponible
  • quartz GND24 : disponible
  • perle ferrite MH2029-300Y : commandée
  • potentiomètre écran : disponible
  • potentiomètre volume : disponible
  • connecteur femelle 16 contacts : commandé
  • écran LCD 2 lignes : commandé
  • touches KAILH BOX-BLACK : disponibles

Carte au 23/02/2025

Première réalisation

Carte au 27/02/2025

Carte avec la quasi totalité des composants insérés

Non encore réalisé :

  • ajouter la perle de ferrite.

Carte au 07/03/2025

Fontionnement

La carte est un clavier MIDI, cela permet d'émuler un instrument sur un logiciel de MAO (Musique assistée par Ordinateur).

La carte possède :

  • 18 touches de piano
  • Un potentiomètre, qui peut être affecté à n'importe qu'elle fonction dans le logiciel (volume, effets...)
  • Deux touches + et - permettant d'augmenter ou de diminuer l'octave (de 1 à 7). En appuyant simultanément sur les touches, le clavier bascule en mode sélection d'instrument, et les 2 boutons permettent de cycler entre les instruments.
  • Un écran LCD permettant de visualiser l'instrument, le volume (ou autre fonction) actuel, l'octave actuelle.


Les instruments disponibles sont :

  • Piano
  • Pad (Famille de son d'un synthétiseur)
  • Trompette
  • Violon
  • Basse
  • Guitare
  • Percussion
  • Drums (Batterie)


Au niveau du clavier, l'oublie de diodes sur la matrice de boutons fait que nous ne pouvons appuyer que sur 2 boutons simultanément au maximum, sinon nous avons des boutons fantômes.

Nous avons également un problème électrique au niveau du potentiomètre qui va de 0V à environ 0.7V au lieu de 5V, de plus il n'est pas linéaire ce qui ne le rend pas facile à utiliser.


Pour tester la carte:

  • En ligne: https://signal.vercel.app/edit, ce site permet de jouer de la musique, de tester le changement d'instrument et d'octave.
  • Logiciels de MAO utilisés: Ableton, FL Studio, ce sont des logiciels payant qui permettent de tester le potentiomètre

Nous avons eu besoin des 2 plateformes pour tester la carte, car les sites web permettant de jouer du MIDI sont minimalistes, et acceptent les fonctions MIDI de base comme le changement d'instrument. En revanche, ils ne prennent souvent pas en compte le potentiomètre. Les logiciels de MAO eux, ont tendance à ignorer les fonctions prédéfinies par le MIDI (notamment la sélection d'instrument et des effets), car ils gèrent cela eux même, c'est pourquoi notre potentiomètre est configuré pour envoyer des données sur le canal MIDI 14, qui n'est assigné à rien. L'association du potentiomètre à une fonction se fait dans le logiciel. Nous pouvons quand même utiliser le clavier et changer les octaves.


Ressource utiles :

Listes des commandes disponibles dans MIDI pour le potentiomètre : https://anotherproducer.com/online-tools-for-musicians/midi-cc-list/

Liste des commandes MIDI non assignées : https://anotherproducer.com/online-tools-for-musicians/midi-cc-list/#undefined

Liste des instruments disponibles dans MIDI : https://musicordes.fr/tableau-des-128-instruments-general-midi/

Logiciel qui permet de voir toutes les entrées sorties MIDI d'un périphérique, utile pour programmer: https://hautetechnique.com/midi/midiview/

Code

Nous avons modifié le template MIDI fournit dans la lufa pour plus de lisibilité:

A la racine nous avons le dossier lufa sur lequel nous n'avons rien modifié, et le dossier app/ avec :

  • Hardware.c : Initialisation de l'usb et des entrées sorties, gestion du potentiomètre
  • HD44780.c : Fonctions de l'écran LCD
  • Keyboard.c : Scan et traitement de l'appui sur les boutons
  • Midi.c : Envoi des commandes MIDI et gestions des octaves
  • Descriptors.c : Fichier de description du périphérique (fourni avec la lufa)
  • Globals.h : Définition des constantes et des struct
  • main.c : Boucle principale et définition des variables globales


Quelques extraits de code:

Scan de la matrice de bouton:

void scanKeyboard(void) {
	for(uint8_t l = 0; l < NB_LINES ; l++) {

		*lines[l].port &= ~(1 << lines[l].bit);

		for(uint8_t c = 0; c < NB_COLS; c++) {

			int t = l * NB_COLS + c;

			if(!(*cols[c].pin & (1 << cols[c].bit))) {
				if(!buttonPressed[t]){
					buttonPressed[t] = true;
					isPressed = t;
					isReleased = -1;
					toProcess = true;
				}
			} else {
				if(buttonPressed[t]){
					buttonPressed[t] = false;
					isReleased = t;
					isPressed = -1;
					toProcess = true;
				} 			
			}	
		}

		*lines[l].port |= (1 << lines[l].bit);
	}
}


Nous avons créé une structure de données pour lier un bouton à une note MIDI. Par défaut le clavier est sur le 3ème octave.

Table des notes MIDI : https://computermusicresource.com/midikeys.html

// 60 to 71 => Octave 3 in order C, C#, D, D#, E, F, F#, G, G#, A, A#, B
// 72 TO 77 => Octave 4 up to F
NoteMIDI notes[NB_NOTES] = { 
	{4, 60}, {3, 61}, {1, 62}, {2, 63}, {0, 64}, {9, 65},
	{8, 66}, {7, 67}, {6, 68}, {5, 69}, {14, 70}, {13, 71},
	{12, 72}, {11, 73}, {10, 74}, {19, 75}, {18, 76}, {17, 77}
};


Concernant le volume (potentiomètre) :

/* Capture the adc value */
unsigned int ad_capture(void){
    ADCSRA |= (1<<ADSC);                      // Start conversion
    while(bit_is_set(ADCSRA, ADSC));          // Wait for conversion to complete
    return ADCH;                              // Return 8-bit result (0-255)
}

/* Convert the ADC value to a volume */
uint8_t convert_volume(uint8_t volume, uint8_t maxVolume) {
	return (volume * maxVolume) / MAX_POT; 
}

/* In the main loop */
uint8_t newReading = ad_capture();
filteredVolume = (FILTER_WEIGHT * filteredVolume) + ((1 - FILTER_WEIGHT) * newReading); // Prevent the oscillation from sending too many messages
uint8_t newVolume = (uint8_t)filteredVolume > MAX_POT ? MAX_POT : (uint8_t)filteredVolume;
if (volume != newVolume) {
    volume = newVolume;
    lcdVolume = convert_volume(volume, MAX_VOLUME_LCD);
    midiVolume = convert_volume(volume, MAX_VOLUME_MIDI);

    MIDICommand = MIDI_COMMAND_CONTROL_CHANGE;
    HD44780_GoTo(20);
    HD44780_WriteInteger(lcdVolume, 10);
    HD44780_WriteString("  ");
} 

/* Example of MIDI Command sending (Volume here) */
if (MIDICommand == MIDI_COMMAND_CONTROL_CHANGE) {
    MIDI_EventPacket_t MIDIEvent = (MIDI_EventPacket_t)
        {
            .Event    = (MIDI_EVENT(0, MIDICommand)),

            .Data1    = MIDICommand | MIDI_CHANNEL(1),
            .Data2    = 14,
            .Data3    = midiVolume
        };

    Endpoint_Write_Stream_LE(&MIDIEvent, sizeof(MIDIEvent), NULL);
    Endpoint_ClearIN();


Changement d'octave ou d'instrument :

        if (isReleased == BUTTON_OCTAVE_UP && toProcess && currentState != WAIT_RELEASE) {
            if (mode == MODE_OCTAVE) {
                octaveUp();
                HD44780_GoTo(31);
                HD44780_WriteInteger(octave, 10);
                isReleased = -1;
            } else if (mode == MODE_INSTRUMENT) {
                if (currentInstrument < NB_INSTRUMENTS - 1) {
                    currentInstrument++;
                } else {
                    currentInstrument = 0;
                }

                MIDICommand = MIDI_COMMAND_PROGRAM_CHANGE;
                HD44780_GoTo(0);
                HD44780_WriteString("             ");
                HD44780_GoTo(0);
                HD44780_WriteString(instruments[currentInstrument].instrumentName);
                
                isReleased = -1;
            }
        }

Pour charger le programme sur la carte nous avons modifié le makefile pour y ajouter 2 commandes :

  • make clean: Nettoie les fichiers de build générés
  • make upload: Charge le programme sur la carte

Démonstrations

Rendus

Projet KiCAD : Fichier:I2L-2024-Carte-G6.zip

Programmes : Fichier:I2L-2024-Programmes-G6.zip