Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

26
Proyecto OpenPipe: Diseño Conceptual de un Controlador MIDI 09 de Abril de 2007 (primera versión pública, por completar) http://openpipe.wordpress.com/ 2007 © Santiago José Barro Torres <[email protected] > Estudiante de Quinto curso de Ingeniería Informática Facultade de Informática Universidade da Coruña

Transcript of Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Page 1: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Proyecto OpenPipe: Diseño Conceptual de un Controlador MIDI

09 de Abril de 2007 (primera versión pública, por completar)

http://openpipe.wordpress.com/

2007 © Santiago José Barro Torres <[email protected]>

Estudiante de Quinto curso de Ingeniería Informática

Facultade de Informática

Universidade da Coruña

Page 2: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Objetivo del Documento

En ingeniería de sistemas, el diseño conceptual siempre precede al diseño

físico y a la implementación. El diseño conceptual pretende dar una visión de

alto nivel del sistema que se va a construir, de forma simbólica. Es de gran

ayuda para su comprensión y asimilación por parte de los ingenieros y los

usuarios, y también permite el establecimiento de pautas y metodologías

dentro del diseño de sistemas, dotando de orden y sentido a ésta actividad.

Un diseño conceptual es un modelo construido sobre papel, a un nivel alto de

abstracción. A su vez, un modelo es una abstracción de una parte de la

realidad, un pequeño minimundo (en nuestro caso, un sistema informático) que

tratamos de describir formalmente. Abstracción significa discernir entre

importante y no importante, relevante e irrelevante; por lo que es, en última

instancia, decisión del ingeniero el escoger la granularidad o nivel de detalle

con el que se va a describir el modelo. Es decir, la pregunta principal es: En mi

nivel de abstracción, ¿qué es importante para mí? ¿Qué detalles puedo obviar?

Sin embargo, habitualmente no basta con un único modelo para describir un

sistema:

Un diseño físico es “práctico”, en el sentido que es el único imprescindible para

iniciar la construcción e implementación del sistema. Sin embargo, el diseño

físico está atado a la tecnología predominante en un instante de tiempo; por lo

que un cambio en la tecnología significa un cambio en el diseño físico. Por el

contrario, el diseño conceptual a partir del cual debería haber surgido el diseño

físico se mantiene, en un caso ideal, prácticamente constante. Además, un

diseño físico es un modelo a un nivel demasiado bajo, en el sentido de que es

mucho más complicado encontrar los errores conceptuales (o de alto nivel) que

se producen inherentemente durante el proceso de diseño.

Page 3: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

El diseño conceptual es un primer paso fundamental en el diseño de un

sistema. Pero aún así, el diseño conceptual sigue siendo insuficiente, ya que no

proporciona los detalles suficientes como para construir el sistema real.

Necesitamos un diseño físico, concreto, que nos diga cómo implementar el

sistema a partir de cada uno de sus subsistemas; o que al menos proporcione

directrices generales que puedan servir de guía.

Como conclusión sacamos que ni el diseño conceptual ni el diseño físico son,

en general, suficientes por sí solos.

El Proyecto OpenPipe y el Diseño Conceptual

El presente documento forma parte del proyecto OpenPipe, cuyo objetivo

principal es el diseño e implementación de un controlador MIDI con apariencia

de una flauta o de una gaita.

Esquema Conceptual de la OpenPipe

Como veremos, OpenPipe no es un dispositivo excesivamente complejo. La

mayor parte de su funcionalidad la realizará un microcontrolador (situado

Page 4: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

dentro de la Unidad de Procesamiento), que no es más que un circuito

integrado con capacidad de control (ejecución de programas). Como

consecuencia, el diseño conceptual estará centrado en definir la estructura de

cada uno de los componentes y su interconexión con el microcontrolador, que

será el encargado de traducir la información musical obtenida del cilindro con

“sensores” a información MIDI interpretable por otro dispositivo externo

conectado a la interfaz de salida MIDI (un ordenador, un sintetizador, un

secuenciador...).

El principal problema de un diseño “hardware”, como es el caso de OpenPipe,

es que determinados componentes pueden ser difíciles de encontrar, ya sea

por estar anticuados, o porque la empresa que los fabricaba ha decidido

retirarlos de su catálogo. Ello no significa que no se pueda implementar la

OpenPipe, ya que posiblemente existan componentes alternativos de ese u

otro fabricante perfectamente válidos. Lo que sucede es que probablemente

habrá que modificar ligeramente el diseño físico, exigiendo parte de

conocimientos por parte de la persona que finalmente decide implementar la

OpenPipe.

Un segundo problema surge a raíz de su naturaleza OpenSource. Los

microcontroladores son dispositivos muy variados, y habitualmente cada

familia tiene su propio software de programación (ensambladores, enlazadores,

compiladores...) creados por sus propios fabricantes o terceros, que conocen la

