Member #128791

Member Since: April 8, 2010

Country: United States

  • Whenever I have ran into a speed issue using PWM, it has been the PWM frequency that was set incorrectly. The reason your motor turns slowly while at 100% duty cycle is because the pulse, or Frequency is too looooooooooong of a period for 1 pulse. It needs a higher frequency resulting in a faster pulse (Shorter width at 100% duty) which will give you your speed.

    Here is some code to change the frequency of Timer1 (Pins 9 + 10) on an ATmega32U4 based microcontroller (Leonardo, Pro Micro...) Code was adapted from the best tutorial on PWM I found here: http://r6500.blogspot.com/2014/12/fast-pwm-on-arduino-leonardo.html Code is for a pitching machine I repaired. Had a 10K pot for speed input.

    #define SPEED_PWM_OUT A10 //Pin 10
    #define SPEED_INPUT A7 //Pin 6
    #define SPEED_SNIFFER A6 //Pin 4
    
    // Frequency modes for TIMER1
    #define PWM62k   1   //62500 Hz
    #define PWM8k    2   // 7812 Hz
    #define PWM1k    3   //  976 Hz
    #define PWM244   4   //  244 Hz
    #define PWM61    5   //   61 Hz
    
    // Direct PWM change variables
    #define PWM9   OCR1A
    #define PWM10  OCR1B
    #define PWM11  OCR1C
    
    // Configure the PWM clock
    // The argument is one of the 5 previously defined modes
    void pwmConfig(int mode)
    {
      // TCCR1A configuration
      //  00 : Channel A disabled D9
      //  00 : Channel B disabled D10
      //  00 : Channel C disabled D11
      //  01 : Fast PWM 8 bit
      TCCR1A = 1;
    
      // TCCR1B configuration
      // Clock mode and Fast PWM 8 bit
      TCCR1B = mode | 0x08;
    
      // TCCR1C configuration
      TCCR1C = 0;
    }
    
    
    // Set PWM to D9
    // Argument is PWM between 0 and 255
    void pwmSet9(int value)
    {
      OCR1A = value; // Set PWM value
      DDRB |= 1 << 5; // Set Output Mode B5
      TCCR1A |= 0x80; // Activate channel
    }
    
    
    // Set PWM to D10
    // Argument is PWM between 0 and 255
    void pwmSet10(int value)
    {
      OCR1B = value; // Set PWM value
      DDRB |= 1 << 6; // Set Output Mode B6
      TCCR1A |= 0x20; // Set PWM value
    }
    
    //VARS-----------------------
    unsigned int speedInput = 0;
    unsigned int speedSniffer = 0;
    unsigned int speedPwmOut = 0;
    
    int prevSpeed = 0;
    bool update_PWM = false;
    
    void setup() {
    
      Serial.begin(9600);
      Serial.setTimeout(100);
    
      pinMode(SPEED_PWM_OUT, OUTPUT);
      pinMode(SPEED_INPUT, INPUT);
      pinMode(SPEED_SNIFFER, INPUT);
    
      analogRead(SPEED_INPUT);
    
      pwmConfig(PWM1k);
      pwmSet10(0);
    
    }
    
    void loop() {
    
      speedSniffer = analogRead(SPEED_SNIFFER);
      speedInput = analogRead(SPEED_INPUT);
    
    
      if (speedInput < 20)
      {
        speedPwmOut = 0;
        prevSpeed = 0;
        if (update_PWM = true) {
          pwmSet10(0);
        }
      } else {
        speedPwmOut = map(speedInput, 0, 1023, 60, 255);
        if (speedPwmOut != prevSpeed)
        {
          pwmSet10(speedPwmOut);
          prevSpeed = speedPwmOut;
          update_PWM = true;
        }
    
      }
    
    
    
      Serial.println("----------------------");
      Serial.print("Start POT Sniffer (A6): ");
      Serial.println(speedSniffer);
      Serial.print("Speed POT Input (A7): ");
      Serial.println(speedInput);
      Serial.print("Speed PWM Out (A10): ");
      Serial.println(speedPwmOut);
      Serial.println("----------------------");
      delay(250);
    
    }
    

No public wish lists :(