Hello,
I'm trying to get my ATtiny13 to do the following task: The trimmer of a 10K potentiometer on PB2 is registered as an input. PB0 is used as an output for a 109kHz PWM signal. Depending on the current value of my potentiometer the interval between 1 second long PWM signals. So for example im my potentiometer is at 5K, then theres a 1 second long PWM signal and then there's 20 seconds of no output. Also if the potentiometer is below 1K, then the PWM signal is there all the time. I've already written the code for this, but for some reason it doesn't work right, as it is permanently giving me the 109kHz. Below is the code and a cutout of the mentioned circuit. The ATtiny is supplied with 5V DC.
I'm thankfull for any help regarding hard- or software.
#define F_CPU 9600000UL
#include <avr/io.h>
#include <util/delay.h>
// Timer konfigurieren
void setupTimer() {
OSCCAL += 2; // Feinjustierung des Oszillators
TCCR0A = (1 << WGM01) | (1 << WGM00); // Fast PWM, Modus 3
TCCR0B = (1 << WGM02) | (1 << CS00); // Kein Prescaler, Modus 7
OCR0A = 43; // Feineinstellung für 108 kHz
}
// ADC konfigurieren
void setupADC() {
ADMUX = (1 << MUX1); // PB2 (ADC1) auswählen
ADCSRA = (1 << ADEN) | (1 << ADPS1) | (1 << ADPS0); // ADC aktivieren, Prescaler 8
}
// ADC-Wert auslesen
uint16_t readADC() {
ADCSRA |= (1 << ADSC); // Start der Konvertierung
while (ADCSRA & (1 << ADSC)); // Warten auf Abschluss
return ADC;
}
// Intervall basierend auf ADC-Wert berechnen
uint8_t getInterval(uint16_t adcValue) {
if (adcValue < 102) return 1; // 0-1k Ohm -> 1 Sekunde
else if (adcValue < 204) return 3; // 1-2k Ohm -> 3 Sekunden
else if (adcValue < 307) return 5; // 2-3k Ohm -> 5 Sekunden
else if (adcValue < 409) return 10; // 3-4k Ohm -> 10 Sekunden
else if (adcValue < 512) return 20; // 4-5k Ohm -> 20 Sekunden
else if (adcValue < 614) return 30; // 5-6k Ohm -> 30 Sekunden
else if (adcValue < 716) return 40; // 6-7k Ohm -> 40 Sekunden
else if (adcValue < 819) return 50; // 7-8k Ohm -> 50 Sekunden
else if (adcValue < 921) return 60; // 8-9k Ohm -> 60 Sekunden
return 0; // Immer an (9-10k Ohm)
}
// Variable Verzögerung
void delay_ms_variable(uint16_t delay_ms) {
while (delay_ms--) {
_delay_ms(1); // Kleinste Einheit: 1 ms
}
}
int main() {
DDRB |= (1 << PB0); // PB0 als Ausgang
setupTimer();
setupADC();
while (1) {
uint16_t adcValue = readADC();
uint8_t interval = getInterval(adcValue);
if (interval == 0) {
// Immer an
TCCR0A |= (1 << COM0A0); // PWM aktivieren
} else {
// Intervallmodus
TCCR0A |= (1 << COM0A0); // PWM aktivieren
delay_ms_variable(1000); // 1 Sekunde an
TCCR0A &= ~((1 << COM0A0) | (1 << COM0A1)); // PWM deaktivieren
PORTB &= ~(1 << PB0); // Ausgang auf Low setzen
delay_ms_variable(interval * 1000 - 1000); // Pause
}
}
}