implementación del microcontrolador. Esa implementación no es pública, por lo

que es complicado que exista software libre para la programación del

microcontrolador que nosotros hemos elegido (existe software libre de

programción para los modelos de microcontroladores más populares, como

pueden ser determinadas familias de los PIC, o algunos modelos “clásicos”,

como el 8051, por ejemplo).

Es más, cuando alguien compra una tarjeta de evaluación (una tarjeta en la

que se puede programar y probar el microcontrolador), es habitual que el

fabricante ya incluya software de programación. Lo cual complica tener un

Page 5: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

único diseño físico para OpenPipe, pues un programa en ensamblador para una

familia de microcontroladores generalmente no es reutilizable directamente

para otra familia de microcontroladores. ¡El código en ensamblador no se

caracteriza precisamente por ser portable! ¡Todo lo contrario! Es específico

para cada familia de microcontroladores, o en el peor de los casos,

dependiente incluso de un modelo particular de una familia de

microcontroladores.

Los dos problemas anteriores recalcan la importancia de tener un diseño

conceptual para la OpenPipe. Quien quiera implementar la OpenPipe, tendrá

que formalizar el diseño físico adecuado para su caso. Probablemente, cada

ingeniero tendrá sus preferencias respecto a microcontroladores. Mi tutor [1]

es un amante de la familia 8051, en cambio hay muchos estudiantes que están

más aficionados a los PIC.

¡Que cada uno escoja el que más le guste! Sin embargo, el modelo conceptual

seguirá siendo válido, en todo caso. En caso de que otras personas hagan

implementaciones para otros microcontroladores, se publicarían en la web del

proyecto http://openpipe.wordpress.com/.

De todas formas, aunque es un diseño conceptual, se han incluído pautas de

diseño que, de alguna forma, lo complementan.

Page 6: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Definición de Controlador MIDI

En pocas palabras, y definido de forma sencilla, un controlador MIDI no es más

que un dispositivo lógico (implementado en software) o un dispositivo físico

(implementado en hardware) que produce mensajes MIDI a partir de la

ocurrencia de una serie de eventos producidos por la interacción con un

usuario.

¿Qué es un evento? Un evento no es más que un determinado hecho que ha

ocurrido o que ocurrirá en un determinado instante del tiempo. Normalmente,

para nosotros (como programadores) la ocurrencia de un evento tendrá

asociada la ejecución de un determinada acción.

Por ejemplo, para una aplicación visual (es decir, con interfaz gráfica), que el

usuario haga clic sobre un determinado botón puede significar un evento.

Probablemente, cuando ocurra el evento “el usuario ha hecho clic sobre el

botón X”, desearemos ejecutar una determinada porción de nuestro código.

Por tanto, en la programación visual es bastante normal programar de forma

orientada a eventos.

El concepto de “evento” es intencionadamente poco concreto, puesto que en

principio, cualquier hecho puede ser potencialmente un evento. ¿Cuál es la

frontera entre un hecho y un evento? Como hemos comentado anteriormente,

un evento tiene un significado especial para nosotros, pues estamos

interesados en saber en qué momento tiene lugar su ocurrencia, para actuar

en consecuencia. Es el propio programador quien define qué eventos quiere

controlar, y como cabría esperar, son específicos para cada aplicación.

En el caso de un controlador MIDI, un evento es cualquier tipo de hecho

relacionado con la interpretación de un músico, cuya ocurrencia sea relevante

Page 7: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

para la posterior ejecución del sonido por parte de un sintetizador. Por ejemplo,

si deseamos crear un controlador MIDI con apariencia de piano, un posible

evento sería la pulsación por parte del pianista de una tecla, ya que

posiblemente querremos iniciar la ejecución de una nota cuando el pianista

pulse una tecla. Como cabría esperar, que un pianista deje de pulsar una tecla

también podría ser un evento, éste asociado con la finalización de la ejecución

de la nota anteriormente iniciada.

Sin embargo, mientras tengamos medios para detectar un evento, podemos

definir el número que nosotros queramos. La idea es determinar qué eventos

son importantes de cara a simular el comportamiento de un instrumento real,

lo cual depende del instrumento en cuestión. Por ejemplo, en el modelo del

piano, sería interesante que la intensidad del sonido fuese proporcional a la

intensidad con que el pianista ha pulsado la tecla.

Lo anterior no sería válido si en vez de diseñar un controlador para un piano,

quisiésemos diseñar un controlador para un violín o para una flauta. Para el

caso de un controlador MIDI con apariencia de violín, estaríamos interesados

en saber en qué momento el músico frota y deja de frotar una cuerda con el

arco, lo cual constituirían sendos eventos. Para el caso de un controlador MIDI

con apariencia de flauta, estaríamos interesados en saber qué agujeros está

tapando y destapando en un determinado instante, lo cual constituirían el

