Problem with rotaey detection

Hello everybody. I'm not so good at coding so bear me with my low coding knowledge. So i wanted to make a heater for my self and i already built it but it has one issue that i couldn't fix it.(btw , i mostly wrote the code using chatGPT and did some adjustments for my need.) so the problem is the fact when i rotate the rotary encoder some time it gets confused and instead of counting up it counts down and vise versa. I did check the rotary with same arduino and same wiring in a different code( i used the simple library code ) and in that code it just worked fine but when i upload this code it doesn't work. i did few things but it didn't help.
please if you know even one simple thing let me know. I also upload the code for you guys to tell me where should i modify .
Thanks , Pourya

#include <Wire.h>
#include <Adafruit_SSD1306.h>
#include <max6675.h>
#include <Encoder.h>

#define SCREEN_WIDTH 128
#define SCREEN_HEIGHT 64
#define OLED_RESET    -1
#define RELAY_PIN     12
#define MOSFET_PIN    9
#define BUZZER_PIN    8
#define ENCODER_PIN1  13
#define ENCODER_PIN2  7
#define SWITCH_PIN    4
#define THERMO_SO     5
#define THERMO_CS     6
#define THERMO_SCK    10
#define STANDBY_PIN   11

Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
MAX6675 thermocouple(THERMO_SCK, THERMO_CS, THERMO_SO);
Encoder myEnc(ENCODER_PIN1, ENCODER_PIN2);

int menuPos = 0;
bool heaterState = false;
float setTemp = 100.0;
int fanSpeed = 0;
long oldPosition = -999;
float currentTemp = 0.0;
bool standbyMode = false;
unsigned long standbyStartTime = 0;
unsigned long lastEncTime = 0;
const int encDebounce = 20; 

void setup() {
  pinMode(RELAY_PIN, OUTPUT);
  pinMode(MOSFET_PIN, OUTPUT);
  pinMode(BUZZER_PIN, OUTPUT);
  pinMode(SWITCH_PIN, INPUT_PULLUP);
  pinMode(STANDBY_PIN, INPUT_PULLUP);
  
  display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  display.setTextColor(WHITE);
  display.clearDisplay();
  
  digitalWrite(RELAY_PIN, LOW);
  analogWrite(MOSFET_PIN, map(fanSpeed, 0, 100, 77, 255));
}

void loop() {
  if (digitalRead(STANDBY_PIN) == LOW && !standbyMode) {
    standbyMode = true;
    standbyStartTime = millis();
    digitalWrite(RELAY_PIN, LOW);
  } else if (digitalRead(STANDBY_PIN) == HIGH && standbyMode) {
    standbyMode = false;
    analogWrite(MOSFET_PIN, map(fanSpeed, 0, 100, 77, 255));
  }

  if (standbyMode) {
    unsigned long elapsedTime = (millis() - standbyStartTime) / 1000;
    if (elapsedTime < 120) {
      analogWrite(MOSFET_PIN, 255);
      displayStandby(elapsedTime);
    } else {
      digitalWrite(RELAY_PIN, LOW);
      analogWrite(MOSFET_PIN, 0);
      displayStandby(elapsedTime);
    }
    return;
  }

  currentTemp = thermocouple.readCelsius();
  
  
  long newPosition = myEnc.read(); 
  if (newPosition != oldPosition && millis() - lastEncTime > encDebounce) {
    if (newPosition > oldPosition) {
      adjustValue(1);  
    } else if (newPosition < oldPosition) {
      adjustValue(-1); 
    }
    oldPosition = newPosition;
    lastEncTime = millis();
  }
  
  if (digitalRead(SWITCH_PIN) == LOW) {
    menuPos = (menuPos + 1) % 3;
    tone(BUZZER_PIN, 1000, 100);
    delay(200);
  }
  
  if (heaterState && currentTemp < setTemp) {
    digitalWrite(RELAY_PIN, HIGH);
  } else {
    digitalWrite(RELAY_PIN, LOW);
  }
  
  analogWrite(MOSFET_PIN, map(fanSpeed, 0, 100, 77, 255));
  
  updateDisplay();
}

void adjustValue(int direction) {
  switch(menuPos) {
    case 0: heaterState = !heaterState; break;
    case 1: setTemp += direction * 5; setTemp = constrain(setTemp, 20, 430); break;
    case 2: fanSpeed += direction * 5; fanSpeed = constrain(fanSpeed, 0, 100); break;
  }
}

void updateDisplay() {
  display.clearDisplay();
  display.setTextSize(1);
  display.setCursor(0,0);
  display.print("Heater: ");
  display.print(heaterState ? "ON" : "OFF");
  display.setCursor(0,20);
  display.print("Temp: ");
  display.print(currentTemp);
  display.print("/");
  display.print(setTemp);
  display.print("C");
  display.setCursor(0,40);
  display.print("Fan: ");
  display.print(fanSpeed);
  display.print("%");
  display.setCursor(110, menuPos * 20);
  display.print(">");
  display.display();
}

void displayStandby(unsigned long elapsedTime) {
  display.clearDisplay();
  display.setTextSize(1);
  if (elapsedTime < 120) {
    display.setCursor(0, 10);
    display.print("Heater on Stand");
    display.setCursor(0, 30);
    display.print("Cooldown: ");
    display.print(120 - elapsedTime);
    display.print("s");
  } else {
    display.setCursor(0, 20);
    display.print("Standby...");
  }
  display.display();
}

Oh i forgot to mention that im using a pro mini for the brain of this heater

So why don't you use that code?

I tried to implement it but it didn't work for some reason

Since you know it works by itself, I suggest you try to use it in your code and try to figure out why it does not work.

Do you have code that uses the simple rotary encoder library?

#include <Encoder.h>

// Change these two numbers to the pins connected to your encoder.
//   Best Performance: both pins have interrupt capability
//   Good Performance: only the first pin has interrupt capability
//   Low Performance:  neither pin has interrupt capability
Encoder myEnc(5, 6);
//   avoid using pins with LEDs attached

void setup() {
  Serial.begin(9600);
  Serial.println("Basic Encoder Test:");
}

long oldPosition  = -999;

void loop() {
  long newPosition = myEnc.read();
  if (newPosition != oldPosition) {
    oldPosition = newPosition;
    Serial.println(newPosition);
  }
}

So this was the code that i tested with and i tried to use it in my code but it didn't work

Try using pins 2 and 3 in your original code for the encoder. They are the 328 interrupt pins and should speed up reading the encoder

i did try it at first. but nothing changed. i think some kind of debouncing?

You should also change the way updateDisplay() works. Clearing the display and rewriting the same stuff every time takes a lot of time and can interfer with reading the encoder.
Don't blindly clear the display and only update things that need to be updated.

Is your encoder wired properly with pull-up and filter capacitors?

yes im using a rotary encoder module ky-040

The code given to you by chat is a mess.
I would start over.

which one ? my main code?

Yes the main. Did you try making the changes I suggested?

First describe exactly what you are trying to do and include a wiring diagram/schematic of your set-up.

Yes i tried somethings
but i forgot to mention that one of my encoders are on pin 13
can this thing be the problem?

why can't you use pins 2 and 3?

I think it had some problem or something
but im going to test it with 2 and 3
and does it matter which pin i connect to pin 2 and 3?
I mean clk to2 or clk to 3. Does it matter?

does not matter

Ok thanks. Im going to test it and write the results.

Thank you for your help. i don't know why from the beginning i didn't use 2 and 3. I think when i started this project my code was buggy and 2 and 3 didn't work so i moved the pin to 7 and 13.

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