buen dia comunidad, he estado con algunas dudas en una practica que tengo que realizar, que es un control de RPM mediante un teclado matricial, donde yo le ingreso las rpm que deceo y este responde llegando a las rpm deseadas, pero el motor que se utiliza no es de DC es de AC el cual por medio de un cruce por cero controlo el disparo del triac,pero mi duda es como controlo las rpm por teclado matricial, anteriormente lo habia realizado con un potenciometro pero ahora se requiere con teclado, anexo el codigo hasta dondel llevo si alguien tuviera una idea o me diera una orientacion se los agradeceria
#include <LiquidCrystal.h>
#include <TimerOne.h>
#include <Keypad.h>
LiquidCrystal lcd(14,15,16,17,18,19);
//teclado
int ans;
int cuadro=5;
int fila =0;
int b=0;
int dato;
char regt[]={0,0,0,0};
const byte Rows=4;
const byte Cols=4;
byte pinsFilas[Rows] = {22, 24,26,28};//{A8, A9 , A10, A11}; //{7, 6, 5, 4};
byte pinsColumnas[Cols] ={30, 32, 34, 36 };// {A12,A13,A14,A15}; // {3, 2, 1, 0}
char hexakeys[Rows][Cols]={
{'1','2','3','A'},
{'4','5','6','B'},
{'7','8','9','C'},
{'*','0','#','D'}
};
Keypad tecla=Keypad(makeKeymap(hexakeys),pinsFilas,pinsColumnas,Rows,Cols);
//RPM
int ticsPerRev = 12; // define el numero de ranuras del encoder
float rpm = 0.0; // variable flotante que mide la rpm
volatile int rpmcount =0; //variable manipulada durante las interrupciones
unsigned long timeold = 0; //d_t= millis()-timeold;
int d_t;
int statusPin = 7; // salida al conector de entrada Vcc del encoder
volatile byte status= LOW; // inicializacion del estado
//Cruce por cero
volatile int i=0; // Variable usada como contador
volatile boolean zero_cross=0; // Boolean para la interrupcion del cruce por cero
int AC_pin = 3; // salida al optoTriac
int POT_pin = A0; // entrada del potenciometro
int dim = 128; // Dimming level (0-128) 0 = on, 128 = 0ff
int pass=8;
int dim2,dim3=0;
int freqStep = 65; //frecuencia de lectura a 60Hz formula =10000/120Hz
void setup() {
lcd.begin(16, 2); //inicializacion de la lcd
pinMode(AC_pin, OUTPUT); // salida al MOC
attachInterrupt(0, zero_cross_detect, RISING); // Attach an Interupt to Pin 2 (interupt 0) for Zero Cross Detection
Timer1.initialize(freqStep); // libreria TimerOne inicializada
Timer1.attachInterrupt(dim_check, freqStep);
Serial.begin(9600);
lcd.clear();
//RPM
attachInterrupt(2, rpm_fun, FALLING);
pinMode(statusPin, OUTPUT);
digitalWrite(statusPin,HIGH);
}
//cruce por cero
void zero_cross_detect() {
zero_cross = true;
i=0;
digitalWrite(AC_pin, LOW);
}
//TRIAC
void dim_check() {
if(zero_cross == true) {
if(i>=dim) {
digitalWrite(AC_pin, HIGH);
i=0; //
zero_cross=false; // detector de zero_cross
}
else {
i++; //
}
}
}
void loop() {
dim=analogRead(POT_pin)/8;
//teclado
lcd.setCursor(0,0);
lcd.print("RPM1");
char tiempo = tecla.getKey();
lcd.display();
if(tiempo != NO_KEY){
if(b<=4)
lcd.setCursor(cuadro,fila);
regt[b]=tiempo;
dato=atol(regt);
lcd.print(regt[b]);
b++;
cuadro++;
if(tiempo == '#' ){
lcd.clear();
cuadro=5;
fila=0;
b=0;
dato=0;
dim=128;
}
}
if(dato!=0){
detachInterrupt(2);
d_t=millis()-timeold;
if (d_t >= 1000)
{
rpm = float(60.0*1000.0)/float((d_t))*float(rpmcount)/ticsPerRev;
timeold = millis();
d_t=0; //reset d_t
//Serial Port Output
Serial.print("Time(ms) ");
Serial.print(timeold);
Serial.print(" TicsPerInterval ");
Serial.print(rpmcount);
Serial.print(" RPM ");
Serial.println(rpm);
lcd.setCursor(0,1);
lcd.print("RPM:");
lcd.print(rpm);
rpmcount = 0; //reset rpmcount
}
//Restart the interrupt processing
attachInterrupt(2, rpm_fun, FALLING);
}
}
void rpm_fun()
{
detachInterrupt(2);
rpmcount++; //update rpmcount
attachInterrupt(2, rpm_fun, FALLING);
}