[partage] Librairie Minuteur (gestion de délais)

Bonjour

Suite de la série "petites librairies en français et simples d'utilisation à destination des débutants"

Voici une librairie qui permet de gérer le temps, spécialement conçue pour les personnes qui ne sont pas à l'aise avec la fonction millis().

A l'image de l'ustensile de cuisine, le minuteur est un dispositif que l'on met en marche pour une certaine durée, avant de passer à l'étape suivante.

Après installation, les exemples d'utilisation sont disponibles directement depuis l'IDE Arduino.
Ces exemples montrent une manière alternative, et peut-être plus accessible, d'arriver à faire ce fameux "blink without delay", ou encore de gérer le cadencement de différentes actions pour arriver à faire "plusieurs choses à la fois".

Header :

//Librairie Arduino pour la gestion de délais
//En utilisant la notion de minuteur
//Version 2.0
//
//8 octets alloués en RAM par minuteur
//
//Bricoleau 2016

#ifndef simpleMinuteur_h
#define simpleMinuteur_h

#include <Arduino.h>

class simpleMinuteur
{
  public :
    //constructeur
    simpleMinuteur(uint32_t duree_ms = 0); //si le minuteur a toujours la même durée, la renseigner dès la construction

    //actions essentielles
    void demarrer();                       //lance le minuteur à partir de maintenant et pour la durée pré-enregistrée
    void demarrer(uint32_t duree_ms);      //lance le minuteur à partir de maintenant pour une durée différente
    void redemarrer();                     //relance le minuteur à la suite du précédent (utile pour cadence régulière)
    void redemarrer(uint32_t duree_ms);    //relance le minuteur à la suite du précédent, mais sur une durée différente
    operator bool();                       //Retourne true si le minuteur est terminé, puis le redémarre

    //état du minuteur
    uint32_t duree() const                 {return this->_duree;}
    uint32_t tempsEcoule() const           {return millis() - this->_millis_depart;}

    bool     estActif() const              {return tempsEcoule() <  duree();}
    bool     estTermine() const            {return tempsEcoule() >= duree();}
    uint32_t tempsRestant() const          {return estTermine() ? 0 : duree() - tempsEcoule();}

    //actions secondaires
    void repousser(uint32_t duree_ms);     //ajoute une duree supplémentaire à celle pré-enregistrée

  private :
    uint32_t _millis_depart, _duree;
};

#endif

simpleMinuteur.zip (4.43 KB)

1 Like

Super librairie!

Je l'utilise (avec simpleBouton V2) dans mon projet de réalisation d'une pico brasserie et elles me rendent bien des services!

Merci à toi :wink:

Merci pour ce retour d'utilisation :slight_smile:

Du coup, je viens de mettre à jour le .zip attaché au premier post.

La librairie en V2 contient à présent une nouvelle fonction bien utile : le minuteur peut être utilisé comme un booléen, et redémarre automatiquement.

Ainsi, par exemple, pour exécuter une fonction1() chaque seconde, et une fonction2() toutes les 5 secondes, le code est :

simpleMinuteur tempo1(1000);
simpleMinuteur tempo2(5000);
...
void loop()
{
  if (tempo1) fonction1();
  if (tempo2) fonction2();
}

Difficile de faire plus simple :stuck_out_tongue:

Autre exemple que j'aime bien :

Couplé à la lib simpleLed, le fameux "blink without delay" devient minimaliste :

simpleLed led(13);
simpleMinuteur tempo(1000);

void setup() {}
void loop()  {if (tempo) led.basculer();}

Sympa !
Il y a possibilité de travailler dans l'ordre de la mico-seconde ?

Pas avec la librairie telle que fournie, mais c'est très facile à modifier.

Il suffit d'éditer les fichiers .h et .cpp, en remplaçant partout "millis" par "micros".
Tous les délais sont alors des microsecondes, au lieu de millisecondes

Merci pour cette librairie vraiment très pratique.
J'ai eu un doute à cause de la fonction millis() car elle se réinitialise au bout d'environ 50 jours (unsigned long). Mais en fait, ce n'est pas un problème, ça marche quand même :slight_smile:

Bonjour

Effectivement, le retour à zéro de la fonction millis() est sans conséquence pour un minuteur.

Bonjour,

Je cherche à faire des animations pour des maquettes à l'aide de leds (Forge, Cheminee, Gyrophare, Eclairage public,etc...).
J'ai réussi à faire une petite bibliothèque de mes animations avec:
-le Constructeur ou je définie la broche consernée.
-une fonction .begin(arg1,arg2....arg x) dans le setup pour définir mon objet.
-une fonction .on() pour la mettre en marche.
-une fonction .off() pour l’arrêter.

