Skip to content
  • MySensors
  • OpenHardware.io
  • Categories
  • Recent
  • Tags
  • Popular
Skins
  • Light
  • Brite
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Brand Logo
  1. Home
  2. Troubleshooting
  3. Question about wait() and program logic

Question about wait() and program logic

Scheduled Pinned Locked Moved Troubleshooting
9 Posts 3 Posters 1.6k Views 3 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • X Offline
    X Offline
    xefil
    wrote on last edited by
    #1

    Hello,

    I'm planning to rewrite a sketch which actually is handling a RGB led strip. For now I've written the sketch to fade out from Red 100% to off in some minutes. The fade out is managed by the Controller (OpenHAB). It sends the command to the node every 'x' seconds with a new lower dimmer value until it comes to zero, in this way:

    Controller -> Red color 100% -> Node
    after minutes
    Controller -> Red color 90% -> Node
    after minutes
    Controller -> Red color 80% -> Node
    (...)
    Controller -> Red color 0% -> Node

    The procedure stops.

    It works most of the time.

    Sometimes happens the Node doesn't answer well. So It happens the led remains on even if the Controller has sent the command to turn the light off. I'll debug it better from hardware side, but I was thinking a different approach as well.
    I would like to move the logic on the Node in this way:

    Controller -> send V_LIGHT status set to 1 -> Node
    In the void receive() I check if the message.sensor is set to the Sensor-ID associated to my trigger and in case it starts a function that turns the RedLight off... something like this:

    void receive(const MyMessage &message) {
      if (message.sensor == 10) {
        RedOff();
      }
    }
    
    RedOff() {
      // turn Red ON 100%
      analogWrite(RED_PIN, 255);
      // Fade Red Off
      for (r = 255; r > 0; r--) { 
        analogWrite(RED_PIN, r);
        wait(1000);
      } 
    }
    

    This procedure would fade out in 1000 * 255 = 255000 ms = 255 seconds = 4 minutes more or less.

    My question is:

    Would this the best approach to reach the goal?

    Then, in case I would STOP the fade even if the RedOff() procedure is not finished, in example turning on a different light attached to the same Node, how to do that?
    AFAYK the wait() function calls process() to handle incoming messages during the delay, but I'm missing the logic on how, if a different message is coming to the node, should STOP the RedOff() procedure.

    Any help would be really apreciated!

    Thanks!

    Simon

    TheoLT 1 Reply Last reply
    0
    • X xefil

      Hello,

      I'm planning to rewrite a sketch which actually is handling a RGB led strip. For now I've written the sketch to fade out from Red 100% to off in some minutes. The fade out is managed by the Controller (OpenHAB). It sends the command to the node every 'x' seconds with a new lower dimmer value until it comes to zero, in this way:

      Controller -> Red color 100% -> Node
      after minutes
      Controller -> Red color 90% -> Node
      after minutes
      Controller -> Red color 80% -> Node
      (...)
      Controller -> Red color 0% -> Node

      The procedure stops.

      It works most of the time.

      Sometimes happens the Node doesn't answer well. So It happens the led remains on even if the Controller has sent the command to turn the light off. I'll debug it better from hardware side, but I was thinking a different approach as well.
      I would like to move the logic on the Node in this way:

      Controller -> send V_LIGHT status set to 1 -> Node
      In the void receive() I check if the message.sensor is set to the Sensor-ID associated to my trigger and in case it starts a function that turns the RedLight off... something like this:

      void receive(const MyMessage &message) {
        if (message.sensor == 10) {
          RedOff();
        }
      }
      
      RedOff() {
        // turn Red ON 100%
        analogWrite(RED_PIN, 255);
        // Fade Red Off
        for (r = 255; r > 0; r--) { 
          analogWrite(RED_PIN, r);
          wait(1000);
        } 
      }
      

      This procedure would fade out in 1000 * 255 = 255000 ms = 255 seconds = 4 minutes more or less.

      My question is:

      Would this the best approach to reach the goal?

      Then, in case I would STOP the fade even if the RedOff() procedure is not finished, in example turning on a different light attached to the same Node, how to do that?
      AFAYK the wait() function calls process() to handle incoming messages during the delay, but I'm missing the logic on how, if a different message is coming to the node, should STOP the RedOff() procedure.

      Any help would be really apreciated!

      Thanks!

      Simon

      TheoLT Offline
      TheoLT Offline
      TheoL
      Contest Winner
      wrote on last edited by
      #2

      @xefil Dear Simon,

      Whether or not this will solve you problem. Your implementation is not a good strategy (in my opinion).

      You block everything in the main loop when you enter the redOff() function. So what happens if during the turnOff method you node receives a turn on?

      X 1 Reply Last reply
      0
      • TheoLT TheoL

        @xefil Dear Simon,

        Whether or not this will solve you problem. Your implementation is not a good strategy (in my opinion).

        You block everything in the main loop when you enter the redOff() function. So what happens if during the turnOff method you node receives a turn on?

        X Offline
        X Offline
        xefil
        wrote on last edited by
        #3

        @TheoL that's exactly what I would like to handle and don't know how.
        The wait() command should not stop to accept messages. Is there a way into the RedOff() function to stop the execution in case I get a message I need to handle? Like a turnOn as you said. Maybe @tekka or @hek have better ideas from their experience ;)
        Thanks!
        Simon

        1 Reply Last reply
        0
        • hekH Offline
          hekH Offline
          hek
          Admin
          wrote on last edited by
          #4

          Maybe you can get some inspiration from my DimmableLight example where I do a none-blocking fade.

          https://github.com/mysensors/MySensorsArduinoExamples/blob/master/examples/DimmableLightWithRotaryEncoderButton/DimmableLightWithRotaryEncoderButton.ino

          X 1 Reply Last reply
          0
          • hekH hek

            Maybe you can get some inspiration from my DimmableLight example where I do a none-blocking fade.

            https://github.com/mysensors/MySensorsArduinoExamples/blob/master/examples/DimmableLightWithRotaryEncoderButton/DimmableLightWithRotaryEncoderButton.ino

            X Offline
            X Offline
            xefil
            wrote on last edited by
            #5

            @hek , great - simply approach!
            If I'm not wrong, your fade function does NOT fade out until the end in one shot, but it simply it's called 'x' times between checks for button or rotary. Right??

            Another question: When is exactly the void receive() function called? At the end of every loop()? I'm missing a little bit this part.... ;) but seems I'm understanding a way to solve what I would like to do!
            Thanks!!
            Simon

            1 Reply Last reply
            0
            • hekH Offline
              hekH Offline
              hek
              Admin
              wrote on last edited by
              #6

              receive() gets called here:

              https://github.com/mysensors/MySensors/blob/c85de960d40d140205fa5a752a07fabe8c09a2ea/core/MyTransport.cpp#L573

              Normally transportProcessMessage() gets called once every loop (unless you use wait()).

              X 1 Reply Last reply
              1
              • hekH hek

                receive() gets called here:

                https://github.com/mysensors/MySensors/blob/c85de960d40d140205fa5a752a07fabe8c09a2ea/core/MyTransport.cpp#L573

                Normally transportProcessMessage() gets called once every loop (unless you use wait()).

                X Offline
                X Offline
                xefil
                wrote on last edited by
                #7

                @hek , thanks for the clarifications.
                What do you mean:
                Normally transportProcessMessage() gets called once every loop (unless you use wait()).

                Does wait() call transportProcessMessage() as well on every use? That would make sense.

                I.e.:

                void loop(){
                  // transportProcessMessage() is called in background somewhere here and so receive(_msg) as well.
                
                  // some code..
                  
                  wait(100); // this calls transportProcessMessage() again and so receive(_msg) as well.
                
                  // other code...
                  
                }
                

                Is that above correct?

                If yes, then my initial aproach would work as well. a procedure where wait() is called like this:

                RedOff() {
                  // turn Red ON 100%
                  analogWrite(RED_PIN, 255);
                  // Fade Red Off
                  for (r = 255; r > 0; r--) { 
                    analogWrite(RED_PIN, r);
                    wait(1000);   // <<<<--------- here it checks for new messages and I could interrupt this procedure.
                  } 
                }
                

                BTW I prefer your approach taken from 'DimmableLightWithRotaryEncoderButton.ino'. Seems more clean.

                I ask you that, only to understand correctly how the logic works.

                Thanks a lot,

                Simon

                1 Reply Last reply
                0
                • hekH Offline
                  hekH Offline
                  hek
                  Admin
                  wrote on last edited by
                  #8

                  @xefil said:

                  Does wait() call transportProcessMessage() as well on every use? That would make sense.

                  Yes it will call it multiple times depending on how long you wait for, which could call your receive() -> RedOff(), which would call wait(), and so on.. resulting in a unpredictable call-stack size. The arduino would probably crash if you receive many incoming color changes.

                  X 1 Reply Last reply
                  0
                  • hekH hek

                    @xefil said:

                    Does wait() call transportProcessMessage() as well on every use? That would make sense.

                    Yes it will call it multiple times depending on how long you wait for, which could call your receive() -> RedOff(), which would call wait(), and so on.. resulting in a unpredictable call-stack size. The arduino would probably crash if you receive many incoming color changes.

                    X Offline
                    X Offline
                    xefil
                    wrote on last edited by
                    #9

                    @hek ok, thank you!
                    I'll adopt your example as starting point.
                    Many thanks!

                    Simon

                    1 Reply Last reply
                    0
                    Reply
                    • Reply as topic
                    Log in to reply
                    • Oldest to Newest
                    • Newest to Oldest
                    • Most Votes


                    20

                    Online

                    11.7k

                    Users

                    11.2k

                    Topics

                    113.1k

                    Posts


                    Copyright 2025 TBD   |   Forum Guidelines   |   Privacy Policy   |   Terms of Service
                    • Login

                    • Don't have an account? Register

                    • Login or register to search.
                    • First post
                      Last post
                    0
                    • MySensors
                    • OpenHardware.io
                    • Categories
                    • Recent
                    • Tags
                    • Popular