#1
  1. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Mar 2017
    Posts
    4
    Rep Power
    0

    Question IF FOR loop problem


    When I'm using this Dimmer Code then its working fine even for a long time and nothing is getting burnt nor heated up.
    Code:
    /*
    
    AC Voltage dimmer with Zero cross detection
    Author: Charith Fernanado <a href="http://www.inmojo.com">  http://www.inmojo.com
    
    </a>
    Adapted by DIY_bloke
    License: Creative Commons Attribution Share-Alike 3.0 License.
    Attach the Zero cross pin of the module to Arduino External Interrupt pin
    Select the correct Interrupt # from the below table 
    (the Pin numbers are digital pins, NOT physical pins: 
    digital pin 2 [INT0]=physical pin 4 and digital pin 3 [INT1]= physical pin 5)
    check: <a href="http://arduino.cc/en/Reference/attachInterrupt">  http://www.inmojo.com
    
    </a>
    
    Pin    |  Interrrupt # | Arduino Platform
    ---------------------------------------
    2      |  0            |  All -But it is INT1 on the Leonardo
    3      |  1            |  All -But it is INT0 on the Leonardo
    18     |  5            |  Arduino Mega Only
    19     |  4            |  Arduino Mega Only
    20     |  3            |  Arduino Mega Only
    21     |  2            |  Arduino Mega Only
    0      |  0            |  Leonardo
    1      |  3            |  Leonardo
    7      |  4            |  Leonardo
    The Arduino Due has no standard interrupt pins as an iterrupt can be attached to almosty any pin. 
    
    In the program pin 2 is chosen
    */
    int AC_LOAD = 3;    // Output to Opto Triac pin
    int dimming = 128;  // Dimming level (0-128)  0 = ON, 128 = OFF
    
    void setup()
    {
      pinMode(AC_LOAD, OUTPUT);// Set AC Load pin as output
     // digitalPinToInterrupt(2);
      attachInterrupt(digitalPinToInterrupt(2), zero_crosss_int, RISING);  // Choose the zero cross interrupt # from the table above
    }
    
    //the interrupt function must take no parameters and return nothing
    void zero_crosss_int()  //function to be fired at the zero crossing to dim the light
    {
      // Firing angle calculation : 1 full 50Hz wave =1/50=20ms 
      // Every zerocrossing thus: (50Hz)-> 10ms (1/2 Cycle) 
      // For 60Hz => 8.33ms (10.000/120)
      // 10ms=10000us
      // (10000us - 10us) / 128 = 75 (Approx) For 60Hz =>65
    
      int dimtime = (75*dimming);    // For 60Hz =>65    
      delayMicroseconds(dimtime);    // Wait till firing the TRIAC    
      digitalWrite(AC_LOAD, HIGH);   // Fire the TRIAC
      delayMicroseconds(10);         // triac On propogation delay 
             // (for 60Hz use 8.33) Some Triacs need a longer period
      digitalWrite(AC_LOAD, LOW);    // No longer trigger the TRIAC (the next zero crossing will swith it off) TRIAC
    }
    
    void loop()  {
      for (int i=5; i <= 128; i++){
        dimming=i;
        delay(100);
       }
    }
    But when I want to run this code when I receive something from I2C then my resistor is getting burnt and the hunch what I have is that keeping the for() loop inside the if() loop is causing me this problem .

    Code:
    if (x == 243)
      {
        digitalWrite(led1, HIGH);
          for (int a = 5; a <= 128; a++)
      {
        dimming = a;
        delay(100);
      }
      }
      else
        digitalWrite(led1, LOW);
  2. #2
  3. Contributing User
    Devshed God 1st Plane (5500 - 5999 posts)

    Join Date
    Aug 2011
    Posts
    5,787
    Rep Power
    508
    Is dimming supposed to have global scope?
    Shouldn't dimming be declared volatile?
    [code]Code tags[/code] are essential for python code and Makefiles!
  4. #3
  5. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Mar 2017
    Posts
    4
    Rep Power
    0
    ThankYou.
    This is the code I've written where if I get some data say 243 from I2C then it should dim the bulb for 5% and similarly if I get 255 then the should be from 40% etc..
    Code:
    #include <Wire.h>
    int led1 = 4;
    int led2 = 5;
    //int led3=5;
    int DIM_AC_LOAD = 11;
    int SC_AC_LOAD = 9;
    int dimming = 128;
    //int temp=A0;
    
    void dim_zero_crosss_int()
    {
      int dimtime = (75 * dimming);
      delayMicroseconds(dimtime);
      digitalWrite(DIM_AC_LOAD, HIGH);
      delayMicroseconds(10);
      digitalWrite(DIM_AC_LOAD, LOW);
    }
    
    void sc_zero_crosss_int()
    {
      int dimtime = (75 * dimming);
      delayMicroseconds(dimtime);
      digitalWrite(SC_AC_LOAD, HIGH);
      delayMicroseconds(10);
      digitalWrite(SC_AC_LOAD, LOW);
    }
    
    void setup()
    {
      Wire.begin(8);                // join i2c bus with address #8
      Wire.onReceive(receiveEvent); // register event
      Serial.begin(9600);           // start serial for output
      pinMode(led1, OUTPUT);
      pinMode(led2, OUTPUT);
      //  pinMode(led3, OUTPUT);
      pinMode(DIM_AC_LOAD, OUTPUT);
      pinMode(SC_AC_LOAD, OUTPUT);
      attachInterrupt(digitalPinToInterrupt(2), dim_zero_crosss_int, RISING);
      attachInterrupt(digitalPinToInterrupt(3), sc_zero_crosss_int, RISING);
    }
    
    void loop()
    {
      delay(100);
    }
    void receiveEvent(int howMany)
    {Serial.print(howMany); 
    
      int x = Wire.read();    // receive byte as an integer
      Serial.println(x);         // print the integer
    
      if (x == 243)
      {
        digitalWrite(led1, HIGH);
          for (int a = 5; a <= 128; a++)
      {
        dimming = a;
        delay(100);
      }
      }
      else
        digitalWrite(led1, LOW);
    
      if (x == 255)
     {   digitalWrite(led2, HIGH);
       for (int a = 5; a <= 128; a++)
      {
        dimming = a;
        delay(100);
      }
    }
    else
        digitalWrite(led2, LOW);
    
    }
    but whenever the code is coming to the if() loop then my resistor is getting burnt.

    Any help & hints appreciated
    Thanks in advance
  6. #4
  7. Contributed User
    Devshed Specialist (4000 - 4499 posts)

    Join Date
    Jun 2005
    Posts
    4,460
    Rep Power
    1874
    The problem is, you're calling delay(100) https://www.arduino.cc/en/Reference/Delay, each one of which takes 100mS, for a combined total delay of over 12 seconds!

    Why is this a problem? Because it seems that receiveEvent() is an interrupt service routine(ISR) just like dim_zero_crosss_int() is. The result being that it seems like receiveEvent is blocking any zero crossing detection for an extended period of time (long enough to lock everything up and burn your circuitry.

    An ISR should do the minimum amount of work necessary, before passing the data onto something else to complete the work. Something like this perhaps.
    Code:
    int wireValue;
    void loop()
    {
      delay(100);
      if ( wireValue != 0 ) {
        if (x == 243)
        {
          digitalWrite(led1, HIGH);
          for (int a = 5; a <= 128; a++)
          {
            dimming = a;
            delay(100);
          }
        }
        else
          digitalWrite(led1, LOW);
    
        if (x == 255)
        {   
          digitalWrite(led2, HIGH);
          for (int a = 5; a <= 128; a++)
          {
            dimming = a;
            delay(100);
          }
        }
        else
          digitalWrite(led2, LOW);
      }
    }
    void receiveEvent(int howMany)
    {
      Serial.print(howMany); 
      int x = Wire.read();    // receive byte as an integer
      Serial.println(x);         // print the integer
      wireValue = x;
    }

    Comments on this post

    • ishtiaqshaheer agrees
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper
  8. #5
  9. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Mar 2017
    Posts
    4
    Rep Power
    0
    ThankYou, I'll try it once... :)
  10. #6
  11. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Mar 2017
    Posts
    4
    Rep Power
    0
    I've tried the code which you sent and the error I'm getting through this is I'm receiving the data too late and my LEDs are being off after receiving the data after a long time.
    Like, (this is serial monitor data)
    Code:
    1 //howmany
    255 //received 255 > led2 is ON
    1
    243 //received 243 > led1 is ON but led2 is still ON without being OFF
    1
    255 //received 255 > but led1 is ON & led2 is still ON
    1
    243 //received 243 > led1 is ON but led2 gets OFF
    1
    255
    in this way the data is being late and my output too.
  12. #7
  13. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Apr 2017
    Posts
    3
    Rep Power
    0
    Use if to specify a block of code to be executed, if a specified condition is true
    Use else to specify a block of code to be executed, if the same condition is false
    Use else if to specify a new condition to test, if the first condition is false
    Use switch to specify many alternative blocks of code to be executed
    Learn C++ here https://hackr.io/tutorials/learn-c-c-plus-plus
    Try this syntax:

    Syntax
    Code:
    if (condition) {
        block of code to be executed if the condition is true
    }

IMN logo majestic logo threadwatch logo seochat tools logo