evento principal.

De todas formas, aunque los eventos que estamos monitorizando en cada caso

sean completamente distintos entre sí (¿verdad que no es lo mismo pulsar una

tecla que frotar una cuerda?), podemos seguir hablando de evento como un

hecho abstracto. Al fin y al cabo, aunque sean eventos distintos, tanto al pulsar

una tecla en un piano como al frotar una cuerda en un violín implican acciones

similares: Inicio de ejecución de una nota.

Page 8: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Capturando Eventos

Ahora viene el problema, ¿cómo capturamos los eventos? En el caso de un

controlador software el problema es trivial, ya que son los propios lenguajes de

programación los encargados de capturar el evento. El programador no tiene

más que proporcionar una implementación para la función de callback que el

lenguaje de programación invocará cuando se produzca el evento deseado. Por

ejemplo, en el caso de Java:

JButton boton = new JButton(“Púlsame”);boton.addActionListener(new ActionListener() {

public void actionPerformed(ActionEvent e) {/* Aquí iría la acción asociada al evento */System.out.println(“¡Me han pulsado!”);

}});

En el caso de un controlador hardware, el problema es más complicado, ya que

necesitamos dispositivos electromecánicos que sean capaces de detectar el

evento deseado. En el ejemplo del piano, necesitamos que, de alguna forma, la

tecla nos proporcione información del estado de su pulsación por medio de

señales eléctricas. Si además queremos conocer la intensidad con que la tecla

ha sido pulsada, la tecla es quien ha de proveer dicha información mediante

otra señal eléctrica.

Para capturar eventos, podemos utilizar cualquier tipo de dispositivo que nos

imaginemos. La complejidad puede ser tan grande o tan pequeña como

nosotros queramos, siempre al alcance de nuestras posibilidades. No habría

ningún problema en utilizar pulsadores o interruptores convencionales. Ahora

bien, a la hora de interpretar melodías, ¡notaremos que nuestro diseño, aún

siendo correcto, es poco práctico!

Se recomienda consultar los catálogos de tiendas de electrónica por internet.

Hay bastantes posibilidades de encontrar sensores u otros dispositivos a partir

Page 9: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

de los cuales podamos capturar los eventos que deseamos. ¡Es cuestión de

tener paciencia y afán de investigación!

Capturando eventos en OpenPipe

Como seguramente muchos ya sabréis, el objetivo del proyecto OpenPipe es

proporcionar el diseño de un controlador MIDI con apariencia de flauta o gaita.

Todo lo comentado hasta ahora también es válido para OpenPipe, pero

aplicado al caso particular de los flautistas o gaiteiros.

¿Cuál es el evento más importante a detectar en éste tipo de vientos? Pues sin

duda, es indispensable conocer qué agujeros están tapados o destapados en

un determinado instante. Grosso modo, el flautista toca diversas notas tapando

unos agujeros u otros. La flauta, como muchos otros instrumentos de viento,

tiene una serie de “posturas” asociadas para cada nota que puede tocar. El

conjunto de todas las “posturas” que puede tocar un instrumento constituye la

digitación.

Para el caso de la flauta, existen dos digitaciones alternativas: La digitación

alemana, y la digitación barroca. Con ambas digitaciones se pueden conseguir

el mismo número de notas, lo que sucede es que, en determinadas notas, la

“postura” asociada es distinta. Quien lo notará, principalmente, es el

intérprete. De cara al espectador que escucha, no habrá prácticamente

diferencia (¡a menos que sea tan ávido como para llevar cuenta de los agujeros

que tapa y destapa, lo cual personalmente me parece improbable!).

Durante algún tiempo estuve buscando por la red algún tipo de sensor que

fuese capaz de detectar la pulsación de un dedo, no de forma mecánica (no un

pulsador), sino de forma sensitiva. Mirándolo desde el punto de vista del

intérprete, lo más cómodo es que el “sensor” en cuestión cambie de estado

simplemente con posar el dedo encima, y nunca pulsando un elemento

mecánico, ya que resultaría en un aparato engorro de utilizar.

Page 10: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Después de una búsqueda incesante, sin ningún resultado positivo, decidí

pedirle ayuda al que será mi tutor en el proyecto fin de carrera [1]. Cuando

entendió lo que quería hacer (relativo al “sensor”), me propuso un circuito tan

sencillo como el siguiente:

Esquema propuesto del “sensor” que capturará los eventos.

Los que tengan conocimientos de electrónica, sabrán que es un circuito

bastante sencillo. No es más que un generador de tensión conectado a una

impedancia (o resistencia). La idea es la siguiente: Nuestro cuerpo también

genera internamente electricidad. Si tocamos con nuestra mano un punto

cualquiera del circuito mostrado en la figura, introducimos una pequeña

componente de corriente, de unos pocos miliamperios (la cantidad aproximada

habría que estimarla experimentalmente). Si además la resistencia es lo

suficientemente grande, la corriente que circula por el circuito es pequeña

(recordemos la fórmula de Ohm V = IR), por lo que llegará un momento en el

que la corriente introducida por una persona al tocar el circuito será lo

suficientemente significativa como para detectar cuándo se está tocando el

circuito, y cuándo no.

En definitiva, con los valores de tensión y resistencia adecuados, cuando una

persona toque el circuito, se producirá un aumento significativo en la tensión

Page 11: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

debido principalmente a la corriente producida en el interior del cuerpo de la

persona. Ahora bien, dicho valor de tensión no es utilizable directamente, pues

contiene un valor impreciso. Suponiendo conocidos los umbrales de tensión

ideales (determinados de forma empírica) para detectar “pulsación” / “no

pulsación”, la señal debería pasar previamente por un comparador que,

teniendo en cuenta dichos umbrales, generaría finalmente los valores de

tensión correspondientes a los valores lógicos “alto” y “bajo” utilizados por el

resto de la circuitería (5 voltios y 0 voltios; o 3’3 voltios y 0 voltios; etc.).

Una vez que ya hemos definido cómo se construiría un “sensor”, podemos

juntar varios para hacer nuestro instrumento.

Esquema Conceptual de la OpenPipe

En la figura se puede observar que se han utilizado ocho “sensores”. Cada uno

de ellos se correspondería con un agujero en una flauta convencional. Se ha

añadido uno adicionalmente, para utilizarlo como “sensor” de control.

Lo más normal es que distribuyamos los nueve “sensores” anteriores sobre un

tubo cilíndrico, para imitar la forma de una flauta o una gaita. En principio, el

material del tubo cilíndrico podría ser plástico o incluso madera. Los sensores

Page 12: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

estarían “incrustados” literalmente en el tubo, y no sería más que un pequeño

cilindro metálico en el que se introduciría la componente de corriente generada

por el cuerpo del intérprete.

Los “sensores” irían incrustados en el tubo.

Ahora bien, el resto de la circuitería correspondiente a cada uno de los

sensores estaría en la unidad de procesamiento, junto al microcontrolador y al

resto de componentes que conforman la lógica de OpenPipe.

Page 13: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Diseño de la Lógica del Controlador MIDI

Hasta ahora no se ha comentado nada relativo al procesamiento de datos. Nos

hemos limitado a detectar eventos, y a generar señales eléctricas (en principio

digitales, aunque también podrían ser analógicas) en respuesta a esos eventos.

Sin embargo, no hemos de olvidar que nuestro Controlador MIDI debe generar

mensajes MIDI como respuesta a los eventos que se han producido.

¿Por qué tipo de interfaz enviaremos la salida? Porque no es lo mismo enviar

datos a través del puerto USB que a través de una tarjeta de Red. Como cabría

esperar, a la salida tendremos una interfaz MIDI, que será la que transmita

nuestros datos a otro dispositivo MIDI externo, probablemente un sintetizador.

En caso de querer conectar OpenPipe al ordenador, es posible encontrar

interfaces MIDI – USB a partir de 50 euros en tiendas especializadas. También

existen opciones más económicas, pero más en desuso, como podría ser

interfaces MIDI – Puerto de Juegos, en caso de que la tarjeta de sonido

disponga de tal puerto.

En todo caso, a pesar de la gran cantidad de opciones de interconexión que

existen actualmente, es conveniente diseñar OpenPipe para que trabaje con

interfaces MIDI. La razón es muy sencilla: La gran mayoría de dispositivos

musicales electrónicos siguen utilizando el protocolo MIDI como estándar de

facto, aunque existan alternativas más modernas al respecto. En cualquier

caso, siempre queda la posibilidad de utilizar cables conversores y / o hardware

y software especializado para buscar la combinación deseada.

Entonces ya tenemos claro que nuestro diseño lógico: (a) Por un lado, tendrá

como entrada una serie de señales digitales que contienen información sobre

la ocurrencia de determinados eventos, y (b) Por otro lado, deberá producir

como salida información MIDI a través de una interfaz de dicho tipo.

Page 14: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Quienes hayan estado trabajando en temas relacionados con la electrónica,

sabrán que en cuanto es necesario “procesar” una pequeña cantidad de

información, se suele utilizar un componente denominado microcontrolador.

Microcontroladores y Lógica de Control

¿Qué es un microcontrolador? Pues a grandes rasgos, un microcontrolador es

como un microprocesador, en el sentido que tiene capacidad de procesamiento

(puede ejecutar instrucciones de un programa) pero más limitado, puesto que

normalmente se utilizan en actividades de control dentro de otros dispositivos,

o incluso en procesos industriales (donde su uso es más habitual).

Las actividades de control suelen ser rutinarias, y se caracterizan por necesitar

