Hey guys,
I'm very new to microcontroller development and I'm doing my best to follow the data sheet for the Atmega328P-PU on the Arduino Uno R3 shield, but there are some concepts I'm having a hard time grasping. I have the code I'm using for a working RGB LED below (it blinks Red/Green). Some explanations/advice would be greatly appreciated! I'm also not using the Arduino IDE; I'm using a text file/terminal to flash the file onto the microcontroller, if that matters to you.
I've gotten the built-in led and normal led on a breadboard to blink, but when I'm trying to fade in/out an RGB led using Phase Correct PWM (I've read from other forums this is what I should use, I could be incorrect), I feel like doing it wrong (even though it technically works).
-
I understand the TCNTn is used for accessing the different Timer/Counters and the OCRxn's are used with the timers for constant comparison, but I don't really understand what exactly happens when a compare match is met. I've looked a lot online but I see a lot of different answers to people's questions about this stuff, but doesn't really make a ton of sense to me.
-
Is the port the OCRxn (OCR0A --> PD6) is linked to being sent an electrical current based on the OCRxn value and the led's brightness matches that value during each clock cycle (rising edge)?
-
Adjusting the OCRxn value after each cycle means changing the brightness of the led because the match from TCNTn and OCRxn meets at a higher value?
-
Are interrupts inseparable from compare matches or do I need them (for this specific pulsing led example)? Are interrupts only used for inputs (like buttons or motor controls)?
-
-
Phase Correct PWM
- Similar to other modes, but it has an incline and decline for counting and the OCRxn registers are used the same way?
- If so, how is the decline used? How is it different than using, let's say, Fast PWM and increasing/decreasing OCRxn for each cycle to create a fading effect?
- Similar to other modes, but it has an incline and decline for counting and the OCRxn registers are used the same way?
I believe those are the main questions I have. Any explanations or questions you have would be great. Thank you!
#define F_CPU 16000000 // 16Mhz
#include <avr/io.h>
#include <stdio.h>
#include <util/delay.h>
#include <stdbool.h>
int main(void) {
DDRD = DDRD | (1 << DDD6)
| (1 << DDD5);
PORTD = PORTD | (1 << PORTD6)
| (1 << PORTD5);
TCCR0A = (1 << COM0A1) | (0 << COM0A0) | (1 << COM0B1) | (0 << COM0B0) | (0 << WGM01) | (1 << WGM00);
TCCR0B = (0 << WGM02) | (1 << CS02) | (0 << CS01) | (0 << CS00);
TCNT0 = 0x00;
OCR0A = 0x00;
OCR0B = 0x00;
bool inverse = false;
while(1) {
if (OCR0A == 0xFF) {
inverse = true;
} else if (OCR0A == 0x00) {
inverse = false;
}
if ((OCR0A < 0xFF) && (inverse == false)) {
OCR0A += 0x1;
} else if ((OCR0A <= 0xFF) && (inverse == true)) {
OCR0A -= 0x1;
}
if (OCR0B == 0xFF) {
inverse = true;
} else if (OCR0B == 0x00) {
inverse = false;
}
if ((OCR0B < 0xFF) && (inverse == false)) {
OCR0B += 0x1;
} else if ((OCR0B <= 0xFF) && (inverse == true)) {
OCR0B -= 0x1;
}
_delay_ms(2);
}
}