Can someone check my code? Please :)



  • I am trying to put togheter a scenecontroller with LCD display, so far i have started with a sketch made by Gizmocuz over at the domoticz forum for the LCD display (standard 16x2 lcd).

    I did remove some code from the original LCD sketch (powermeter, water etc) and added another temperature sensor to be displayed on the LCD and added some code for my buttons.

    Im not a programmer so i dont realy know what every line of code do and i suspect that something is blocking my buttons. I use touch button modules, but i have to touch the module 10-20 times before it is sent to the controller. The modules works on my ESP so i dont think its a hardware problem.

    Can someone at least point me in the right direction?

    /* LCDDisplay 
     16 character 2 line I2C Display
     Backpack Interface labelled "A0 A1 A2" at lower right.
     ..and
     Backpack Interface labelled "YwRobot Arduino LCM1602 IIC V1"
     MOST use address 0x27, a FEW use 0x3F
    */ 
    
    // Enable debug prints to serial monitor
    #define MY_DEBUG 
    
    // Enable and select radio type attached
    #define MY_RADIO_NRF24
    
    #define MY_NODE_ID 23
    
    #include <Bounce2.h> // Added for button debounce
    #include <SPI.h>
    #include <MySensor.h> 
    #include <Wire.h>
    #include <LiquidCrystal_I2C.h>
    
    // Added buttons
    #define BUTTON_PIN_1  3  // Arduino Digital I/O pin number for button 
    #define BUTTON_PIN_2  4  // Arduino Digital I/O pin number for button 
    
    #define CHILD_ID 1                              // Id of the sensor child 
    #define CHILD_ID_3 2 // Button 1
    #define CHILD_ID_4 3 // Button 2
    
    Bounce debouncer1 = Bounce(); // Added debounce x2
    Bounce debouncer2 = Bounce();
    
    int oldValue1=-1; // Added for buttons
    int oldValue2=-1;
    
    unsigned long POLL_FREQUENCY_TEMP = 600000; // Minimum time between send (in milliseconds). We don't want to spam the gateway.
    unsigned long POLL_FREQUENCY_TEMP2 = 600000;  // Added for temp2
    
    MyMessage pollRequestMsg(CHILD_ID,V_CUSTOM);
    MyMessage msg1(CHILD_ID_3,V_LIGHT); // Added message for buttons
    MyMessage msg2(CHILD_ID_4,V_LIGHT); // Added message for buttons
    
    #define ID_TEMP_HUM_SENSOR_OUTSIDE 7
    #define ID_TEMP_HUM_SENSOR_OUTSIDE2 20
    
    // set the LCD address to 0x27 for a 16 chars 2 line display
    // A FEW use address 0x3F
    // Set the pins on the I2C chip used for LCD connections:
    //                    addr, en,rw,rs,d4,d5,d6,d7,bl,blpol
    LiquidCrystal_I2C lcd(0x3f, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);  // Set the LCD I2C address
    #define LCD_WIDTH 16
    #define LCD_HEIGHT 2
    
    // Creat a set of new characters
    byte cdegrees[8] = {
      0b01100,
      0b10010,
      0b10010,
      0b01100,
      0b00000,
      0b00000,
      0b00000,
      0b00000
    };
    
    unsigned long lastTempPolled=0;
    unsigned long lastTempPolled2=0; // Added for temp2
    String lastTemp;
    String lastHum;
    String lastTemp2; // Added for temp2
    String lastHum2; // Added for temp2
    bool tempReceived=false;
    bool tempReceived2=false; // Added for temp2
    
    void CenterString(String &inText, const int width)
    {
      int osize=inText.length();
      if (osize>=width)
        return;
      int padLeft=(width-osize)/2;
      for (int ii=0; ii<padLeft; ii++)
      {
        inText=" " + inText;
      }
      while (inText.length()<width)
      {
        inText=inText+" ";
      }
    }
    
    String SpaceStrings(const String &lString, const String &rString)
    {
      String lText=lString;
      int ibc = LCD_WIDTH - lText.length() - rString.length();
      while (ibc>0) {
        lText+=" ";
        ibc--;
      }
      lText+=rString;
      return lText;
    }
    
    void setup()
    {
    // Added for buttons
    pinMode(BUTTON_PIN_1,INPUT);
    pinMode(BUTTON_PIN_2,INPUT);
    
    // Activate internal pull-up
    digitalWrite(BUTTON_PIN_1,HIGH);
    digitalWrite(BUTTON_PIN_2,HIGH);
    
    // After setting up the button, setup debouncer
    debouncer1.attach(BUTTON_PIN_1);
    debouncer1.interval(5);
    
    debouncer2.attach(BUTTON_PIN_2);
    debouncer2.interval(5);
    
      lastTemp="-";
      lastHum="-";
      lastTemp2="-";
      lastHum2="-";
    
      lcd.begin(LCD_WIDTH,LCD_HEIGHT);   // initialize the lcd for 16 chars 2 lines, turn on backlight
      
      lcd.createChar (1, cdegrees);    // load character to the LCD
      
      lcd.backlight();
    
      lcd.home ();                   // go home
    
      String sText;
      sText="Velkommen";
      CenterString(sText, LCD_WIDTH);
      lcd.print(sText);
      lcd.setCursor ( 0, 1 );        // go to the next line
      sText="Vennligst vent...";
      CenterString(sText, LCD_WIDTH);
      lcd.print(sText);
      wait(1000);
    }
    
    void presentation()  {
      // Send the sketch version information to the gateway and Controller
      sendSketchInfo("LCD Display", "1.0");
      wait (400); // Added wait to solve problem with st=fail
      present(CHILD_ID_3, S_LIGHT); // Present button
      wait (400); // Added wait to solve problem with st=fail
      present(CHILD_ID_4, S_LIGHT); // Present button
    }
    
    void loop()
    {
      debouncer1.update();
    // Get the update value
    int value1 = debouncer1.read();
    
    if (value1 != oldValue1) {
    // Send in the new value
    send(msg1.set(value1==HIGH ? 1 : 0));
    oldValue1 = value1;
    }
    
    debouncer2.update();
    // Get the update value
    int value2 = debouncer2.read();
    if (value2 != oldValue2) {
    
    // Send in the new value
    send(msg2.set(value2==HIGH ? 1 : 0));
    oldValue2 = value2;
    }
      unsigned long currentTime = millis();
      if ((!tempReceived)||((currentTime - lastTempPolled > POLL_FREQUENCY_TEMP)))
      {
        lastTempPolled = currentTime;
        //Request the temperature sensor
        send(pollRequestMsg.set(ID_TEMP_HUM_SENSOR_OUTSIDE));
        wait(500);
      }
        if ((!tempReceived2)||((currentTime - lastTempPolled2 > POLL_FREQUENCY_TEMP2)))
      {
        lastTempPolled2 = currentTime;
        //Request the temperature sensor
        send(pollRequestMsg.set(ID_TEMP_HUM_SENSOR_OUTSIDE2));
        wait(500);
      }
    wait(5000);
    }
    
    void PrintTempHumWater()
    {
      lcd.setCursor ( 0, 0 );
      String lText,rText;
      // lText="Inne:";
      lText=lastTemp;
      lText+=char(1);
      lText+="/";
      lText+=lastHum;
      lText+="%";
      
      // rText=lastWater;
      // rText+=" L";
      String outString=SpaceStrings(lText,rText);
      lcd.print(outString);
    }
    
    void PrintTempHumWater2()
    {
      lcd.setCursor ( 0, 1 );
      String lText,rText;
      lText="Ute:";
      lText=lastTemp2;
      lText+=char(1);
      lText+="/";
      lText+=lastHum2;
      lText+="%";
      
      // rText=lastWater;
      // rText+=" L";
      String outString=SpaceStrings(lText,rText);
      lcd.print(outString);
    }
    
    String getValue(String data, char separator, int index)
    {
      int found = 0;
      int strIndex[] = {0, -1  };
      int maxIndex = data.length()-1;
      for(int i=0; i<=maxIndex && found<=index; i++){
        if(data.charAt(i)==separator || i==maxIndex){
          found++;
          strIndex[0] = strIndex[1]+1;
          strIndex[1] = (i == maxIndex) ? i+1 : i;
        }
      }
      return found>index ? data.substring(strIndex[0], strIndex[1]) : "";
    }
    
    void receive(const MyMessage &message) {
      if (message.type==V_CUSTOM) {
        String cMessage =  message.getString();
        int idx = getValue(cMessage, '#', 0).toInt();
        if (idx == ID_TEMP_HUM_SENSOR_OUTSIDE) {
          //0,temp,hum,humstatus
          tempReceived=true;
          lastTemp=getValue(cMessage, '#', 2);
          lastHum=getValue(cMessage, '#', 3);
          PrintTempHumWater();
        }
        else if (idx == ID_TEMP_HUM_SENSOR_OUTSIDE2) {
          //0,temp,hum,humstatus
          tempReceived2=true;
          lastTemp2=getValue(cMessage, '#', 2);
          lastHum2=getValue(cMessage, '#', 3);
          PrintTempHumWater2();
        }
        else {
          Serial.print("Received unknown custom message from gw:");
          Serial.println(cMessage);
        }
      }
    }```

  • Contest Winner

    I would strip the complete sketch and leave only the button part in it. That way it's much easier to detect if there's any mistake. It's really hard to help you with a sketch if this size.

    You could try to give the debouncer a higher interval, e.g.:
    debouncer2.interval(25);


  • Mod

    If you happen to press and let go of the button while one of the wait is running, the press will not be detected. Maybe that's what is happening? Try commenting out the wait statements (at least the one at the end of the loop) and see if the node becomes more responsive.



  • @TheoL said:

    I would strip the complete sketch and leave only the button part in it. That way it's much easier to detect if there's any mistake. It's really hard to help you with a sketch if this size.

    You could try to give the debouncer a higher interval, e.g.:
    debouncer2.interval(25);

    Thanks for the troubleshooting tip!

    @mfalkvidd After commenting out almost all of the LCD/temp functions i was left with the last wait that caused the problems, it seems to be working now but havent got the time to run it more than a few minutes.


 

446
Online

7.9k
Users

8.8k
Topics

94.3k
Posts