Je cherche maintenant à créer une "TimeLine" ( une journée accélérée ) où je pourrais activer mes animations.

Je suis tombé sur votre bibliothèque qui a l'air bien simple mais tous les exemples sont des minuteurs qui bouclent.

Par exemple, j'ai imaginé une journée de 1440 minutes(chaque minute valant 1 seconde)quand elle atteint 24H, elle repart a 0.
de 0 à 350 mn eclairagePublic.on();
de 0 à 360 mn phare.on();
de300 à 320mn passageNiveau.on();
de 600 à720 mn forge.on();
etc....
Peut-on faire ça simplement avec votre bibliothèque?
J'ai essayé avec des if() mais ça marche moyennement et ce n'est pas bien souple....
Merci de m'aider .

Bonjour

Cette librairie est faite pour gérer des durées, et non des événements sur programmation horaire.

Quand tu cuisines, ton minuteur ne connaît pas l'heure courante. Il mesure juste la durée de cuisson.
Là c'est pareil :slight_smile:

Du coup j'ai répondu plus précisément à ta question ICI pour ne pas mélanger les sujets

Merci. Une bonne option cette librairie.

bricoleau:
Bonjour

Suite de la série "petites librairies en français et simples d'utilisation à destination des débutants"

Voici une librairie qui permet de gérer le temps, spécialement conçue pour les personnes qui ne sont pas à l'aise avec la fonction millis().

A l'image de l'ustensile de cuisine, le minuteur est un dispositif que l'on met en marche pour une certaine durée, avant de passer à l'étape suivante.

Après installation, les exemples d'utilisation sont disponibles directement depuis l'IDE Arduino.
Ces exemples montrent une manière alternative, et peut-être plus accessible, d'arriver à faire ce fameux "blink without delay", ou encore de gérer le cadencement de différentes actions pour arriver à faire "plusieurs choses à la fois".

Header :

//Librairie Arduino pour la gestion de délais

//En utilisant la notion de minuteur
//Version 2.0
//
//8 octets alloués en RAM par minuteur
//
//Bricoleau 2016

#ifndef simpleMinuteur_h
#define simpleMinuteur_h

#include <Arduino.h>

class simpleMinuteur
{
  public :
    //constructeur
    simpleMinuteur(uint32_t duree_ms = 0); //si le minuteur a toujours la même durée, la renseigner dès la construction

//actions essentielles
    void demarrer();                      //lance le minuteur à partir de maintenant et pour la durée pré-enregistrée
    void demarrer(uint32_t duree_ms);      //lance le minuteur à partir de maintenant pour une durée différente
    void redemarrer();                    //relance le minuteur à la suite du précédent (utile pour cadence régulière)
    void redemarrer(uint32_t duree_ms);    //relance le minuteur à la suite du précédent, mais sur une durée différente
    operator bool();                      //Retourne true si le minuteur est terminé, puis le redémarre

//état du minuteur
    uint32_t duree() const                {return this->_duree;}
    uint32_t tempsEcoule() const          {return millis() - this->_millis_depart;}

bool    estActif() const              {return tempsEcoule() <  duree();}
    bool    estTermine() const            {return tempsEcoule() >= duree();}
    uint32_t tempsRestant() const          {return estTermine() ? 0 : duree() - tempsEcoule();}

//actions secondaires
    void repousser(uint32_t duree_ms);    //ajoute une duree supplémentaire à celle pré-enregistrée

private :
    uint32_t _millis_depart, _duree;
};

#endif

bonjour,
débutant en Arduino et ne connaissant rien du c++ , j'ai regardé avec beaucoup d'intérêt cette biblioteque
simpleminuteur.h.
j'aurai bien voulu essayer de voir sur le moniteur serie le temps en train de s'écouler quand une temporisation
est en cours , je n'est pas vu celà dans les exemples proposés
j'ai essayé differentes choses avec duree et tempsEcoule mais je ne connais pas la syntaxe et çà ne marche pas
merci d'avance pour votre aide.

Bonjour

guillaumetell:
bonjour,
débutant en Arduino et ne connaissant rien du c++ ...

C'est par là qu'il faut commencer : apprendre les bases de la programmation, via un des multiples tutos disponibles sur internet.

La primitive .tempsEcoule() donne tout simplement le temps écoulé en millisecondes, depuis le démarrage du minuteur.

Voici un exemple de programme qui permet d'observer le temps écoulé sur le moniteur série.

Et pour réaliser cette observation, j'utilise tout simplement un minuteur secondaire qui se déclenche une fois par seconde.

#include "simpleMinuteur.h"

