Botones para sustituir el encoder

Hola
Por favor si alguien me puede ayudar con esto que quiero hacer.
Tengo un skecth donde se usa un encoder para cambiar la frecuencia de un sintetizador y quiero obviar el encoder y hacer lo mismo con dos botones uno para adelante y otro para atras.
Gracias por adelantado
wj6c(at)arrl.net

Su publicacion se MUEVE a su ubicacion actual ya que es mas adecuada.

Ok, entonces empecemos por el principio...
Sube el código que tienes (lee como hacerlo correctamente en Normas del Foro, punto 7) porque somos simples mortales y no adivinos. :wink:

Muy simple.
Cuando el enconder gira en sentido horario subes, bueno eso lo repites con un botón que será el de incremento.
Cuando el encoder gira en el otro sentido antihorario bajas o sea con el botón decrementaras tu valor de frecuencia.
Listo, extremadamente simple.
Conecta cada botón entre GND y pin, usa input_pullup en la definición y mal que mal ya lo tienes.
Si rebotan los botones agrega una rutina antirebotes como Bounce2.h

Moderador:
Por favor, lee las Normas del foro
Si posteas en el foro en inglés usa idioma inglés para expresarte.
Si escribes en español debes usar el foro Arduino en español.

Gracias, una disculpa y voy a tomar muy encuenta la recomendacion.

Disculpenme si estoy haciendo algo mal hecho por no entender lo que acabo de leer.
Este es el sketch en cuestion y si es necesario puedo subir el diagrama electrico, creo voy a hcerlo de todas formas.
Este skecth me trabaja muy bien y quiero hacer el pcb bien pequeño usando 7 segmentos de la serie CL2351 28x11mm y la MAX7219/21.

// Si5351 VFO, CLK0, CLK2, 20m, 8-digit 7-segnemt LED display MAX7219, 50Hz/1000Hz, v0.1
// 25.01.2019, Arduino IDE v1.8.8, Original from LZ2WSG, KN34PC,modified by WJ6C(FI=8.192MHz,7.0-7.3.0, CLK2 activated,si5351_set_freq(-rx + IF_FREQ) 
//---------------------------------------------------------------------------------------------------------
#include "src/Rotary.h"                 // http://www.buxtronix.net/2011/10/rotary-encoders-done-properly.html
#include "src/si5351.h"                 // https://github.com/etherkit/Si5351Arduino, v2.1.2
#include "src/LedControl.h"             // https://github.com/wayoda/LedControl/releases

#define DEFAULT_RX    7110000
#define BAND_L        7000000
#define BAND_H        7300000
#define IF_FREQ       8193700
#define SW_STEP       A0                // encoder step switch
#define ENC_INC_1     50                // encoder increment 1
#define ENC_INC_2     1000              // encoder increment 2

Rotary r = Rotary(2, 3);
Si5351 si5351(0x60);                    // Si5351 I2C address
LedControl lc = LedControl(8, 10, 9, 1); // LED display (DIN, CLK, CS, no. devices)

uint32_t rx = DEFAULT_RX;
uint32_t enc_inc = ENC_INC_2;
int8_t enc_dir = 0;                     // -1 DIR_CCW, 0 DIR_NONE, 1 DIR_CCW
bool ch_flag = true;
bool step_point = false;
//---------------------------------------------------------------------------------------------------------
void setup() {
  pinMode(SW_STEP, INPUT_PULLUP);

  attachInterrupt(0, rotary_encoder, CHANGE);
  attachInterrupt(1, rotary_encoder, CHANGE);

  si5351.init(SI5351_CRYSTAL_LOAD_8PF, 0, 27000);  // crystal 25.000 MHz, my correction is 7500 ???
  si5351.set_freq(IF_FREQ * SI5351_FREQ_MULT, SI5351_CLK2);  // Fif, enable/disable CLK2

  lc.shutdown(0, false);//(Do not use saving mode)
  lc.setIntensity(0, 1);//(Brignetss control, it is from 0 to 15)
  lc.clearDisplay(0);
}
//---------------------------------------------------------------------------------------------------------
void loop() {
  if (ch_flag) {
    ch_flag = false;
    rx += enc_dir * enc_inc;
    enc_dir = 0;
    rx = constrain(rx, BAND_L, BAND_H);

    //si5351_set_freq(rx - IF_FREQ);      // Fhet = Fin - Fif
     si5351_set_freq(-rx + IF_FREQ  );   // Fhet = Fin + Fif

    show_freq(rx);
  }

  if (digitalRead(SW_STEP) == LOW) {    // increment events
    if (button_state(SW_STEP) > 0) {
      set_inc();
      show_inc();
      do {
      }
      while (digitalRead(SW_STEP) == LOW);
    }
  }
}
//---------------------------------------------------------------------------------------------------------
void rotary_encoder() {                 // rotary encoder events
  uint8_t result = r.process();

  if (result) {
    ch_flag = true;
    if (result == DIR_CW)
      enc_dir = 1;
    else
      enc_dir = -1;
  }
}
//---------------------------------------------------------------------------------------------------------
void si5351_set_freq(uint32_t frequency) {
  si5351.set_freq(frequency * SI5351_FREQ_MULT, SI5351_CLK0);
}
//---------------------------------------------------------------------------------------------------------
void set_inc() {
  if (enc_inc == ENC_INC_1) {
    enc_inc = ENC_INC_2;                // 1000 Hz, round to XX.XXX.000
    float tmp = round (rx / (ENC_INC_2 * 1.000));
    rx = (uint32_t)(tmp * ENC_INC_2);
    ch_flag = true;
    step_point = false;
  }
  else {
    enc_inc = ENC_INC_1;                // 50 Hz
    step_point = true;
  }
}
//---------------------------------------------------------------------------------------------------------
void show_inc() {
  uint8_t x010  = (rx / 10) % 10;

  lc.setDigit(0, 0, x010, step_point);
}
//---------------------------------------------------------------------------------------------------------
void show_freq(uint32_t sf_rx) {
  uint8_t x010m = sf_rx / 10000000;
  uint8_t x001m = (sf_rx / 1000000) % 10;
  uint8_t x100k = (sf_rx / 100000) % 10;
  uint8_t x010k = (sf_rx / 10000) % 10;
  uint8_t x001k = (sf_rx / 1000) % 10;
  uint8_t x100  = (sf_rx / 100) % 10;
  uint8_t x010  = (sf_rx / 10) % 10;

  if (x010m > 0)
    lc.setDigit(0, 6, x010m, false);
  lc.setDigit(0, 5, x001m, true);
  lc.setDigit(0, 4, x100k, false);
  lc.setDigit(0, 3, x010k, false);
  lc.setDigit(0, 2, x001k, true);
  lc.setDigit(0, 1, x100, false);
  lc.setDigit(0, 0, x010, step_point);
}
//---------------------------------------------------------------------------------------------------------
uint8_t button_state(uint8_t pin_bt) {  // push button state: 0(very fast), 1(fast), 2(slow)
  uint32_t t_start;
  uint32_t t_bt = 0;
  uint8_t bt_state;

  t_start = millis();
  while (!digitalRead(pin_bt)) {
    t_bt = millis() - t_start;
    if (t_bt > 1000)
      break;
  }
  if (t_bt < 20)                        // 'nothing' for debounce
    bt_state = 0;
  else if (t_bt < 400)                  // fast
    bt_state = 1;
  else                                  // slow
    bt_state = 2;
  return bt_state;
}


Gracias a todos por la ayuda.

Buenas a todos
Creo la solicon que me propones no sirve, ya eso por logica pense que serviria, pero no es asi, poniendo a gnd D2 o D3 nada sucede.
Quizas tenga ademas que usar "input_pullup
Pruebo y les comento
Gracias

Pero no dijo que reemplaces los dos contactos del encoder por pulsadores y nada más.
Tienes que cambiar el código también, por eso te sugirió que uses la librería Bounce2 para leer los pulsadores.

De hecho si la idea es eliminar el encoder vas a tener que agregar un tercer pulsador para sustituir el del propio encoder y que se conecta a A0.

Lo tengo hasta aqui pero no se me mueve la frecuencia...

// Si5351 VFO, CLK0, CLK2, 20m, 8-digit 7-segnemt LED display MAX7219, 50Hz/1000Hz, v0.1
// 25.01.2019, Arduino IDE v1.8.8, Original from LZ2WSG, KN34PC,modified by WJ6C(FI=8.192MHz,7.0-7.3.0, CLK2 activated,si5351_set_freq(-rx + IF_FREQ) 
//---------------------------------------------------------------------------------------------------------
//#include "Rotary.h"                 // http://www.buxtronix.net/2011/10/rotary-encoders-done-properly.html
#include "si5351.h"                 // https://github.com/etherkit/Si5351Arduino, v2.1.2
#include "LedControl.h"             // https://github.com/wayoda/LedControl/releases

#define DEFAULT_RX    7110000
#define BAND_L        7000000
#define BAND_H        7300000
#define IF_FREQ       8193700
#define SW_STEP       A0                // encoder step switch
#define SW_STEPU       2                // encoder step up switch
#define SW_STEPD       3                // encoder step down switch

#define ENC_INC_1     50                // encoder increment 1
#define ENC_INC_2     1000              // encoder increment 2

//Rotary r = Rotary(2, 3);
Si5351 si5351(0x60);                    // Si5351 I2C address
LedControl lc = LedControl(8, 10, 9, 1); // LED display (DIN, CLK, CS, no. devices)

uint32_t rx = DEFAULT_RX;
uint32_t enc_inc = ENC_INC_2;
int8_t enc_dir = 0;                     // -1 DIR_CCW, 0 DIR_NONE, 1 DIR_CCW
bool ch_flag = true;
bool step_point = false;
//---------------------------------------------------------------------------------------------------------
void setup() {
  pinMode(SW_STEP, INPUT_PULLUP);
  pinMode(SW_STEPU, INPUT_PULLUP);
  pinMode(SW_STEPD, INPUT_PULLUP);

//  attachInterrupt(0, rotary_encoder, CHANGE);
//  attachInterrupt(1, rotary_encoder, CHANGE);

  si5351.init(SI5351_CRYSTAL_LOAD_8PF, 0, 27000);  // crystal 25.000 MHz, my correction is 7500 ???
  si5351.set_freq(IF_FREQ * SI5351_FREQ_MULT, SI5351_CLK2);  // Fif, enable/disable CLK2

  lc.shutdown(0, false);//(Do not use saving mode)
  lc.setIntensity(0, 1);//(Brignetss control, it is from 0 to 15)
  lc.clearDisplay(0);
}
//---------------------------------------------------------------------------------------------------------
void loop() {
  if (ch_flag) {
    ch_flag = false;
    rx += enc_dir * enc_inc;
    enc_dir = 0;
    rx = constrain(rx, BAND_L, BAND_H);

    //si5351_set_freq(rx - IF_FREQ);      // Fhet = Fin - Fif
     si5351_set_freq(-rx + IF_FREQ  );   // Fhet = Fin + Fif

    show_freq(rx);
  }

  if (digitalRead(SW_STEP) == LOW) {    // increment events
    if (button_state(SW_STEP) > 0) {
      set_inc();
      show_inc();
      do {
      }
      while (digitalRead(SW_STEP) == LOW);
    }
  }

  if (digitalRead(SW_STEPU) == LOW) {    // increment events
    if (button_state(SW_STEP) > 0) {
        ch_flag = true;
        enc_dir = 1;
      do {
      }
      while (digitalRead(SW_STEP) == LOW);
    }
  }
  if (digitalRead(SW_STEPD) == LOW) {    // increment events
    if (button_state(SW_STEP) > 0) {
        ch_flag = true;
        enc_dir = -1;
      do {
      }
      while (digitalRead(SW_STEP) == LOW);
    }
  }
  
}
//---------------------------------------------------------------------------------------------------------
//void rotary_encoder() {                 // rotary encoder events
//  uint8_t result = r.process();
//
//  if (result) {
//    ch_flag = true;
//    if (result == DIR_CW)
//      enc_dir = 1;
//    else
//      enc_dir = -1;
//  }
//}
//---------------------------------------------------------------------------------------------------------
void si5351_set_freq(uint32_t frequency) {
  si5351.set_freq(frequency * SI5351_FREQ_MULT, SI5351_CLK0);
}
//---------------------------------------------------------------------------------------------------------
void set_inc() {
  if (enc_inc == ENC_INC_1) {
    enc_inc = ENC_INC_2;                // 1000 Hz, round to XX.XXX.000
    float tmp = round (rx / (ENC_INC_2 * 1.000));
    rx = (uint32_t)(tmp * ENC_INC_2);
    ch_flag = true;
    step_point = false;
  }
  else {
    enc_inc = ENC_INC_1;                // 50 Hz
    step_point = true;
  }
}
//---------------------------------------------------------------------------------------------------------
void show_inc() {
  uint8_t x010  = (rx / 10) % 10;

  lc.setDigit(0, 0, x010, step_point);
}
//---------------------------------------------------------------------------------------------------------
void show_freq(uint32_t sf_rx) {
  uint8_t x010m = sf_rx / 10000000;
  uint8_t x001m = (sf_rx / 1000000) % 10;
  uint8_t x100k = (sf_rx / 100000) % 10;
  uint8_t x010k = (sf_rx / 10000) % 10;
  uint8_t x001k = (sf_rx / 1000) % 10;
  uint8_t x100  = (sf_rx / 100) % 10;
  uint8_t x010  = (sf_rx / 10) % 10;

  if (x010m > 0)
    lc.setDigit(0, 6, x010m, false);
  lc.setDigit(0, 5, x001m, true);
  lc.setDigit(0, 4, x100k, false);
  lc.setDigit(0, 3, x010k, false);
  lc.setDigit(0, 2, x001k, true);
  lc.setDigit(0, 1, x100, false);
  lc.setDigit(0, 0, x010, step_point);
}
//---------------------------------------------------------------------------------------------------------
uint8_t button_state(uint8_t pin_bt) {  // push button state: 0(very fast), 1(fast), 2(slow)
  uint32_t t_start;
  uint32_t t_bt = 0;
  uint8_t bt_state;

  t_start = millis();
  while (!digitalRead(pin_bt)) {
    t_bt = millis() - t_start;
    if (t_bt > 1000)
      break;
  }
  if (t_bt < 20)                        // 'nothing' for debounce
    bt_state = 0;
  else if (t_bt < 400)                  // fast
    bt_state = 1;
  else                                  // slow
    bt_state = 2;
  return bt_state;
}

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.