una cierta cantidad de procesamiento de datos a bajo nivel. Los

microcontroladores suelen incorporar una memoria interna de programa, en la

que se puede almacenar el programa de control, una memoria de datos, para

almacenar datos y variables, así como puertos de entrada / salida (tanto

analógicos como digitales) que permiten el flujo de datos con el exterior.

La arquitectura del microcontrolador es específica para cada aplicación.

Podemos encontrarnos microcontroladores con más o menos capacidad de

memoria, con más o menos puertos de entrada / salida. Incluso es habitual que

los microcontroladores incorporen algún tipo de periférico, como puede ser un

puerto serie, un puerto paralelo, un puerto USB, una tarjeta de red, etc. Todo

depende del uso que queramos darle.

En nuestro caso, hablaremos sobre el microcontrolador 8051. Se podrían haber

escogido muchos otros microcontroladores, siendo igualmente válida la

elección. Sin embargo, uno de los puntos a favor del 8051 es que es un

microcontrolador considerado actualmente como un “estándar”, muchos

fabricantes tienen en su catálogo diversos microcontroladores compatibles con

la familia 8051, como por ejemplo Phillips y Samsung.

Page 15: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

La arquitectura “tradicional” del 8051 está formada por los siguientes

elementos:

● Arquitectura Harvard (existen espacios de direcciones separados para

código y datos).

● CPU de 8 bits.

● Procesador booleano (operaciones sobre bits).

● Permite direccionar hasta 64 KB de ROM externa y 64 KB de RAM.

● Dos contadores / temporizadores.

● 128 o 256 bytes de memoria RAM interna (16 bytes de los cuales son

direccionables a nivel de bit).

● 4 KB de memoria ROM interna.

● Cuatro puertos de entrada / salida de ocho bits.

● Una UART.

● Cinco fuentes de interrupción (dos externas, dos para los temporizadores

y una para el puerto serie).

● Oscilador interno.

Sin embargo, como se trata de un diseño conceptual (a alto nivel), no se

profundizará mucho más sobre la arquitectura concreta del microcontrolador.

Simplemente se esbozará cómo el microcontrolador es capaz de controlar la

lógica del funcionamiento de la OpenPipe.

Lógica de Funcionamiento de un Controlador MIDI

A partir de los nueve sensores indicados anteriormente, obtendremos nueve

señales binarias, de valor uno o cero. Podemos considerar que un valor de uno

es “agujero tapado”, y que un valor de cero es “agujero destapado”, aunque

Page 16: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

sería sencillo implementar una lógica alternativa.

En principio, mientras el usuario mantiene una combinación de agujeros

tapados / destapados, se supone que el instrumento ha de mantener la nota

actual. En el momento que se destape o se tape un nuevo agujero, habrá que

silenciar la nota anterior (es decir, enviar un mensaje NOTE_OFF(notaId) de la

nota que estaba sonando hasta ese momento) y generar una nueva nota (es

decir, enviar un mensaje NOTE_ON(notaId) de la nota que se corresponda con

la nueva postura).

¿Cómo se podría implementar lo anterior? Pues con un bucle que comprobaría

continuamente el estado actual de los “sensores” (notar que el estado de los

sensores viene determinado por el valor de la señal eléctrica correspondiente)

con un estado de referencia (que se correspondería con la última nota

generada). En el momento que el estado actual no fuese exactamente igual al

estado de referencia, apagaríamos la nota actual y generaríamos la nueva

nota, puesto que un cambio en el estado de los “sensores” implica,

necesariamente, un cambio de postura por parte del usuario, lo cual implica, a

su vez, un cambio de nota.

Por tanto, es necesario tener almacenado en una serie de variables el valor

anterior de la señal, para ser capaces de detectar un cambio de estado en

cualquier instante de tiempo. La encuesta se haría de forma continua, ya que

el aparato tiene que ser capaz de responder en tiempo real a los eventos

producidos por parte del usuario.

001002003004005

006007008

// Encuesta el estado actual de los sensoresestadoAnteriorSensor0 = estadoSensor0 = detectarEstadoSensor0();estadoAnteriorSensor1 = estadoSensor1 = detectarEstadoSensor1();…estadoAnteriorSensor8 = estadoSensor8 = detectarEstadoSensor8();eventoNoteON(estadoSensor0, estadoSensor1, …, estadoSensor8);