simpleMinuteur principal(20000);
simpleMinuteur secondaire(1000);

void setup() {
  Serial.begin(9600);
  principal.demarrer();
  secondaire.demarrer();
}

void loop() {
  if (secondaire) { //on entre dans le if une fois par seconde
    Serial.print("Minuteur principal ");
    if (principal.estActif()) {
      Serial.print("actif");
    } else {
      Serial.print("termine");
    }
    Serial.print(", temps ecoule = ");
    Serial.print(principal.tempsEcoule());
    Serial.println(" ms");
  }
}

(deleted)

Merci pour cet outil,

Peut-on incrémenter la durée du Minuteur secondaire ?
Pour faire une action qui s’accélère ou décélère .....

merci :slight_smile:

Pierre_VINSON:
Peut-on incrémenter la durée du Minuteur secondaire ?

si vous regardez les fonctions dispo vous avez la fonction

void repousser(uint32_t duree_ms);     //ajoute une duree supplémentaire à celle pré-enregistrée

Pierre_VINSON:
Pour faire une action qui s’accélère ou décélère .....

la fonction telle que prévue ne permet que de rajouter une durée donc pas accélérer (réduire la durée du minuteur). On pourrait tricher en sachant qu'un uint32_t fait un rollover et donc en ajoutant une très grande durée on peut finalement retomber sur un timing plus court mais c'est pas super beau..

Pour cela il suffit simplement de relancer le minuteur avec un nouvelle durée par exemple avecvoid redemarrer(uint32_t duree_ms);    //relance le minuteur à la suite du précédent, mais sur une durée différente

Bonsoir , après quelques mois d'initiation au monde d'arduino je commence a prendre un grand plaisir a utiliser cette librairie !

Donc au passage , un grand merci pour ce travail !

Ma question est, peut on gerer un décompte de temps ?

actuellement j'utilise ce code :

 void compte_a_rebours () {

  TempsActuelGame = millis();
  


  if ((TempsActuelGame - TempsPasseeGame >= 1000) && (runing_time)) {
    TempsPasseeGame = TempsActuelGame;
    Temps_de_Jeu -= 1000;
    if (Temps_de_Jeu <= 0) {
      runing_time = false;
      finDePartie = true;
    }
  }
}

.

corrigez votre post ci dessus et rajoutez les code tags autour du code:
[code]`` [color=blue]// votre code ici[/color] ``[/code].

ça doit ressembler à cela:// votre code ici
(faites aussi ctrl-T (PC) or cmd-T (Mac) dans l'IDE avant de copier le code pour qu'il soit indenté correctement)


il semble que vous ayez bien compris comment utiliser millis() donc vous n'avez pas vraiment besoin de la librairie. Vous pourriez sinon mettre un timer toutes les secondes et (dé)compter le nombre de déclenchements pour faire quelque chose de similaire

Désolé ... en fait j'ai répondu a ma question tout seul avant d'envoyer le message mais ... envoyé par erreur et non terminé !

je pense pouvoir simplifier en utilisant un simpleminuteur d'une seule seconde pour remplacer mes quelques lignes ...

est-ce mieux :

void compte_a_rebours () {

 uneSeconde.demarrer();



  if ((uneSeconde.estTermine()) && (runing_time)) {
    uneSeconde.redemarrer();
    Temps_de_Jeu -= 1000;
    if (Temps_de_Jeu <= 0) {
      runing_time = false;
      finDePartie = true;
    }
  }
} //End void

Bonsoir

Je suppose que Temps_de_Jeu est initialisé à une valeur fixe, par exemple 30000 pour 30 secondes.

C'est dommage d'utiliser un minuteur pour compter chaque seconde, le relancer, tout ça pour décrémenter le temps de jeu restant.
Autant utiliser un minuteur qui permet de suivre la totalité du temps de jeu.

donc un truc comme :

simpleMinuteur compte_a_rebours(30000);

...
compte_a_rebours.demarrer();
...
if (runing_time && compte_a_rebours.estTermine()) {
  runing_time = false;
  finDePartie = true;
}

et cerise sur le gâteau, la classe minuteur comporte une fonction tempsRestant()
par exemple, pour afficher chaque seconde le temps restant, via un second minuteur :

simpleMinuteur uneSeconde(1000);
...
if (uneSeconde) { //=true une fois par seconde
  Serial.println(compte_a_rebours.tempsRestant() / 1000);
}

Car comme indiqué dans le header de la lib, un simpleMinuteur peut être utilisé comme un booléen.
Lorsque de délai est expiré, il retourne la valeur true et redémarre tout seul
Pratique :slight_smile: