This commit is contained in:
Grouch 2017-05-07 23:58:54 +02:00
parent dd2a40419d
commit 71bec01111
1 changed files with 95 additions and 95 deletions

View File

@ -1,24 +1,23 @@
//------------------------------------------------------------------------------
// *** STROBODUINO ***
//------------------------------------------------------------------------------
char Ver[] = "cg060517";
char Ver[] = "cg070517";
#include <TimerOne.h> // Timer1 --> timer entre étincelle et Flash
#include <Encoder.h> // Bibiliothèque pour gestion encoder avec anti-rebond
#include <EEPROM.h> // Lect/Ecrit dans l'EEPROM interne à l'ATMEL pour svg des param.
#include <Encoder.h> // Lib pour gestion encoder avec anti-rebond
#include <EEPROM.h> // Lect/Ecr ds l'EEPROM interne à l'AVR pour svg des param.
#include <LiquidCrystal.h> // LCD
#include <RunningAverage.h> // Calcul de moy. glissante pour lisser le compte-tour
#include <QueueArray.h>
//------------------------------------------------------------------------------
// PARAMETRES (stockés dans l'EEPROM)
//------------------------------------------------------------------------------
byte D_Flash = 10; // Durée du flash en µs, autour de 10µs
byte Ncyl = 2; // Nombre de cylindres
byte Refresh = 100; // Refresh du LCD en millisec.
byte D_Flash = 10; // Durée du flash en µs, autour de 10µs
byte Ncyl = 2; // Nombre de cylindres
byte Refresh = 100; // Refresh du LCD en millisec.
bool debug = false; // true si debug
bool debug = true; // true si debug
//------------------------------------------------------------------------------
// CONSTANTES
@ -29,89 +28,80 @@ bool debug = false; // true si debug
#define Flash 11 // Flash
#define Codeur_A 3 // D3 pour entrée codeur A sous interruption
#define Codeur_B 4 // D4 pour entrée codeur B
const byte lissrpm = 3; // Nb de valeurs pour moy. glissante compte-tours
#define T_MINI 100 // T mini acceptable en µs
const byte lissrpm = 30; // Nb de valeurs pour moy. glissante compte-tours
const int deg_Initial = 10; // Affiché au demarrage
//-------------------------------------------------------------------------------
// VARIABLES
//-------------------------------------------------------------------------------
volatile int signed long T = 0; // Periode en cours(signée pour le calcul de D_deg)
volatile int unsigned long prec_H = 0; // Heure du front precedent en µs
int signed deg_dem = deg_Initial; // Compteur des degrés demandés
int signed long D_deg = 0; // Délai pour deg_dem degrès en µs
int unsigned long N = 0; // N en tours/mn
int unsigned long Nc = 0; // Pour le calcul de N
unsigned long pm = 0; // Previous millis pour Refresh LCD
byte modconfig = 0; // Flag pour savoir si on est en mode config
int degT = 720 / Ncyl; // Degrés entre 2 étincelles
bool moteur_tourne = false;
volatile long T = 0L; // Periode en cours(signée pour le calcul de D_deg)
volatile unsigned long prec_H = 0L; // Heure du front precedent en µs
volatile long F = 0L; // Periode Flash
volatile unsigned long prec_F = 0L; // Heure Flash precedent
int deg_dem = deg_Initial; // Compteur des degrés demandés
volatile long D_deg = 0L; // Délai pour deg_dem degrès en µs
unsigned long N = 0L; // N en tours/mn
unsigned long Nc = 120000000L / Ncyl; // Pour le calcul de N
volatile long D = 0L;
unsigned long pm = 0L; // Previous millis pour Refresh LCD
byte modconfig = 0; // Flag pour savoir si on est en mode config
int degT = 720 / Ncyl; // Degrés entre 2 étincelles
volatile bool moteur_tourne = false;
LiquidCrystal lcd( 9, 17, 15, 16, 14, 10);
//lcd(RS, E, D4, D5, D6, D7)
Encoder Enco(Codeur_A, Codeur_B);
RunningAverage RArpm(lissrpm);
QueueArray <int signed long> Q;
volatile RunningAverage moyT(lissrpm);
//--------------------------------------------------------------------------------
// ISR
//--------------------------------------------------------------------------------
void isrEtincelle() {
if (!moteur_tourne){
Timer1.initialize(D);
moteur_tourne=true;}
T = micros() - prec_H; // Calcul de T
prec_H = micros();
if (T < T_MINI) {T = moyT.getAverage();} // Sécurité valeur aberrante
if (!moteur_tourne){
moteur_tourne = true;
Timer1.initialize(D_deg);
}
else {
Q.enqueue(prec_H + D_deg); // Heure flash correspondant à cette Etincelle.
}
//if (debug) {Serial.print("Q : "); Serial.println(Q.count());}
D_deg = (moyT.getAverage() * (long)deg_dem) / (long)degT;
D = D_deg - 200L;
if (D<=80){D+=T;}
// D+=T*2;
// On ajoute la valeur de T au calcul de moy. glissante
moyT.addValue(T);
}
void isrFlash(){
moteur_tourne = false;
Timer1.stop();
// Flash et flash sur LED13
digitalWrite (Flash, 1); delayMicroseconds(D_Flash); digitalWrite (Flash, 0);
//digitalWrite (LED_BUILTIN, 1); delayMicroseconds(5 * D_Flash); digitalWrite (LED_BUILTIN, 0);
digitalWrite (LED_BUILTIN, 1); delayMicroseconds(5 * D_Flash); digitalWrite (LED_BUILTIN, 0);
moteur_tourne=false;
// Délai en µs pour les degrés demandés, periode suivante
D_deg = float(T * (deg_dem + 360)) / float(degT);
int signed long D = 0;
if (!Q.isEmpty()){ // Si y'a des Flashs dans la queue
do {
D = Q.pop() - micros();
if (D > 0) { // et qu'il n'est pas trop tard, on programme le prochain flash
moteur_tourne = true;
Timer1.initialize(D);
}
} while (D <= 0);
}
// On ajoute la valeur de T au calcul de moy. glissante
RArpm.addValue(T);
// DEBUG
if (debug) {Serial.print("T : "); Serial.print(T); Serial.print(" D_deg : "); Serial.println(D_deg);}
if (debug) {Serial.print("degT : "); Serial.print(degT); Serial.print(" deg_dem : "); Serial.println(deg_dem);}
}
F = micros() - prec_F;
prec_F = micros();
}
//--------------------------------------------------------------------------------
// FONCTIONS
//--------------------------------------------------------------------------------
void Affic_N_et_deg_dem(){ // Affiche compte-tour et dégrés demandés
N = Nc / RArpm.getAverage(); // Calculer N en t/mn
N = Nc / moyT.getAverage(); // Calculer N en t/mn
if (N > 99998) {N = 99999;}; // Sécurité affichage
lcd.setCursor(0, 0); lcd.print(" ");
lcd.setCursor(0, 0); lcd.print(N); // Régime tr/min
lcd.setCursor(0, 1); lcd.print(" ");
lcd.setCursor(0, 1); lcd.print(deg_dem); lcd.write(223); // Avance °
if (debug) {lcd.print(""); lcd.print(D); lcd.print(" ");}
}
void Affich_fond_ecran(){ // Affiche le fond d'écran au début ou après la config.
@ -149,27 +139,23 @@ void Regl(bool &var, String titre){ // Macro de réglage pour param type bool
lcd.print(" ");
}
}
while (digitalRead(Inter) == 0); // Si on a appuyé, on attend le relachement
while (digitalRead(Inter) == 0); // Si on a appuyé on attend le relachement
}
void ConfiG() {
lcd.clear();
lcd.print("CONFIG");
lcd.setCursor(7, 1);
lcd.write(126);
while (digitalRead(Inter) == 0); //toujours appuyé ? on attend
// Réglages avec le codeur
Regl(Ncyl, "Nb cyl.");
modconfig=0;
lcd.clear(); lcd.print("CONFIG"); // Titre
lcd.setCursor(7,1); lcd.write(126); // ->
while (digitalRead(Inter) == 0); // toujours appuyé ? on attend
Regl(Ncyl, "Nb cyl."); // Réglages avec le codeur
Regl(D_Flash, "D Flash");
Regl(Refresh, "Refresh");
//Regl(debug, "!DEBUG!");
// Sauvegarde des paramètres dans l'EEPROM
EEPROM.write(0, Ncyl);
EEPROM.write(0, Ncyl); // Svgarde des paramètres dans l'EEPROM
EEPROM.write(1, D_Flash);
EEPROM.write(2, Refresh);
IniT();
}
@ -188,7 +174,8 @@ void IniT() {
// Timer entre Etincelle et Flash
Timer1.attachInterrupt(isrFlash);
Timer1.stop();
//Timer1.initialize(1);
//Timer1.stop();
modconfig=0;
@ -197,8 +184,7 @@ void IniT() {
lcd.print("Strobo"); lcd.setCursor(3, 1); lcd.print("duino");
delay(1200);
// Bouton appuyé
if (digitalRead(Inter) == 0) {modconfig++;}
if (digitalRead(Inter) == 0) {modconfig++;} // Bouton appuyé ?
// Test Flash
digitalWrite (Flash, 1); delayMicroseconds(D_Flash); digitalWrite (Flash, 0);
@ -206,36 +192,39 @@ void IniT() {
// Affichage version
lcd.clear();
lcd.print("Version");
lcd.setCursor(0, 1); lcd.print(Ver); // N° de version
lcd.setCursor(0, 1); lcd.print(Ver); // N° de version
delay(1000);
if (digitalRead(Inter) == 0) {modconfig++;} // si bouton toujours appuyé
if (modconfig >= 2){ // on entre dans le mode config
modconfig=0;
ConfiG();
}
if (digitalRead(Inter) == 0) {modconfig++;} // si bouton toujours appuyé
if (modconfig >= 2) {ConfiG();} // on entre dans le mode config
Enco.write(deg_Initial*4);
degT = 720 / Ncyl;
Nc = 120000000 / Ncyl;
T = 150000;
RArpm.addValue(T);
D_deg = float(T * deg_dem) / float(degT); // Pour le premier cycle
moyT.addValue(T);
D_deg = float(T * deg_dem) / float(degT); // Pour le premier cycle
Affich_fond_ecran();
Affic_N_et_deg_dem();
moteur_tourne = false;
if (debug) {
Serial.print("degT : "); Serial.println(degT);
Serial.print(" Nc : "); Serial.println(Nc);
Serial.print(" Ncyl : "); Serial.println(Ncyl);
}
}
void setup() {
if (debug) {Serial.begin(9600);} // Pour debug
pinMode(Etin, INPUT); // Entrée bobine
pinMode(Flash, OUTPUT); // Sortie FLASH
if (debug) {Serial.begin(9600);} // Pour debug
pinMode(Etin, INPUT); // Entrée bobine
pinMode(Flash, OUTPUT); // Sortie FLASH
pinMode(Codeur_A, INPUT_PULLUP);
pinMode(Codeur_B, INPUT_PULLUP);
pinMode(Inter, INPUT_PULLUP); // Le codeur met son inter à la masse quand poussé
lcd.begin(8, 2); // LCD 8 colonnes, 2 lignes
pinMode(Inter, INPUT_PULLUP); // Le codeur met son inter à la masse
lcd.begin(8, 2); // LCD 8 colonnes, 2 lignes
IniT();
}
@ -244,15 +233,26 @@ void setup() {
//------------------------------------------------------------------------------
void loop(){
if ((millis() - pm) > Refresh) { // Mise à jour affichage LCD
deg_dem = Enco.read()/4; // On lit les degrés demandés via l'encodeur
Affic_N_et_deg_dem(); // Affichage tr/min et deg_demandés
pm = millis();
if (debug) {Serial.print("deg_dem= "); Serial.println(deg_dem);}
if ((millis() - pm) > Refresh) { // Mise à jour affichage LCD
deg_dem = Enco.read()/4; // On lit les degrés demandés via l'encodeur
Affic_N_et_deg_dem(); // Affichage tr/min et deg_demandés
pm = millis();
if (debug) {
Serial.print("T:"); Serial.print(T);
Serial.print(" deg_dem:"); Serial.println(deg_dem);
Serial.print(" D:"); Serial.print(D);
Serial.print(" F:"); Serial.print(F);
Serial.print(" D_deg:"); Serial.println(D_deg);
Serial.print(" pH:"); Serial.print(prec_H);
Serial.print(" pF:"); Serial.println(prec_F);
Serial.print("delta:"); Serial.println(prec_H-prec_F);
}
if (digitalRead(Inter) == 0) { // Si l'inter du codeur est poussé, geler l'affichage
delay(1000); while (digitalRead(Inter) == 0); // Encore poussé, attendre
delay(100); // Continuer
if (digitalRead(Inter) == 0) { // Si inter est poussé, geler l'affichage
delay(1000);
while (digitalRead(Inter) == 0); // Encore poussé, attendre
delay(100); // Continuer
}
}
}}