while(1 + 1 != 7) {while(estadoSensor0 == estadoAnteriorSensor0 &&

estadoSensor1 == estadoAnteriorSensor1 && … &&

Page 17: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

009

010011012013014

015

016

017018019020021

estadoSensor8 == estadoAnteriorSensor8) {

// Encuesta del estado actual de los sensoresestadoSensor0 = detectarEstadoSensor0();estadoSensor1 = detectarEstadoSensor1();…estadoSensor8 = detectarEstadoSensor8();

}

//// El siguiente código se ejecuta si, y sólo si, el estado// actual no es igual al estado anterior, lo que significa// que el usuario ha cambiado su postura//

// Silenciamos la nota anterioreventoNoteOFF(estadoAnteriorSensor0, estadoAnteriorSensor1, …,

estadoAnteriorSensor8);// Iniciamos la ejecución de la nueva notaeventoNoteON(estadoSensor0, estadoSensor1, …, estadoSensor8);

//// El estado actual pasa a ser el estado anterior//estadoAnteriorSensor0 = estadoSensor0;estadoAnteriorSensor1 = estadoSensor1;…estadoAnteriorSensor8 = estadoSensor8;

}

Figura: Programa de Control de OpenPipe

En la figura se ha escrito en pseudocódigo el programa de control de OpenPipe.

Las líneas de la 1 a la 4 detectan el estado actual de cada uno de los nueve

sensores (numerados desde el cero al ocho). La pseudofunción

detectarEstadoSensor0() detecta el estado del sensor 0, que estará conectado

a una de las señales de algún puerto de entrada salida. En la práctica, lo

habitual es consultar el estado de un bit de algún registro especial del

microcontrolador, como sucede en el 8051.

Se han utilizado nueve variables de un bit para almacenar el estado actual de

cada uno de los nueve sensores. El valor de dichas variables se actualizará de

forma constante mediante encuesta, como se puede comprobar en las líneas

de la 10 a la 13. Además, se utilizan otras nueve variables de un bit para

almacenar el estado anterior de cada uno de los nueve sensores, que también

se inicializan en las líneas 1 a 4. El valor de dichas variables se utiliza como

Page 18: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

valores de referencia para detectar los cambios de postura por parte del

usuario.

Las líneas 7 a 14 mantienen el programa en espera activa mientras no se

produce un cambio de postura. En el momento que el estado actual no es el

mismo que el estado de referencia (entendiendo un estado como un valor

determinado por el conjunto de valores de los sensores en un instante

arbitrario), se pasa a ejecutar las instrucciones de las líneas 15 y 16, que

ejecutan dos pseudofunciones. La primera es

eventoNoteOFF(estadoAnteriorSensor0, estadoAnteriorSensor1, …,

estadoAnteriorSensor8), y envía un evento NoteOFF para la nota asociada con

el estado anterior de los sensores. La segunda es

eventoNoteON(estadoSensor0, estadoSensor1, …, estadoSensor8), que envía

un evento NoteON para la nota asociada con el estado actual de los sensores.

Finalmente, las líneas 17 a 20 establecen que el estado anterior es igual al

estado actual.

La implementación de las pseudofunciones eventoNoteOFF(estado) y

eventoNoteON(estado) se comentará posteriormente. En principio, nos basta

con saber que cada una de las funciones genera un mensaje NOTE_OFF y

NOTE_ON, respectivamente. Dicho mensaje se enviará por el puerto de salida

MIDI.

Estado de los “Sensores”, Posturas y Notas MIDI

Es interesante comentar la relación entre los siguientes conceptos: Estado de

los “Sensores”, Posturas y Notas MIDI.

En primer lugar, habíamos definido el estado de los “sensores” como una

combinación de los estados individuales de cada “sensor”. En términos

matemáticos, podríamos pensar como un vector de nueve elementos con

valores binarios representado estados “tapado” / “destapado”.

Page 19: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Por otra parte, habíamos comentado que una “postura” es una combinación de

dedos “tapando” y “destapando” agujeros, que es la que se utiliza en un

determinado instrumento de viento para tocar una nota determinada. El

conjunto de todas las posturas que se podían utilizar en un instrumento

constituye lo que se conoce como “digitación”.

¿Cuál es la diferencia entre ambos conceptos? Los dos definen el mismo hecho,

pero visto desde dos puntos de vista complementarios. Para el músico, una

postura define cómo tiene que poner las manos sobre el instrumento, tapando

y destapando agujeros, para que suene una determinada nota. Para el

ingeniero, el estado de los sensores es la forma de detectar la postura del

músico en un instante determinado de su interpretación, para luego generar

una nota u otra.

Por último, tenemos el concepto de “Nota MIDI”. La cuestión planteada es la

siguiente: Ante una postura determinada (o, equivalentemente, estado de los

“sensores”), ¿qué nota hemos de generar? En principio no existe una

equivalencia exacta, en el sentido que en un instrumento una postura produce

una nota determinada, mientras que en otro instrumento esa misma postura

produce otra nota distinta.

Éste hecho es particularmente cierto para casos en el que existen variantes de

un mismo instrumento, como puede ser como sucede con la gaita gallega.

Existen tres variantes especialmente importantes: La gaita en do (redonda), la

gaita en re (requinta) y la gaita en si bemol (tumbal). Se trata del mismo

instrumento, pero construido de tal forma que su escala principal se

corresponde con una escala de do, una escala de re en el segundo, y una

escala de si bemol, respectivamente, como cabría esperar. En esas tres gaitas,

la misma postura produce notas distintas, según la escala en la que estén

afinadas.

Page 20: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Por tanto, es interesante que se pueda configurar la relación entre “posturas” y

“notas MIDI” utilizando alguna herramienta gráfica. Dicha configuración

debería entonces ser almacenada en el microcontrolador, para que traduzca

las posturas indicadas a las “notas MIDI” que el usuario desea.

La implementación de la relación entre “posturas” y “notas MIDI” se realiza

mediante una tabla de correspondencia almacenada en memoria. Como el

número de posturas utilizadas en la práctica por un instrumento es muchísimo

menor que la combinación total de posibles posturas determinadas por nueve

agujeros (2^9 = 512 posturas posibles, mientras que, tirando por lo alto, se

utilizarán 30 posturas), lo más recomendable es realizar una búsqueda

secuencial hasta encontrar la nota correspondiente al estado actual.

Implementación de la Tabla de Correspondencia Posturas – Notas MIDI

Los datos que debería contener la tabla son los siguientes:

● El estado de los ocho sensores (recordemos que el noveno era de control,

por lo que no aporta información sobre la nota en cuestión). Dicho valor

será sobre el que se realicen las búsquedas en memoria.

● El identificador MIDI de la nota que vamos a generar o a apagar: 60 para

la nota Do, 61 para la nota Do#, etc.

Por tanto, cada fila de la tabla tendría una longitud de dos bytes. Un byte para

el estado de los ocho sensores, y otro byte para representar una de las 128

notas posibles dentro de los identificadores MIDI.

Ejemplo: Supongamos una gaita gallega afinada en re, que utilice digitación

abierta. Asumiendo que cada bit, una posible tabla de correspondencia

Posturas – Notas MIDI podría ser la siguiente:

Page 21: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Postura Nota MIDI

11111111 61 – Do#

11111110 62 – Re

11111100 64 – Mi

11111010 65 – Fa

11111000 66 – Fa#

11110000 67 – Sol

11100000 69 – La

11010000 70 – Sib

11000000 71 – Si

10100000 72 – Do

10000000 73 – Do#

00000000 74 – Re

01111110 74 – Re

01111100 76 - Mi

La digitación anterior contiene las posturas correspondientes a las notas de

mayor uso en la música tradicional gallega, por lo que constituiría un ejemplo

completamente real. Notar que existen dos posturas, la 00000000 y la

01111110, que se corresponden con la misma nota: La 74, un Re. No es raro

que en un instrumento existan varias posturas alternativas para una misma

nota. Es más, incluso existen posturas que se corresponden con notas “falsas”

(en el sentido que no tienen exactamente la misma frecuencia que su

correspondiente nota real), que se utilizan por comodidad al tocar notas

rápidas, como puede ser el caso de los trinos.

En los instrumentos reales, la correspondencia entre posturas y notas viene

dado por cómo está construido. Sin embargo, aquí la correspondencia la

establecemos nosotros, por lo que podríamos inventarnos una digitación que

fuese cómoda para tocar. Podría ser una ventaja en relación de los

instrumentos electrónicos en relación a los instrumentos tradicionales.

Supongamos un ejemplo de funcionamiento. En un instante determinado, el

Page 22: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

usuario está tocando la postura 11110000. Si al instante siguiente cambia a la

postura 11100000, saldremos del bucle de espera, apagaremos la nota

correspondiente a la postura 11110000 (que era un Sol, según la tabla

anterior) e iniciaremos la ejecución de la nota correspondiente a la postura

11100000 (según la tabla, un La). Eso es exactamente lo que ocurriría en un

instrumento real. Siguiendo con el ejemplo, ahora nuestra postura de

referencia para realizar futuras comparaciones será la postura 11100000.

Cuando el usuario cambie nuevamente de postura, tendremos que apagar la

nota correspondiente a la postura 11100000, e iniciaremos la ejecución de la

nota correspondiente a la postura actual del usuario. Y así sucesivamente.

Una mejora en la Tabla de Correspondencias

En la tabla anterior, el valor asociado a una postura obtiene el identificador

MIDI que finalmente se transmitirá. Sin embargo, observemos la siguiente tabla

alternativa:

Postura Nota MIDI

11111111 0

11111110 1

11111100 3

11111010 4

11111000 5

11110000 6

11100000 8

11010000 9

11000000 10

10100000 11

10000000 12

00000000 13

01111110 13

01111100 15

Page 23: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

La tabla se ha construido restando a todos los valores de la columna Nota MIDI

el valor más pequeño, el 61, correspondiente a la postura 11111111. Como

