Introducción
En la primera parte de esta serie de blogs, después de haber puesto en funcionamiento el reproductor de MP3 para la salida de voz y haber desarrollado un flujo de programa, en la segunda parte le mostramos cómo conectar y programar el sensor de color TCS3200. Ahora, en la tercera y última parte ahora, uniremos las dos partes, escanearemos los colores y permitiremos que el detector de color hable. Implementaremos un modo de calibración en vivo y haremos que la fuente de alimentación sea móvil con una batería. ¡Empecemos!
Lo que necesitamos
Numero | Componente |
---|---|
1 | TCS3200 Módulo Sensor de color |
1 | Módulo Mini Reproductor MP3 DFPlayer |
1 | Tarjeta micro SD |
1 | Arduino Nano V3.0 |
1 | Altavoz (máximo 3W) |
Cables puente | |
1 | Resistencias 1 KOhm |
1 | Resistencia variable (Potenciómetro) |
2 | Taster |
Computador con Arduino IDE y conexión a Internet | |
Fuente de alimentación externa (recomendada), 7 - 12V | |
Carta de referencia de colores | |
LiPo Batería 3,7 V | |
1 | Módulo MT3608 Adaptador Step up |
1 | Módulo TP4056 Cargador de batería |
1 | Voltímetro |
Preparación
Asumo que construyó el circuito a partir de la parte 2 e insertó la tarjeta SD con los archivos de voz en la ranura SD del reproductor de MP3.
Pines de Mini DFPlayer |
Pines de Arduino Nano |
VCC |
5V |
GND |
GND |
RX |
más de 1 kOhm a D11 (TX) |
TX |
D10 (RX) |
|
Altavoz |
SPK_1 |
Rojo (Más) |
SPK_2 |
Negro (Menos) |
Potenciómetro |
Pines de Arduino Nano |
1 |
GND |
2 (Centro) |
A0 |
3 |
+ 5V |
Botón |
Pines de Arduino Nano |
1 |
D12 |
2 |
GND |
Pines de TCS3200 |
Pines de Arduino Nano |
VCC |
5V |
GND |
GND |
OE |
D3 |
S0 |
D4 |
S1 |
D8 |
S2 |
D6 |
S3 |
D7 |
OUT |
D5 |
Para una prueba funcional, cargamos el programa de la parte 1 al Arduino:
Código fuente completo: 1.2DFPlayerStartsoundPotiCatador.ino
También probamos el sensor de color con el programa de la parte 2:
Código fuente completo: 2.0TCS3200Prueba.ino
Combinación de Programas
Ahora nuestra tarea consiste en unir los programas de la parte 1 y 2. Con el programa de la parte 1 podemos operar el dispositivo de forma relativamente simple. Incluso puede emitir colores a través de la salida de voz. Con los programas de la parte 2, podemos escanear los colores correctos. Así que "solo" tenemos que transferir el código fuente de la parte 1.
Primero cambiamos el programa "tcs3200calibration " por la calibración desde la librería tcs3200 que ya usamos en la parte 2. Como mencioné al final de la parte 2, ampliamos las matrices distinctRGB, distinctColors y colorNames. Necesitamos realizar esto porque usamos más colores. Así que tenemos que cambiar las siguientes líneas:
#define num_of_colors 9
int distinctColors[num_of_colors] = {0, 1, 2, 3, 4, 5, 6, 7, 8};
String colorNames[num_of_colors] = {"Rot", "Gruen", "Blau", "Schwarz", "Weiss", "Gelb", "Orange", "Pink", "Braun"};aranja", "Rosa", "Marrón"};
Con esto hemos establecido el número y el orden de nuestros colores. La lista ahora coincide con los archivos de audio que creamos en la Parte 1.
Para que podamos controlar los colores más fácilmente más tarde, agrego una interrupción en la secuencia del programa. Ya habíamos hecho esto en el ejemplo "Calibrate_TCS230" en la parte 2. Además, formateamos la salida para que podamos copiar los valores más fácilmente. La matriz distinctRGB[] [] escribamos para facilitar la lectura sin cambiar el contenido:
int distinctRGB[num_of_colors][3] = {
{17, 4, 7},
{9, 11, 11},
{4, 8, 18},
{3, 3, 4},
{32, 26, 45},
{27, 20, 14},
{28, 15, 12},
{18, 7, 17},
{7, 4, 6}
};
Esto nos permite acceder más fácilmente a los tres valores por color. Ahora declaramos un búfer de dibujo para la edición formateada:
char serialBuffer[55];
Cambiamos la función loop () de la siguiente manera:
void loop() {
// Auf Eingabe warten
while (Serial.available() == 0) {
if (Serial.available() != 0) {
break;
}
}
// Serial Puffer loeschen
while (Serial.read() != -1) {}
Serial.println(colorNames[tcs.closestColor(distinctRGB, distinctColors, num_of_colors)] );
red = tcs.colorRead('r'); //reads color value for red
Serial.print("R= ");
Serial.print(red);
Serial.print(" ");
green = tcs.colorRead('g'); //reads color value for green
Serial.print("G= ");
Serial.print(green);
Serial.print(" ");
blue = tcs.colorRead('b'); //reads color value for blue
Serial.print("B= ");
Serial.print(blue);
Serial.print(" ");
Serial.println();
// Ausgabe
sprintf(serialBuffer, "Rot Gruen Blau: {%d, %d, %d} ", red, green, blue);
Serial.println(serialBuffer);
}
El programa espera la entrada en el monitor serie. Luego se graba el color una vez y salen los valores para que podamos copiarlos directamente e insertarlos de nuevo en el código fuente. Esto lo hacemos sucesivamente con todos los colores que hemos introducido en la lista. Se debe prestar atención a la posición correcta en la matriz correspondiente para que no se cambie ningún color por descuido.
De momento puede ignorar la salida del nombre de color. Después de registrar todos los colores y haber introducido el código fuente aquí, transferimos el programa a Arduino de nuevo. Si ahora escaneamos los colores, la palabra visualizada debería ajustarse al color.
Código fuente completo: 3.0Serie tcs3200Calibraciónnew.ino
El código fuente ahora se transfiere al programa que habíamos escrito en la Parte 1. Tomamos las constantes, variables y matrices. Ahora sólo tenemos que introducir en la máquina de estado en el caso 6, qué color debe ser de salida. Actualmente esta línea es la salida del archivo de audio actual con la palabra "rojo":
myDFPlayer.play()4);
Con esta línea emitimos el nombre del color en la pantalla en el programa de calibración:
Serial.println(Estado no Sub - Especificación)tcs.closestColor(distinct RGB, distinct Colors, num of Colors));
Sólo necesitamos la función llamada ClosestColor ():
tcs.closestColor(distinct RGB, distinct clors, color number)
Esto nos devuelve el número del color reconocido. Sin embargo, los números de color comienza en 0. Nuestros números de los archivos de audio que contienen los colores comienzan en 1. El primer color tiene el número 4. Para ello, eche un vistazo a la tabla de la parte 1 en la sección "Salida de voz". Necesitamos un desplazamiento para los números de la tabla. Nuestro color reconocido tiene el número 0. La tabla tiene el número 4. Así que un desplazamiento de 4. Para esto nos declaramos otra constante:
#define file offset 4
A continuación, la línea para la salida del archivo de audio es una combinación de las líneas anteriores:
myDFPlayer.play()tcs.closestColor(distinct RGB, distinct Colors, num of Colors) + file offset);
Transferimos el número reconocido al reproductor de audio y adicionalmente añadimos nuestro desplazamiento. Para la salida de la palabra del color, tomamos la línea del programa para la calibración:
Serial.println(Estado no Sub - Especificación)tcs.closestColor(distinct RGB, distinct Colors, num of Colors));
Si ahora carga el programa en el Arduino, la palabra correcta debería ser reproducida y visualizada después de escanear el color inmediatamente después de soltar el botón.
Código fuente completo: 3.1OradorFarbdetektor.ino
En este punto, el detector de color parlante está funcionando como se esperaba. Puede reconocer colores y expresarlos en voz alta.
Otras voces
Ahora queremos usar otras voces. Para esto necesitamos nuevos archivos de audio. Utilice el sitio web vinculado en la parte 1 de nuevo, o grábese a usted mismo. Después debe editarlos para que tengan el mismo orden que nuestros archivos de audio existentes. Agregué una voz masculina y otro idioma. Así que ahora tengo voces femeninas y masculinas en alemán, así como femeninas y masculinas en inglés. Después de editar los archivos de audio, los copié a la tarjeta SD. Asegúrese de transferir los archivos en el orden correcto, preferiblemente uno por uno. Mi número de archivos de audio está alcanzando los 53.
Anteriormente habíamos insertado un desplazamiento para que el número de archivo coincida con el número de color. Dicho desplazamiento lo podemos utilizar ahora para cambiar la voz. Aquí hay una lista de numeración de mis voces:
Número |
Voz |
2 - 14 |
femenina, alemana |
15 - 27 |
masculina, alemán |
28 - 40 |
femenina, inglés |
41 - 53 |
masculina, inglés |
Ahora deben implementarse dos consideraciones importantes:
- ¿Cómo cambiamos la voz?
- ¿Dónde cambiamos eso en el programa?
Para la primera pregunta, deberíamos considerar para qué grupo objetivo normalmente construimos el dispositivo. Debido a que voy a priorizar el dispositivo principalmente para personas con discapacidad visual, voy a mantener el funcionamiento tan simple como sea posible. Tomamos el botón que ya se utiliza con un toque corto o un clic y se mantiene. Sin embargo, si añade otro botón, podemos hacerlo más fácil. Lo conectamos a A5 de Arduino y a GND:
Definimos e inicializamos el pulsador en el programa (por qué utilizo aquí el Pin analógico A5 como entrada digital, y lo explico en la conclusión):
#define tasterpin2 A5
Configuración / im:
Pinmode (tecla 2, entrada)
Necesitamos más variables adicionales. Un contador con el que fijamos la voz, un desplazamiento respecto a las otras voces y un número máximo de voces:
Escena interior Número de voz 0;
Inapropiada Escena interior Voz sesgada 13;
Escena interior Sonido máximo 4;
Necesitamos una función para leer el segundo botón y reaccionar a los cambios. Utilizamos la función como una plantilla Button () que ya la tenemos. Para que podamos tomar el relevo. Tal vez más tarde podamos conectar estas dos funciones para evitar redundantes códigos de fuente. La primera vez que copiamos esta función y la renombramos alrededor de Changevoice () y cambia de acuerdo a lo siguiente:
Inválido Cambiar voz ()
Estado del teclado del nuevo 2 = lectura numérica (taster pin2); La clave está en estado de baja activación
Identificar cambios clave e iniciar el temporizador
Si ¡(nuevo Estado del teclado) 2!= Estado del teclado < antiguo < 2 >Cambios clave
Hora de inicio = milisegundos ();
Cambios de teclado Sí.;
}
Cuando se presiona el botón
Si (Estado del teclado para el nuevo 2 = = bajo & Estado del teclado para el antiguo 2 = = bajo & cambiar la clave para el segundo) {
Keyhead
Si (MS () START time > Pre - delay) {
Cambios de teclado Falso;
Voicenumber + +;
Si (voicenumber > maxvoices) 1) {
Número de voz 0;
}
Archivo mydfplayer.play()14 Número de voz * voz offset);
Número de serie.()"El idioma ha cambiado");
Estado 1;
}
}
Estado del teclado = Estado del teclado = nuevo Estado de la clave = nuevo Estado de la clave =;
}
También necesitamos las variables apropiadas:
Inapropiada Largo Nuevo tiempo = 2 0;
Inapropiada Largo Hora de inicio = 2 0;
Booleano Nuevo Estado del teclado 2 = alto;
Booleano Estado del teclado = alto;
Booleano Cambios de teclado Falso;
Cuando se presiona el botón, contamos el número de las voces en 1. Cuando hayamos alcanzado el número máximo de voces, el valor se vuelve 0 y, por lo tanto, se vuelve a utilizar la primera voz. A continuación, emitimos la voz ahora establecida a través de la reproducción de audio. El reproductor obtiene el número del archivo de audio. Para la primera voz sería el número de archivo 14. Añadimos la multiplicación del número de voz y el desplazamiento. Esto da 14 para la primera voz como se mencionó antes (porque 0 * 13 es 0 y 14 + 0 da 14), para la segunda voz, es 14 + 1 * 13, lo que da como resultado 27. Esta es la misma palabra para mí, sólo que pronunciada por la voz masculina. Esto sigue y sigue de esta manera. La segunda voz es 14 + 2 * 13 = 40 y 14 + 3 * 13 = 53. Así que tenemos un pequeño algoritmo que siempre nos da la misma palabra pronunciada por una voz diferente. Por lo tanto, es importante mantener el orden de los archivos igual para todas las voces.
Luego cambiamos la variable state- al valor 1. Así saltamos de nuevo en la máquina de estado al momento anterior a la emisión del texto informativo. Si alguien ya ha escaneado el color y luego cambia el idioma, el texto informativo debe ser emitido una vez más en el nuevo idioma antes de ser escaneado de nuevo.
En la función statemachine()- ahora complementamos las salidas respectivas:
...
caso 2: { // Help jugar
myDFPlayer.jugar(2 + número de voz * voz offset);
...
caso 4: { // Iniciar exploración
myDFPlayer.jugar(3 + número de voz * voz offset);
...
caso 6: { // Color de salida
myDFPlayer.play (tcs.color más cercano (distinctRGB, colores distintos, num_of_colors) + offset de archivo + número de voz * offset de voz);
...
Como paso final, tenemos que llamar a la función changeVoice()- en el bucle principal:
anular bucle() {
catador();
cambiar la voz();
volumen();
statemachine();
}
Si cargamos el programa en el Arduino, podemos ejecutar el detector de color de la misma manera que antes. Además, podemos cambiar la voz o el idioma con el segundo botón.
Código Fuente completo: 3.2hablarDetector de colormasIdiomas hablados.ino
Calibración en vivo
Hemos visto que tenemos que calibrar el sensor para ajustarlo a nuestros colores. Por el momento necesitamos un programa Arduino separado para esto, necesitamos copiar los valores de color y luego copiar todo en nuestro programa. Si el sensor se encuentra en una carcasa fija en la que está protegido de la luz ambiental, por lo general solo necesita realizar la calibración una vez. Debido a que la distancia del sensor a la superficie de color y la luz ambiental son dos factores de interferencia tan pronto como cambian. Para resolverlo de todos modos, que se puede realizar la calibración sin copiar los valores de un lado a otro, necesitamos una forma de capturar los datos y luego transferirlos directamente a la matriz con los valores de color. Sin embargo, sólo si ejecutamos un modo de calibración.
Sería útil si la calibración se lleva a cabo al inicio del programa. Sin embargo, no siempre, sino solo cuando se ha presionado un pulsador o interruptor. La pregunta es si la calibración debe realizarse una y otra vez durante el funcionamiento en vivo, o solo una vez, por ejemplo, después de un reinicio con un botón presionado. Decido usar ambos botones. Cuando se presionan juntos y se inicia el Arduino, se entra en modo de calibración. A continuación, puede cambiar con el primer botón a través de todos los colores y escanee cada uno de los colores de referencia para esto. Después, entra en el modo normal como de costumbre.
Necesitamos algunas variables nuevas. El modo de calibración debe estar marcado como una bandera. Entonces sólo quiero pasar por un bucle al principio, esperando que los dos enlaces sean liberados de nuevo. Además, contamos los números de color a partir de 0 a arriba para que podamos escanearlos por separado. Para la edición formateada, uso una matriz char como en el programa para la calibración por separado:
Booleano Calibración Falso;
Booleano Primera puesta en marcha Sí.;
Escena interior Contador Carl 0;
Carbonización Buffer serial55];
Todos los valores en la matriz con valores de color se establecen en 0:
Escena interior Distinct RGB [número de colores]3] = {0};
Al comienzo del programa, es decir, en la función setup(), podemos identificar la posición en la que ambos botones se presionan simultáneamente:
Pulse dos botones para calibrar al inicio
Si ¡(!Lectura digital (taster PIN)Lectura digital (taster pin2) {
Calibración Sí.;
}
Los pines de los botones son de baja actividad y debido a la doble lógica y la expresión sólo es verdadera cuando ambos están en un Estado Low. Luego la bandera, variable booleana de calibración, se pone en verdadero. Con esto se activa el modo de calibración.
Mi primera consideración es escribir una función para calibrar. Me di cuenta de que tendría que copiar una gran cantidad de código que ya estaba escrito en él. He llegado a la conclusión de que no lo necesito realizarlo. Sólo necesito distinguir en mi código fuente anterior en algunos lugares si el modo de calibración está activo o no.
De este modo, quiero cambiar el voz como antes. Sin embargo, al momento de cambiar, la palabra no debe ser emitida para el idioma, y me gustaría volver al principio del programa completo. Por lo tanto, se complementan en la función Changevoice() el siguiente pasaje:
Archivo mydfplayer.play()14 Número de voz * voz offset);
Número de serie.()"El idioma ha cambiado");
Estado 1;
Modifíquese para que diga lo siguiente:
Número de serie.()"El idioma ha cambiado");
Si (calibración) {
Estado 0;
}
Tiempo estimado de despegue {
Archivo mydfplayer.play()14 Número de voz * voz offset);
Estado 1;
}
Tengo en todas partes, donde se distingue entre la calibración y el modo normal, el programa previo en el ElseBranch de IFQueries escritas. Si la bandera de calibración no está activada, el programa funcionará como antes. Por consiguiente, siempre me refiero a la rama if en lo que continua.
Todos los demás cambios ahora están en la función statemachine(). En el caso 0, distinguimos si está en modo de calibración o no. Si es así, publicamos la palabra "calibrar" o su equivalente en inglés. Ahora podemos distinguir si esta parte del programa se ejecuta por primera vez (recuerde: todo se ejecuta en un bucle interminable) o no. Es sólo la primera vez que queremos ver si ambos botones están presionados. Antes de que ambos se suelten, el programa se ejecutará en otro bucle continuo. También tenemos que aliviar la liberación. Ya que estábamos aquí al principio del programa, lo tengo con un Delay () porque no necesitamos una expiración ininterrumpida aquí. Y seguimos poniendo el firstStart-Flag en false para que esta parte no se vuelva a ejecutar. Si cambiamos la voz, volveremos a este caso. Esta es la razón por la que elegí hacer esto, porque después de cambiar la voz, no reproduzco la palabra para el idioma, pero la palabra "calibración" con la nueva voz:
Casos 0: {
Si (calibración) {
Archivo mydfplayer.play()13 Número de voz * voz offset); Reproducir "calibración"
Número de serie.()Calibración.);
Si (primera puesta en marcha)
Aunque ¡(!(Digital read (tasterpin) and digital read (tasterpin2)) {
♪Número de serie.("suelte los dos botones");
}
Realidad sucia
// desbloqueo no es necesario aquí
retraso (prell_delay);
firstStart = falso;
}
}
else {
myDFPlayer.jugar(1); // Juega Startsound
Serie.println("El programa ha comenzado.");
}
estado = 1;
} romper;
El siguiente caso que se cambia es el número 4. En el modo normal, se reproduce la palabra "scanny". En el modo de calibración, quiero que se llame al color, que se escaneará a continuación. Para obtener el color correcto, necesitamos un desplazamiento de nuevo:
caso 4: { // Iniciar exploración
si (calibrar) {
myDFPlayer.reproducción (archivo, offset + kalCounter + número de voz * offset voice);
Serie.println (colorNames [kalCounter]);
}
else {
myDFPlayer.jugar(3 + número de voz * voz offset);
Serie.println("Escanear...");
}
gastar = falso;
estado = 5;
} romper;
El desplazamiento se compone de varios desplazamientos parciales. FILEOFFSET desplaza el contador al primer color, en nuestro caso el rojo. El kalCounter se desplaza al número actual, el color a escanear. La multiplicación de voiceNumber y offsetVoice da como resultado la voz que hemos seleccionado, como siempre.
El último cambio se produce en el caso 6. Aquí habíamos emitido originalmente el color que escaneamos. Queremos almacenar esto en la matriz de color en el modo de calibración. El kalCounter especifica el número de color. Aquí se incrementa en 1 en cada pasada. Utilizamos la lectura de los valores de un solo color del sensor desde el programa para la calibración por separado. Allí ya se ha tomado el ejemplo de la librería.
Si todos los colores se han ejecutado a través del mismo kalCounter el número de colores Numofcolors. En este punto, toda la matriz con los valores de color se emite una vez más en el monitor serie, el modo de calibración finaliza y la máquina de estado se restablece a Case 0 nuevamente. Por lo tanto, el programa continúa ejecutándose en modo normal y se puede utilizar como antes:
caso 6: { // Color de salida
si (calibrar) {
distinctRGB [kalCounter][0] = tcs.colorRead("r");
distinctRGB [kalCounter][1] = tcs.colorRead("g");
distinctRGB [kalCounter][2] = tcs.colorRead("b");
Serie.imprimir (distinctRGB [kalCounter][0]);
Serie.imprimir(" ");
Serie.imprimir (distinctRGB [kalCounter][1]);
Serie.imprimir(" ");
Serie.println (distinctRGB [kalCounter][2]);
kalCounter++;
si (kalCounter > = num_of_colors) {
para (int siguiente = 0; n < num_of_colors; n++) {
sprintf (serialBuffer, "Rojo, Verde y Azul: {%3d %3d %3d}", distinctRGB[n][0], distinctRGB [n][1], distinctRGB [n][2]);
Serie.imprimir (colorNames[n]);
Serie.println (serialBuffer);
}
calibrar = falso;
estado = 0;
romper;
}
}
else {
myDFPlayer.play (tcs.color más cercano (distinctRGB, colores distintos, num_of_colors) + offset de archivo + número de voz * offset de voz);
Serie.println("Color: ");
Serie.println (colorNames [tcs.color más cercano (distinctRGB, colores distintos, num_of_colors)]);
}
estado = 3;
} romper;
Nuestro detector de color ahora se puede calibrar sin tener que copiar valores del monitor serie y pegarlos en el código fuente. Mantenga las tarjetas de color de referencia listas para cargar el programa en el Arduino y mantenga presionados ambos botones cuando se inicia el programa.
Código Fuente completo: 3.3hablarDetector de colormasLanguages_live calibration.ino
Guardar datos de forma permanente
La siguiente tarea es almacenar los valores de color de la calibración en algún lugar, de lo contrario se perderían después de un reinicio.
Como memoria, hay diferentes soluciones. Las memorias flash externas están disponibles comercialmente en I2C- y SPI-Versión disponible como breakoutboard. También podría utilizar un externo Módulo de tarjeta Micro SD. Utilice y almacene los datos en una tarjeta SD. Del mismo modo, un módulo externo I2C-EEPROM concebible. La tarjeta SD sería ligeramente sobredimensionada para tan pocos datos. Flash externo o EEPROM podría generar costos adicionales, pero sería una solución como Plan B. La interfaz I2C de los Arduino Nano se encuentra en los pines A4 y A5. Podríamos poner el segundo botón en otro pin, entonces se podría dar cuenta de eso.
Sin embargo, dado que el Arduino Nano tiene una EEPROM incorporada, también podemos usarla. Cabe señalar que esta memoria no se puede describir continuamente (100.000 escrituras). La lectura, por otro lado, siempre es posible.
Nota: En la serie de blogs "Arduino: Multi-IO y EEPROM" he trabajado sobre el tema antes. En la Parte 2 usé la EEPROM interna allí.
Supongo que no tenemos que calibrar a menudo. Por lo tanto, elijo esta solución.
En el punto del programa donde todos los colores se han ajustado en el modo de calibración y una vez más toda la matriz de color se emite en el monitor serie, queremos transferir adicionalmente los datos a la EEPROM. Esto sucede en el caso 6. Añadimos antes o después de esta línea:
calibrar = falso;
la nueva línea siguiente:
EEPROM.poner(0, distinctRGB);
La función put() nos permite transferir objetos completos a la EEPROM. Solo se sobrescriben los valores que difieren. Escribimos la matriz completa con los colores recién escaneados en la EEPROM a partir de la dirección 0.
Eso fue fácil. Lo que falta ahora es la lectura de la EEPROM cuando el Arduino se inicia. Pero solo si el modo de calibración no se ejecuta. Para esto, añadimos set up() en este punto:
// calibrar cuando se presionan ambos botones en el arranque
si (!digitalRead (TasterPin)&&!Lectura digital (Catasterpin2)) {
calibrar = verdadero;
}
un else- Añadir rama:
else {
EEPROM.conseguir(0, distinctRGB); // Leer datos de EEPROM
para (int siguiente = 0; n < num_of_colors; n++) {
sprintf (serialBuffer, "Rojo, Verde y Azul: {%3d %3d %3d}", distinctRGB[n][0], distinctRGB [n][1], distinctRGB [n][2]);
Serie.imprimir (colorNames[n]);
Serie.println (serialBuffer);
}
}
Con la función Get() vamos a leer la matriz completa desde la dirección 0 y escribirlo en nuestra matriz de colores vacía. Para comprobar si esto funcionó, seguimos emitiendo los valores en el monitor de serie.
Código Fuente completo: 3.4hablarDetector de colorVarios idiomasLiveKal_EEPROM.ino
Descargue el programa en el Arduino, mantenga pulsados ambos botones y pase por el modo de calibración una vez. Después reinicie el Arduino usando el botón RESET sin presionar los botones. A continuación, verá si los valores se han cargado y si el detector de colores reconoce sus colores.
Fuente de voltaje móvil
Si alguien quiere usar el dispositivo, ciertamente no quiere depender del cargador más cercano. Así que voy a cambiar a la operación de batería. Puede conectar directamente un bloque de 9V al VIN del Arduino, porque se instala un regulador de voltaje. También es posible apagar un banco de energía (no puede apagarse si la carga es demasiado baja) o Paquete de Baterías Raspberry Pi para conectar al puerto USB.
Quiero un Batería LiPo utilizo un Polímero de iones de litio. Están disponibles en diferentes formas, tamaños y con diferentes capacidades. Utilizo una batería plana con una capacidad de 2000 mAh y un voltaje de 3.7 V. Este diseño favorecería la construcción de una carcasa plana. No quiero entrar en más detalles sobre cómo calcular la duración de la batería.
Dado que la fuente de alimentación externa del Arduino en el VIN debe ser de al menos 7V, necesitamos un Convertidor Step-up. Así que ajustamos el voltaje a 9V. Eso debería encajar. Para que también podamos cargar la batería, usamos un Módulo de controlador de carga Micro USB. Gerald Lechner muestra cómo estos componentes están conectados en su Entrada de blog " Fuente de alimentación de batería de 5V con batería LiPo de 3.7 V y controlador de carga". Hemos conectado el Voltímetro al Vout del transformador de voltaje, giramos el Potenciómetro, hasta que hayamos alcanzado los 9V.
Nota: Es posible que tenga que girar el potenciómetro durante mucho tiempo contra las manecillas del reloj (como si estuviera encendiendo un grifo) hasta que aumente el voltaje. Necesitaba muchas revoluciones y ya había sospechado que el dispositivo estaba defectuoso.
Ahora reemplazamos la anterior fuente de voltaje externa (si ha utilizado una) y conectamos en su lugar las conexiones Vout del convertidor step-up a Vin o GND del Arduino. Le recomiendo instalar un interruptor entre Vin del Arduino y Vout del convertidor. De esta forma no tendrá que desconectar la batería cada vez que apague el dispositivo. En la siguiente imagen se muestra de nuevo el diagrama de circuito completo:
Conclusión
Ahora hemos diseñado la electrónica de un detector de color móvil, parlante y calibrable. Se maneja sólo con dos botones, un interruptor y un potenciómetro. El uso de sus propios colores es algo limitado. Cuantos menos colores se utilicen, menos precisa será la ponderación. Un rojo oscuro a veces se reconoce como marrón. Para el control del sensor de color finalmente elegí la librería tcs3200. También es posible utilizar la librería MD_TCS230. El código de ejemplo es un poco más extenso y tiene que depender del pin D5. Por eso decidí hacerlo.
Ahora es posible simplificar el código fuente. El sensor de color podría ponerse en reposo con un tiempo de espera para extender la vida útil de la batería. Para esto puede configurar el divisor de frecuencia en LOW / LOW y el pin OE en HIGH. Desafortunadamente, los cuatro LEDs no se pueden desactivar. Para ello habría que diseñar un circuito de transistores que desactive completamente el sensor.
Unas breves palabras sobre la elección de los pines digitales. Desafortunadamente, aún no he encontrado una solución. Si conecta el sensor de color y lo inicializa en el programa, las resistencias pullup internas de los pines D3, D9 y D13 ya no funcionarán. Es por eso que conecté los pulsadores a los pines D12 y A5. Como puede ver, puede usar los pines analógicos como pines digitales. Hice pruebas con resistencias pull-down externas. Así que debería funcionar. Sin embargo, uno tendría de nuevo más componentes y tendría que cambiar el código fuente. Si encuentra la causa de esto, por favor escríbala como un comentario.
Manual del usuario
Modo de calibración
Debe llevarse a cabo con el primer uso o cambio de la carcasa.
- Mantenga pulsados los botones 1 y 2 y encienda el dispositivo
- Salida de audio "Calibración" (aumentar el volumen si es necesario)
- Los colores están preestablecidos
- Mantenga el escáner en una superficie con el color correspondiente
- Presione el botón 1 vez
- La información se emite
- A continuación, mantenga pulsado el botón
- Se emite el color especificado
- Mantenga el sensor contra la superficie de color y suelte el botón
- Mantenga presionado el botón nuevamente
- Se emite el siguiente color
- Cuando se hayan escaneado todos los colores especificados, el sonido de inicio sonará
- El detector de color se ejecuta en modo de escaneo normal
Modo de escaneo de color
- Encienda el dispositivo sin presionar los botones
- Pulse el botón 1 una vez
- Se emite un mensaje
- Mantenga presionado el botón 1 en la superficie de color deseada
- Botón de liberación 1
- El color se emite (aumentar el volumen si es necesario)
- Escaneando de nuevo sin previo aviso
- Mantenga presionado el botón, luego suéltelo para obtener resultados
Cambiar la voz
- Pulse brevemente el botón 2
- Cambios de voz
- En el modo de escaneo, la voz se emite
- En el modo de calibración, la referencia del modo se escucha
- Si se ha cambiado la voz, pulse el botón 1 de nuevo brevemente para el escaneo en ambos modos
- Suena un mensaje
- A continuación, mantenga pulsado el botón 1
- La voz se puede cambiar en cualquier momento
Cambio los archivos de voz
- El orden de copia debe ser respetarse
- Cambiar los textos en la matriz colorNames[] por otros colores
- Al cambiar el número de colores: numofcolors, distinctColors, colorNames y offsetVoice
- Al cambiar el número de voces: maxVoices
- Vuelva a realizar la calibración
Demovideo
Andreas Wolter
para AZ-Blog de Entrega