NerdKits - electronics education for a digital generation

You are not logged in. [log in]

NEW: Learning electronics? Ask your questions on the new Electronics Questions & Answers site hosted by CircuitLab.

Project Help and Ideas » LED blink with variable flash

March 30, 2011
by Ace
Ace's Avatar

I'm trying to alter the led blink code so I can use a pot to adjust the flash rate. Here's my modification:

// led_blink.c
// for NerdKits with ATmega168
// hevans@nerdkits.edu

#define F_CPU 14745600

#include <avr/io.h>
#include <inttypes.h>

#include "../libnerdkits/delay.h"
#include "../libnerdkits/lcd.h"

// PIN DEFINITIONS:
//
// PC4 -- LED anode

void adc_init() {
  ADMUX = 0;
  ADCSRA = (1<<ADEN) | (1<<ADPS2) | (1<<ADPS1) | (1<<ADPS0);
  ADCSRA |= (1<<ADSC);
}

uint8_t adc_read() {
  while(ADCSRA & (1<<ADSC)) {
  }
  uint16_t result = ADCL;
  ADCSRA |= (1<<ADSC);
  return result;
}

int main() {

  adc_init(0);  
  // LED as output
  DDRC |= (1<<PC4);

  // loop keeps looking forever
  while(1) {    
    PORTC |= (1<<PC4);      // turn on LED         
    delay_ms(500);          // ON for 50 milliseconds          
    PORTC &= ~(1<<PC4);     // turn off LED         
    delay_ms(500);  // OFF from pot setting (lower pot faster flash)             
}

  return 0;
}

I have the center of the pot connected to PC0, left lug to GND, and right lug to AREF. When I turn the pot, nothing happens. Any suggestions? Thank you.

March 31, 2011
by 6ofhalfdozen
6ofhalfdozen's Avatar

Hiya Ace, I am not an expert in C, but I see a few problems.

The most important one that I see is that you don't ever actually call ADC_Read in your main loop, so the ADC is never actually read. You do initialize the ADC on line 33, but never call to read it.

On line 42, your comments claim that you set the LED Off time dependant on the pot. In actuality, since you have the value set to (500) it will always be 500ms off. You need to somehow put the ADC result into that value..

If this were my code, I would use the following as my "main" code. Again, the warning, I am not a C programmer. This "should" work but might need some minor C related code tweeking, so fyi. hopefully this helps get you on the right track to where you need to go.

int main() {     
adc_init(0);     
// LED as output   
DDRC |= (1<<PC4);   
//using a volatile "potvalue" as 16bit integer holder of ADC result
volatile uint16  potvalue;
// loop keeps looking forever   
while(1) {
potvalue = ADC_Read();
PORTC |= (1<<PC4);  // turn on LED              
delay_ms(500);     // ON for 50 milliseconds               
PORTC &= ~(1<<PC4);   // turn off LED              
delay_ms(500/potvalue);   // OFF from pot setting (lower pot faster flash)             
}     return 0; }

Post a Reply

Please log in to post a reply.

Did you know that NerdKits make a great gift? Learn more...