podemos observar, ahora el valor mínimo es cero, y el máximo quince. Podría

ser útil para intentar ahorrar espacio en memoria, pues la segunda columna de

la tabla podría ser almacenada ahora en cuatro bits. Sin embargo, el objetivo

es otro.

Al restar el valor más pequeño a la tabla, hemos perdido el concepto de “nota

absoluta”. Pero nos hemos quedado con otro concepto más importante, el de

“nota relativa”. La postura 11111111 produce una nota más grave que la

postura 11111110, de exactamente un semitono. ¿Por qué? Pues porque la

postura 11111111 tiene asociado un 0, y la postura 11111110 tiene asociado

un 1. Podríamos asignar a la postura 11111111 un Do, y a la postura 11111110

un Do#. O podríamos asignar a la postura 11111111 un Sol, y a la postura

11111110 un Sol#.

Podemos añadir a nuestro diseño un parámetro más, configurable. Es el valor

de la nota correspondiente a la postura 11111111. Dicho valor se sumará a

todas las correspondencias obtenidas a partir de la tabla. Para obtener el

mismo resultado que la tabla propuesta originalmente, basta con configurar

dicho parámetro a 61.

Por ejemplo, supongamos que el parámetro está configurado, efectivamente, a

61. Si nos llega la petición 11111111, obtendremos el valor cero, sumado a 61,

obtenemos 61. Si nos llega la petición 11111110, obtendremos el valor uno,

sumado a 61, resulta en 62. Y así sucesivamente.

Muchos teclados incorporan ésta habilidad, que se denomina “transportar”, y

que permite que un músico, tocando una melodía de la misma forma, pueda

obtener el sonido resultante en cualquier tonalidad. En el caso de la OpenPipe,

podríamos tocar con una gaita en do, en si bemol o en re, simplemente

configurando el parámetro anterior.

Page 24: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Puerto MIDI

Es muy sencillo encontrar microcontroladores que llevan incorporado el puerto

serie, como es el caso del 8051.

A continuación se indica cómo se puede obtener la salida MIDI a partir del

puerto serie:

Y, para aquellos que les interese, a continuación se indica cómo se puede

obtener la entrada MIDI a partir del puerto serie (nosotros no lo utilizaremos):

Page 25: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

Características del Protocolo MIDI

José Soler Sáez [2], en su proyecto de fin de diplomatura “La Norma Standard

MIDI”, comenta las características principales del protocolo MIDI. A

continuación seleccionaré las partes de su memoria que son de especial

interés para nosotros:

“El interface MIDI es un interface digital que trabaja en serie y que, de alguna

forma, es bidireccional. Un interface digital transmite la información como

trenes de números binarios. En MIDI, estos trenes de números tienen ocho bits

de longitud, con lo cual podremos tener hasta 256 valores posibles. Un

interface serie trasmite estos números uno tras otro y, por lo tanto, sólo

requiere un cable con dos conductores”.

“Desde el punto de vista del hardware, el interface MIDI opera a 32,25 Kilo

baudios…” (32,25 Kilobits por segundo) “…de forma asíncrona, con un bit de

arranque (start bit), 8 bits de datos (numerados del cero al siete) y un bit de

parada (stop bit). Esto representa un total de 10 bits para un periodo de 320

microsegundos por byte serie. El bit de arranque (start bit) es un 0 lógico

(corriente desactivada) y el bit de parada es un 1 lógico (corriente activada).

Se envía en primer lugar el LSB” (el bit menos significativo).

“El circuito es del tipo lazo de corriente de 5 mA. Una salida sólo deberá

alimentar una entrada. Para evitar lazos de masa, y los consiguientes errores

en los datos, la circuitería emisora y la receptora se encuentran separadas

internamente por un optoacoplador (un diodo emisor de luz y un sensor

fotosensible, alojados en el mismo encapsulado). El receptor debe precisar

menos de 5 mA para activarse. Los tiempos de subida y bajada deben ser

menores a 2 microsegundos”.

“Los conectores son DIN de 5 pines (180 grados). Los conectores deben ser

identificados como MIDI IN y MIDI OUT. Obsérvese que los pins 1 y 3 no se

Page 26: Proyecto OpenPipe. Diseño Conceptual Controlador MIDI

utilizan, por lo que deben dejarse sin conexión tanto en el transmisor como en

el receptor. El pin 2 del conector MIDI IN también debe dejarse sin conexión”.

“El apantallamiento de masa de los jacks MIDI no debe ser conectado a la

masa de ningún otro circuito o toma de tierra de chasis”.

(por completar)

Referencias del documento

[1]

http://www.fic.udc.es/HarvestExternalData.do?operation=directory.teacher&id=90

José Juan Lamas Seco

Departamento de Electrónica y Sistemas

Facultade de Informática

Universidade da Coruña

[2]

La Norma Standard MIDI

José Soler Saez