Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
2136 | - | 1 | /*********************************************************************/ |
2 | /* */ |
||
3 | /* NG-Video 5,8GHz */ |
||
4 | /* */ |
||
5 | /* Copyright (C) 2011 - gebad */ |
||
6 | /* */ |
||
7 | /* This code is distributed under the GNU Public License */ |
||
8 | /* which can be found at http://www.gnu.org/licenses/gpl.txt */ |
||
9 | /* */ |
||
10 | /* using */ |
||
11 | /*! \file servo.c \brief Interrupt-driven RC Servo function library. */ |
||
12 | /* */ |
||
13 | /*File Name : 'servo.c' */ |
||
14 | /*Title : Interrupt-driven RC Servo function library */ |
||
15 | /*Author : Pascal Stang - Copyright (C) 2002 */ |
||
16 | /*Created : 7/31/2002 */ |
||
17 | /*Revised : 8/02/2002 */ |
||
18 | /*Version : 1.0 */ |
||
19 | /*Target MCU : Atmel AVR Series */ |
||
20 | /*Editor Tabs : 4 */ |
||
21 | /* */ |
||
22 | /*ingroup driver_sw */ |
||
23 | /*defgroup servo Interrupt-driven RC Servo Function Library (servo.c)*/ |
||
24 | /*code #include "servo.h" \endcode */ |
||
25 | /*par Overview */ |
||
26 | /* */ |
||
27 | /*This code is distributed under the GNU Public License */ |
||
28 | /*which can be found at http://www.gnu.org/licenses/gpl.txt */ |
||
29 | /* */ |
||
30 | /*********************************************************************/ |
||
31 | |||
32 | #ifndef SERVO_H |
||
33 | #define SERVO_H |
||
34 | |||
35 | |||
36 | /* Servo */ |
||
37 | #define SERVO_PAN 0 |
||
38 | #define SERVO_TILT 1 |
||
39 | #define SERVO_NUM_CHANNELS 2 // Anzahl der angeschlossen Servos max. 2!!! |
||
40 | /* Servokalibrierungen derzeit zu SERVO_STEPS = 255 skaliert */ |
||
41 | //prescaler 256 |
||
42 | #define SERVO_I0_RIGHT 45 // default Wert, ca. 0,9ms |
||
43 | #define SERVO_I0_RIGHT_MIN 0 // Servokalibrierung Grenze der linken Position |
||
44 | #define SERVO_I0_RIGHT_MAX 100 // SERVO_MIN + SERVO_RIGHT |
||
45 | |||
46 | #define SERVO_I0_LEFT 45 // default Wert, ca. 2,1ms |
||
47 | #define SERVO_I0_LEFT_MIN 0 // Servokalibrierung Grenze der rechten Position |
||
48 | #define SERVO_I0_LEFT_MAX 100 // SERVO_MAX - SERVO_LEFT |
||
49 | |||
50 | #define SERVO_I0_MIDDLE SERVO_STEPS/2 |
||
51 | #define SERVO_I0_MIDDLE_MIN SERVO_STEPS/2 - 25 |
||
52 | #define SERVO_I0_MIDDLE_MAX SERVO_STEPS/2 + 25 |
||
53 | //prescaler 64 |
||
54 | #define SERVO_I1_RIGHT 180 // default Wert, ca. 0,9ms |
||
55 | #define SERVO_I1_RIGHT_MIN 0 // Servokalibrierung Grenze der linken Position |
||
56 | #define SERVO_I1_RIGHT_MAX 400 // SERVO_MIN + SERVO_RIGHT |
||
57 | |||
58 | #define SERVO_I1_LEFT 180 // default Wert, ca. 2,1ms |
||
59 | #define SERVO_I1_LEFT_MIN 0 // Servokalibrierung Grenze der rechten Position |
||
60 | #define SERVO_I1_LEFT_MAX 400 // SERVO_MAX - SERVO_LEFT |
||
61 | |||
62 | //#define SERVO_I1_MIDDLE ((SERVO_STEPS + 1) * 4 - 1)/2 |
||
63 | #define SERVO_I1_MIDDLE_MIN ((SERVO_STEPS + 1) * 4 - 1)/2 - 100 |
||
64 | #define SERVO_I1_MIDDLE_MAX ((SERVO_STEPS + 1) * 4 - 1)/2 + 100 |
||
65 | |||
66 | #define SERVO_REV 0 // kein Reverse |
||
67 | /* Test Servo */ |
||
68 | #define SERVO_PERIODE 20 // default Angabe in ms |
||
69 | #define SERVO_PERIODE_MIN 10 // 10ms |
||
70 | #define SERVO_PERIODE_MAX 30 // 30ms |
||
71 | #define SINGLE_STEP 0 // Einzelschritt aus |
||
72 | #define SINGLE_STEP_MIN 0 |
||
73 | #define SINGLE_STEP_MAX 20 // bei prescaler 256, sonst * 4 (von links nach rechts in 9 Abschnitte) |
||
74 | // zwischen den Schritten muss Pause > der Servoperiode sein, sonst keine Aktualisierung |
||
75 | |||
76 | #define REPEAT 1 |
||
77 | #define REPEAT_MIN 1 |
||
78 | #define REPEAT_MAX 100 |
||
79 | #define PAUSE 10 |
||
80 | #define PAUSE_MIN 4 // mindestens 400ms, da mechanischer Servo-Lauf zur Position berücksichtigt werden muss |
||
81 | #define PAUSE_MAX 20 // Pause pro Links-, Mittel- und Rechtsposition 10*100ms |
||
82 | #define PAUSE_STEP 0 |
||
83 | #define PAUSE_STEP_MIN 0 // Pause bei jeden Servoschritt in ms |
||
84 | #define PAUSE_STEP_MAX 200 |
||
85 | // The numbers below good for parallax servos at an F_CPU of 20.000MHz. |
||
86 | // Da einige Servo's auch eien Winkel von 180 grd zulassen, Wertebereich |
||
87 | // entgegen den sonst üblichen. Einschränkung mit default Kalibrierung |
||
88 | // auf 0,9ms (45) bis 2,1ms(45) gesetzt. Je nach Servo, entspricht einen |
||
89 | // Winkel von etwa 180grd |
||
90 | // Periode default 20ms |
||
91 | |||
92 | #define SERVO_MAX 211 // 2,7 ms bei prescaler 256, bei prescaler 64 SERVO_MAX * 4 |
||
93 | #define SERVO_MIN 26 // 0,33ms bei prescaler 256, bei prescaler 64 SERVO_MIN * 4 |
||
94 | #define SERVO_STEPS 255 // Servo-Schritte von links nach rechts, Anschlagkalibrierung spielt keine Rolle |
||
95 | #define SERVO_PRESCALER 256 // bei prescaler 256, bei prescaler 64 SERVO_PRESCALER / 4 |
||
96 | #define STEPS_255 0 // Servo-Schritte von links nach rechts, Anschlagkalibrierung spielt keine Rolle |
||
97 | #define STEPS_1023 1 // Servo-Schritte von links nach rechts, Anschlagkalibrierung spielt keine Rolle |
||
98 | |||
99 | typedef struct //Servo-Konstante je nach Prescaler |
||
100 | { |
||
101 | uint16_t max; |
||
102 | uint16_t min; |
||
103 | uint16_t steps; |
||
104 | uint16_t prescaler; |
||
105 | }ServoConst_t; |
||
106 | |||
107 | typedef struct //struct_ServoChannel |
||
108 | { |
||
109 | uint8_t pin; // hardware I/O port and pin for this channel |
||
110 | uint16_t duty; // PWM duty setting which corresponds to servo position |
||
111 | uint8_t rev; // Parameter, wie on/off; reverse; range |
||
112 | uint16_t min; // SERVO_MIN + Parameter min |
||
113 | uint16_t max; // SERVO_MAX - Parameter max |
||
114 | uint16_t mid_scaled; // skalierte Servomitte |
||
115 | int16_t mid; // Servomitte = SERVO_STEPS/2 +/- x Schritte; bei Pescaler 256 wird nur uint8_t benötigt aber bei 64 |
||
116 | }ServoChannelType; |
||
117 | |||
118 | //uint8_t sIdxSteps; // 0 für 255 und 1 für 1023 Schritte; Prescaler 256 oder 64 |
||
119 | |||
120 | // Define servo limits (depend on hardware) |
||
121 | typedef struct { |
||
122 | uint16_t min; |
||
123 | uint16_t max; |
||
124 | }servo_limit_t; |
||
125 | |||
126 | extern const servo_limit_t servo_limit[2][3]; |
||
127 | |||
128 | // Define servo positions (depend on hardware) |
||
129 | typedef struct { |
||
130 | uint16_t min; |
||
131 | uint16_t max; |
||
132 | uint16_t mid; |
||
133 | }steps_pw_t; |
||
134 | |||
135 | |||
136 | typedef struct { |
||
137 | uint8_t rev; |
||
138 | uint16_t min; |
||
139 | uint16_t max; |
||
140 | uint16_t mid; |
||
141 | } servo_t; |
||
142 | |||
143 | // Servopositionen für 950µs, 2,05ms und 1,5ms ==> Ergebnis Schritte. Da Zeit in µs ist F_CPU*e-1 |
||
144 | extern const steps_pw_t steps_pw[2]; |
||
145 | |||
146 | #define RIGHT 0 // Servopostionen, welche vom Einbau abhängig sind |
||
147 | #define LEFT 1 |
||
148 | #define MIDDLE 2 |
||
149 | |||
150 | #define POSIDX_MAX 4 |
||
151 | extern const uint8_t PosIdx[POSIDX_MAX]; // anzufahrende Servopositionen 0=MIN, 1=MID, 2=MAX |
||
152 | |||
153 | // functions |
||
154 | |||
155 | |||
156 | void servoSetDefaultPos(void); |
||
157 | |||
158 | // initializes servo system |
||
159 | // You must run this to begin servo control |
||
160 | void servoInit(uint8_t servo_period); |
||
161 | |||
162 | // turns off servo system |
||
163 | // This stops controlling the servos and |
||
164 | // returns control of the SERVOPORT to your code |
||
165 | void servoOff(void); |
||
166 | |||
167 | // set servo position on a given channel |
||
168 | // servoSetPosition() commands the servo on <channel> to the position you |
||
169 | // desire. The position input must lie between 0 and POSITION_MAX and |
||
170 | // will be automatically scaled to raw positions between SERVO_MIN and |
||
171 | // SERVO_MAX |
||
172 | void servoSetPosition(uint8_t channel, uint16_t position); |
||
173 | |||
174 | // set raw servo position on a given channel |
||
175 | // Works like non-raw commands but position is not scaled. Position must |
||
176 | // be between SERVO_MIN and SERVO_MAX |
||
177 | void servoSetPositionRaw(uint8_t channel, uint16_t position); |
||
178 | |||
179 | // set servo to a specific angle |
||
180 | void servoSetAngle(uint8_t servo_nr, int16_t angle); |
||
181 | |||
182 | // vor servoInit(), oder vor sei() ServoWerte mit servoSet...() initialisieren, einschließlich servoSetPosition(...)! |
||
183 | void servoSet_rev(uint8_t channel, uint8_t val); |
||
184 | void servoSet_min(uint8_t channel, uint16_t min); |
||
185 | void servoSet_max(uint8_t channel, uint16_t max); |
||
186 | void servoSet_mid(uint8_t channel, uint16_t mid); |
||
187 | uint16_t pw_us(uint16_t Steps); // gibt Zeit in µs bei x Servoschritte |
||
188 | uint16_t ServoSteps(void); // gibt "Konstante" derzeitiger Servoschritte zürück |
||
189 | |||
190 | #endif /* SERVO_H */ |