Pages: [1]   Go Down
Author Topic: Help with PWM @ 66.8 Hz?  (Read 1223 times)
0 Members and 1 Guest are viewing this topic.
0
Offline Offline
Newbie
*
Karma: 0
Posts: 5
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

how to produce a square wave with PWM for the Arduino Mega Development Board? i need the output wave to be at 5 volts and at a frequency of 66.8 Hz and the duty cycle of 10%.

Any help will be appreciate it

Thanks,
Logged

New Zealand
Offline Offline
Jr. Member
**
Karma: 1
Posts: 69
arduino: far too much like electrical engineering.
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

With an opamp.
This is how to make a square wave oscillator from an opamp with variable duty cycle (shown with 50%):
http://www.facstaff.bucknell.edu/mastascu/eLessonsHTML/UsefulCircuits/SqWaveGenerator.htm
Some general opamp information: http://www.opencircuits.com/Op_amp
also try this book, it's mostly single sided opamps, which is probably what you'd be using, and has a good collection of circuits:
http://focus.ti.com/lit/an/slod006b/slod006b.pdf

Alec
Logged


-- Alec

Manchester (England England)
Offline Offline
Brattain Member
*****
Karma: 597
Posts: 33301
Solder is electric glue
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

You have no need of any external hardware to do this.

First of all you have to set the PWM frequency to the one you want. See this thread for a discussion:-
http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1252073278/7#7

Then for a 10% duty cycle just do an :- analogWrite(pin,25);
With pin being the PWM pin number of your choice.
Logged

0
Offline Offline
Newbie
*
Karma: 0
Posts: 5
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I really dont understand how manipulate the code of prescaling of the frequency to create the PWM? Also, how can you create identical PWM outputs at 66.8 Hz?

« Last Edit: November 02, 2009, 11:44:32 am by krileyll » Logged

Manchester (England England)
Offline Offline
Brattain Member
*****
Karma: 597
Posts: 33301
Solder is electric glue
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
I really dont understand how manipulate the code of prescaling of the frequency to create the PWM?
You just poke the number in that gives you the delay you want. You work out the delay you want from the clock frequency (16MHz)

Quote
Also, how can you create identical PWM outputs at 66.8 Hz?

Once you set the PWM output frequenncy they all run at the same speed.
Logged

France
Offline Offline
Sr. Member
****
Karma: 0
Posts: 266
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Here is an example that runs on mega board using 16bit-timer number 5
Code:
int outputPsuB = 45;  // Timer5-B

void setup()
{
// PSU outputs via timer5
  pinMode(outputPsuB, OUTPUT);  // select Pin as ch-B
  
  TCCR5A = B00100010; // Phase correct PWM change at OCR5A
  TCCR5B = B10010;  // prescaling by 8 the system clock
  OCR5A = 14970; // 66,8002672Hz
  OCR5B = 1497; // 10% PWM
  }  

Suppose you prescale by 1024 instead of 8, you still can have roughly 66,8Hz but with less precision
Code:
int outputPsuB = 45;  // Timer5-B

void setup()
{
// PSU outputs via timer5
  pinMode(outputPsuB, OUTPUT);  // select Pin as ch-B
  
  TCCR5A = B00100010; // Phase correct PWM change at OCR5A
  TCCR5B = B10101;  // prescaling by 1024 the system clock
  OCR5A = 117; // 66,7735Hz
  OCR5B = 12; // 10,26% PWM
  }  
and so on.

Please take time to check atmega1280 data sheet section on timers because there are different ways to generate PWM frequency with different stability: fast PWM, phase correct PWM, phase & frequency correct PWM.

With one 16-bit timer, once you set its frequency by blocking OCRnA, you still have two indepedent PWM outputs via OCRnB and OCRnC.

Of course, you can generate more 66,8Hz PWM outputs by using timer1, timer3 & timer4.

Worthwhile noting you can delay or phase shift same 66,8Hz and 10%PWM by controlling TCNTn counters of respective timers.

If you need more outputs, then use timer0 and timer2 which is 8bit hence less resolution and different register access but it works. Care shoudl be taken with timer0 because it handles millis() and micros() subroutines.

