Hi!
Ich versuche derzeit einen Servo mit einem ATmega328P anzusteuern.
Dieser sitzt in einem Arduino UNO. Dieser dient allerdings nur zur
Stromversorgung, etc. Programmiert wird ohne Bootloader direkt aus
AtmelStudio mit dem AVR ISP mkii.
Habe versucht den Code aus folgendem Artikel
Modellbauservo Ansteuerung auf meine CPU anzupassen:
1 | #define F_CPU 16000000UL
|
2 | #include <avr/io.h>
|
3 | #include <avr/interrupt.h>
|
4 | #include <util/delay.h>
|
5 |
|
6 | #define taster1 PB2
|
7 | #define taster2 PB0
|
8 | #define ausgang PB1
|
9 |
|
10 | ISR( TIMER1_COMPA_vect ) // Interruptbehandlungsroutine
|
11 | {
|
12 | OCR1A = 5000-OCR1A; // Das Servosignal wird aus der Differenz von
|
13 | // Periodenlänge (5000*0.004ms=20ms) und letztem
|
14 | // Vergleichswert (OCR1A) gebildet
|
15 | }
|
16 |
|
17 | int main (void)
|
18 | {
|
19 | DDRB &= ~((1<<taster1) | (1<<taster2)); // PB1 und PB2 ist Eingang
|
20 | DDRB |= (1<<ausgang);
|
21 |
|
22 | TCCR1A = (1<<COM1A0); // Togglen bei Compare Match
|
23 | TCCR1B = (1<<WGM12) | (1<<CS11) | (1<<CS10) ; // CTC-Mode; Prescaler 64
|
24 | TIMSK1 = (1<<OCIE1A); // Timer-Compare Interrupt an
|
25 |
|
26 | OCR1A = 4625; // Neutralposition ist 4625 ((5000-4625)*0.004ms)=1,5ms); 2ms == 4500; 1ms == 4750
|
27 |
|
28 | sei(); // Interrupts global an
|
29 |
|
30 | while( 1 )
|
31 | {
|
32 | if ( !(PINB & (1<<taster1)) )
|
33 | { // Impuls-Zeit verlängern
|
34 | cli();
|
35 | OCR1A = OCR1A + 100;
|
36 | sei();
|
37 | _delay_ms(50);
|
38 | }
|
39 |
|
40 | if ( !(PINB & (1<<taster2)) )
|
41 | { // Impuls-Zeit verkürzen
|
42 | cli();
|
43 | OCR1A = OCR1A - 100;
|
44 | sei();
|
45 | _delay_ms(50);
|
46 | }
|
47 | }
|
48 | return 0;
|
49 | }
|
Irgendwas stimmt da aber nicht.
Ich bekomme an PB1 eine PWM mit ungefähr gleichbleibender Frequenz von
ca. 49Hz.
Wenn ich für OCR1A beispielsweise mal 4500 einsetze, was ja 1ms
Impulsdauer entsprechen sollte, bekomme ich aber eine Impulsdauer von
ca. 17,2ms. Bei OCR1A = 4700 bekomme ich 18,4ms. Für OCR1A = 2000 ist
die Impulsdauer 16,7ms.
Wenn ich nun für OCR1A 200 einsetze, verändert sich das Tastverhältnis
über die Zeit.
Irgendjemand eine Idee, was ich falsch mache? Stimmen die Berechnungen
für OCR1A so (Siehe Code)?
Grüße und schonmal danke!