Mi respuesta estándar:
Mi recomendación es siempre la de usar millis()
y máquinas de estados para cualquier programa. Por muy sencillo que sea. La función delay()
sólo la usaría excepcionalmente en el setup()
, si tuviera la necesidad de realizar una minúscula pausa al inicializar algo al arrancar el Arduino. Y nunca, repito, nunca usar goto
, bajo ninguna circunstancia.
La ventaja de usar millis()
y máquinas de estados es que siempre será más fácil "juntar" varios programas, que tengamos funcionando por separado, en uno solo. Además de que se pueden añadir nuevas "tareas" al programa, sin que interfieran en lo que ya hace. Todo esto es gracias a que no hay ningún delay()
que detenga la ejecución del programa.
Eso sí, al igual que hay que evitar el uso del delay()
, hay que procurar no tener bucles que lleven mucho tiempo de ejecución. Porque la idea es que el programa se demore lo mínimo en atender cada una de las diferentes cosas que ha de hacer. Dando así la sensación de que las está haciendo todas a la vez. Y si se "entretiene" demasiado en alguna cosa, puede que "se pierdan eventos" que ha de controlar de otras.
Además, recomiendo el uso de un buen estilo de programación. Cosas como poner nombres "adecuados" a las variables. Así como la definición y uso de constantes con #define
, cons
o enum
. Siendo lo ideal conocer y hacer uso de las herramientas de programación que nos proporciona la programación orientada a objetos del C++. Porque, después de todo, este entorno de Arduino es C++.
Programar con millis()
y máquinas de estados es mucho más enrevesado que usar delay()
. Pero hay cosas que son imposibles de realizar si usamos delay()
. Sobre todo si se quiere realizar varias cosas a la vez.
Para ver cómo se trabaja y tener una idea del uso de millis()
y máquinas de estados recomiendo ciertos hilos de este mismo foro. Algunos de ellos se publicaron directamente como tutoriales. Mientras que otros son consultas que se hicieron y en las que yo he aportado mi granito de arena, tratando de explicar cómo hacer algunas cosas. Esto son los enlaces a los hilos:
-
Sobre las máquinas de estados:
-
Sobre los
millis()
: -
Cuestión de estilo de programación:
-
Ejemplos de soluciones con máquinas de estados y
millis()
: -
Cómo evitar los
for
: -
Nunca está de más conocer cosas sobre las cadenas de C y las de C++:
Nota: con la migración del foro de Arduino a la nueva plataforma, se ha perdido el formato en algunas ocasiones y esto hace que se vean algunas cosas mal o "raras".
En cuanto al planteamiento de las consultas. Nunca está de más aportar la máxima información posible. Nada de decir sólo «utilizo un sensor de temperatura»; lo mejor es poner la referencia del sensor o un enlace donde se obtenga información detallada de él. Si se utilizan librerías, siempre viene bien decir de dónde se descargaron. Porque muchas veces hay diferentes versiones de la misma librería y no siempre se comportan igual. También es muy útil un diagrama de conexiones de las cosas. Aunque sean cuatro garabatos mal hechos.
Muchas veces, aunque el problema aparece en una parte del código, el origen del problema está en el extremo opuesto de dónde se está mirando. Por eso es muy importante, a veces, el aportar todo el código y no una parte de él. En infinidad de ocasiones el problema ha estado en la definición de una variable al principio del código.
Lo más importante de todo es explicar, lo más detallado posible, qué es lo que se quiere hacer y cómo se quiere que se comporte el Arduino. Es habitual la consulta en la que dicen que quieren que se encienda un led al pulsar un botón, y diez comentarios después aclaran que lo que se quiere es que se encienda al pulsar dos veces seguidas. Pues si es así, se comenta desde el principio y se especifica claramente qué es lo que se considera "dos veces seguidas". Que entre otras cosas se especifique cuánto es el máximo tiempo que ha de transcurrir entre cada pulsación, para considerarlo "seguidas". Lo dicho, cuanto más detalles se den, mejor.
Mi respuesta para este caso en particular:
Por lo que he leído de varias consultas que has hecho, tengo la impresión de que todas van alrededor de un mismo proyecto y que llevas mucho tiempo con este proyecto. Y que tal vez no sea tan pequeño como aparenta. No sé si lo que te interesa en sí es el proyecto porque es algo de utilidad para ti; o si lo usas como excusa para aprender a programar; o si es una mezcla de ambas cosas a partes iguales.
Yo te recomiendo informarte sobre las máquinas de estados y el uso de millis()
. Pero si en tu código hay un delay()
y no es en setup()
, me plantearía rehacer el proyecto de “casi cero”. Digo “casi cero” porque hay muchas cosas que has aprendido en todo este tiempo, que cuando empezaste no sabías, todo eso es un trabajo muy importante que ya has hecho. No des por perdido todo lo que hasta ahora has hecho y que tal vez tengas que “descartar”. Te ha servido para no empezar desde cero.
Yo más de una vez he “apartado” todo lo que tenía hecho y empezado desde “casi cero”. Tomando partes de lo que hasta entonces había hecho, para integrarlo con modificaciones en un nuevo código.
Ten en cuenta que un programa hecho a base de delay()
no se parece en nada a un programa hecho con máquinas de estados y millis()
.
Si nos planteas y detallas todo lo que tienes en mente, y compartes tu conocimiento adquirido, tal vez nos sea mucho más fácil ayudarte. De hecho, con sólo tratar de explicar tus ideas, problemas y posibles soluciones, puede que veas el problema y encuentres la solución sin más.