P.S.1. If you need many PWM outputs with same frequency, PWM and phase, best to use only one timer output pin and build electronic hardware multiple drivers so you can save atmega1280 timers for other use because they are very precious.

P.S.2. Please look excellent document for pin allocation & timer mapping:
http://spreadsheets.google.com/pub?key=rtHw_R6eVL140KS9_G8GPkA&gid=0
« Last Edit: November 02, 2009, 11:35:10 pm by selfonlypath » Logged

0
Offline Offline
Newbie
*
Karma: 0
Posts: 5
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

@selfonlypath Thanks your all your help so far with helping creating code for PWM. I was wondering is there a particular reason why you didnt use any of the PWM timers on pins 2-13?
or if its even possible to?  

 what the code would be for a 2nd PWM at the same frequency and duty cycle as the first one? I need it for controlling a servo motor one PWM for forward and reverse and the other PWM for left and right.

Logged

0
Offline Offline
Newbie
*
Karma: 0
Posts: 29
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

bump
Logged

France
Offline Offline
Sr. Member
****
Karma: 0
Posts: 266
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

hey krileyll
Quote
I was wondering is there a particular reason why you didnt use any of the PWM timers on pins 2-13? or if its even possible to?

I gave you an example working with timer5 which only can handle pins 44-45-46.

Of course, I'm using in my lab pins between 2-13 related to timer1, timer3 and timer4 to set any PWM frequency and duty cycle as well as timer0 and timer1 except these last two timers are only 8bit precision.

Quote
what the code would be for a 2nd PWM at the same frequency and duty cycle as the first one? I need it for controlling a servo motor one PWM for forward and reverse and the other PWM for left and right.

really easy, for example with same frequency but 20% and 30% using same timer:
Code:
int outputPsuB5 = 45;  // Timer5-B
int outputPsuC5 = 44;  // Timer5-C

void setup()
{
// PSU outputs via timer5
  pinMode(outputPsuB5, OUTPUT);  // select Pin as ch-B
  pinMode(outputPsuC5, OUTPUT);  // select Pin as ch-C
  
  TCCR5A = B00100010; // Phase correct PWM change at OCR5A
  TCCR5B = B10010;  // prescaling by 8 the system clock
  OCR5A = 14970; // 66,8002672Hz
  OCR5B = 1497; // 10% PWM on channel B5
  OCR5C = 2994; // 20% PWM on channel C5
}

or another way with same frequency but 20% and 30% using two independent timers:
Code:
int outputPsuB5 = 45;  // Timer5-B
int outputPsuB4 = 7;  // Timer4-B

void setup()
{
// PSU outputs via timer5 and timer 4
  pinMode(outputPsuB5, OUTPUT);  // select Pin as ch-B5
  pinMode(outputPsuB4, OUTPUT);  // select Pin as ch-B4
  
  TCCR5A = B00100010; // Phase correct PWM change at OCR5A
  TCCR5B = B10010;  // prescaling by 8 the system clock
  OCR5A = 14970; // 66,8002672Hz
  OCR5B = 4991; // 30% PWM on channel B5

  TCCR4A = B00100010; // Phase correct PWM change at OCR4A
  TCCR4B = B10010;  // prescaling by 8 the system clock
  OCR4A = 14970; // 66,8002672Hz
  OCR4B = 1497; // 10% PWM on channel B4

}

« Last Edit: November 08, 2009, 11:18:50 pm by selfonlypath » Logged

France
Offline Offline
Sr. Member
****
Karma: 0
Posts: 266
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Oups, slight error, TCCR4A or TCCR5A should be for correct phase PWM:
Code:
TCCR4A = B00100011; // Phase correct PWM change at OCR4A
TCCR5A = B00100011; // Phase correct PWM change at OCR5A
otherwise previous code:
Code:
TCCR4A = B00100010; // Phase correct PWM change at OCR4A
TCCR5A = B00100010; // Phase correct PWM change at OCR5A
was based on PWM interrupt capture trigger source ICR.

From http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1257929313/0#3

Sorry about that...
« Last Edit: November 11, 2009, 10:44:59 pm by selfonlypath » Logged

Pages: [1]   Go Up
Jump to: