Revision 1344
Final version of feedback controls project
branches/encoders/code/behaviors/spline/server/internals.h | ||
---|---|---|
1 | 1 |
#ifndef INTERNALS_H |
2 | 2 |
#define INTERNALS_H |
3 | 3 |
|
4 |
#define LS 0 |
|
5 |
#define LD 1 |
|
6 |
#define RS 2 |
|
7 |
#define RD 3 |
|
8 |
|
|
9 | 4 |
#define LEFT 1 |
10 | 5 |
#define RIGHT 0 |
11 | 6 |
|
12 |
#define FORWARD 1 |
|
13 |
#define BACKWARD 0 |
|
14 | 7 |
#define SENDER 1 |
15 | 8 |
#define RECEIVER 0 |
16 | 9 |
|
... | ... | |
21 | 14 |
#define DT .088 |
22 | 15 |
|
23 | 16 |
#define DIST(x1, y1, x2, y2) (sqrt(((x1)-(x2))*((x1)-(x2)) + ((y1)-(y2))*((y1)-(y2)))) |
24 |
#define LOOK_AHEAD 40
|
|
17 |
#define LOOK_AHEAD 30
|
|
25 | 18 |
#define LOOK_AHEAD_ERR_THRES 5 |
26 |
#define VELOCITY 10
|
|
19 |
#define VELOCITY 15
|
|
27 | 20 |
|
28 | 21 |
typedef struct state |
29 | 22 |
{ |
branches/encoders/code/behaviors/spline/server/server.c | ||
---|---|---|
66 | 66 |
} |
67 | 67 |
} |
68 | 68 |
|
69 |
#define RADIUS 100 |
|
69 |
//#define FORWARD |
|
70 |
|
|
71 |
#ifdef FORWARD |
|
72 |
#undef LEFT |
|
73 |
#undef RIGHT |
|
74 |
#define LEFT 0 |
|
75 |
#define RIGHT 1 |
|
76 |
#endif |
|
77 |
|
|
78 |
#define CIRCLE |
|
79 |
//#define SINE |
|
80 |
//#define COSINE |
|
81 |
//#define LINE45 |
|
82 |
//#define LINE |
|
83 |
|
|
84 |
#define RADIUS 70 |
|
85 |
#define AMP 70 |
|
86 |
|
|
70 | 87 |
int main(int argc, char** args) |
71 | 88 |
{ |
72 |
//init(RADIUS, 0, M_PI/2); |
|
73 |
init(0, 50, 0); |
|
74 |
//init(0,0,0); |
|
89 |
#ifdef CIRCLE |
|
90 |
init(20, 30, 0); |
|
91 |
#endif |
|
92 |
#ifdef SINE |
|
93 |
init(0, 0, M_PI/4); |
|
94 |
#endif |
|
95 |
#ifdef COSINE |
|
96 |
init(0, AMP, 0); |
|
97 |
#endif |
|
98 |
#ifdef LINE45 |
|
99 |
init(0,0,0); |
|
100 |
#endif |
|
101 |
#ifdef LINE |
|
102 |
init(0,0,0); |
|
103 |
#endif |
|
75 | 104 |
double x_ref[LEN]; |
76 | 105 |
double y_ref[LEN]; |
77 | 106 |
int i; |
78 | 107 |
for (i = 0; i < LEN; i++) { |
79 |
// x_ref[i] = RADIUS * cos((double)(i+1) / LEN * 5.0 / 2.0 * M_PI); |
|
80 |
// y_ref[i] = RADIUS * sin((double)(i+1) / LEN * 5.0 / 2.0 * M_PI); |
|
81 |
|
|
108 |
#ifdef CIRCLE |
|
109 |
x_ref[i] = RADIUS * cos((double)(i) / LEN * 2.0 * M_PI); |
|
110 |
y_ref[i] = RADIUS * sin((double)(i) / LEN * 2.0 * M_PI); |
|
111 |
#endif |
|
112 |
#ifdef SINE |
|
82 | 113 |
x_ref[i] = ((double)(i+1) / LEN * 2.0 * M_PI) * 100; |
83 |
y_ref[i] = 50 *cos (x_ref[i] / 16.6667);//(double)(i+1) / LEN * 3.0 / 2.0 * M_PI); |
|
84 |
// x_ref[i] = (double)i / LEN * 100; |
|
85 |
// y_ref[i] = (double)i / LEN * 100; |
|
114 |
y_ref[i] = AMP *sin (x_ref[i] / 50); |
|
115 |
#endif |
|
116 |
#ifdef COSINE |
|
117 |
x_ref[i] = ((double)(i+1) / LEN * 2.0 * M_PI) * 100; |
|
118 |
y_ref[i] = AMP *cos (x_ref[i] / 50); |
|
119 |
#endif |
|
120 |
#ifdef LINE45 |
|
121 |
x_ref[i] = (double)i / LEN * 1000; |
|
122 |
y_ref[i] = (double)i / LEN * 1000; |
|
123 |
#endif |
|
124 |
#ifdef LINE |
|
125 |
x_ref[i] = (double)i / LEN * 1000; |
|
126 |
y_ref[i] = 0; |
|
127 |
#endif |
|
128 |
|
|
86 | 129 |
//printf("%g \t%g\n", x_ref[i], y_ref[i]); |
87 | 130 |
//getchar(); |
88 | 131 |
} |
... | ... | |
127 | 170 |
// ref_vels[LEFT] = 20; |
128 | 171 |
// ref_vels[RIGHT] = 20; |
129 | 172 |
|
173 |
|
|
130 | 174 |
ref_vels[LEFT] = -(char)robot_velocity(1, robot.vl_ref); |
131 | 175 |
ref_vels[RIGHT] = -(char)robot_velocity(1, robot.vr_ref); |
132 |
|
|
176 |
#ifdef FORWARD |
|
177 |
ref_vels[LEFT] = -ref_vels[LEFT]; |
|
178 |
ref_vels[RIGHT] = -ref_vels[RIGHT]; |
|
179 |
#endif |
|
180 |
|
|
133 | 181 |
//printf("Ref Vs: \t\t%d\t%d\n", ref_vels[LEFT], ref_vels[RIGHT]); |
134 | 182 |
// printf("Left Speed: %d \t Right Speed: %d\n", encoders[LS], encoders[RS]); |
135 | 183 |
|
... | ... | |
156 | 204 |
}while(count < 2); |
157 | 205 |
|
158 | 206 |
|
207 |
#ifndef FORWARD |
|
159 | 208 |
robot.vl = real_velocity(1, -ref_vels[LEFT]); |
160 | 209 |
robot.vr = real_velocity(1, -ref_vels[RIGHT]); |
161 |
|
|
162 |
// printf("ACTUAL V \t\t%g\t%g\n", robot.vl, robot.vr); |
|
210 |
#else |
|
211 |
robot.vl = real_velocity(1, ref_vels[LEFT]); |
|
212 |
robot.vr = real_velocity(1, ref_vels[RIGHT]); |
|
213 |
#endif |
|
214 |
|
|
215 |
//printf("ACTUAL V \t\t%g\t%g\n", robot.vl, robot.vr); |
|
163 | 216 |
|
164 | 217 |
updatePosition(); |
165 | 218 |
//printf("Raw Location is x: %g \t y: %g \t o: %g\n", robot.x,robot.y, robot.theta); |
... | ... | |
199 | 252 |
|
200 | 253 |
void pos_control_curve(curv_t *ref, int len) { |
201 | 254 |
int goal_idx = find_goal(ref, len); |
255 |
//printf("\tGOAL: x: %g, y: %g\n", ref->x[goal_idx], ref->y[goal_idx]); |
|
202 | 256 |
//did a transformation here. |
203 | 257 |
double goal_y = cos(robot.theta)*(ref->y[goal_idx]-robot.y) |
204 | 258 |
- sin(robot.theta)*(ref->x[goal_idx]-robot.x); |
205 | 259 |
double goal_rad = 2*goal_y / LOOK_AHEAD; |
206 | 260 |
|
207 |
//printf("GOAL: y: %g, o: %g\n", goal_y, goal_rad); |
|
208 | 261 |
|
209 | 262 |
robot.vl_ref = real_velocity(1, VELOCITY)*(1-0.5*goal_rad); |
210 | 263 |
robot.vr_ref = real_velocity(1, VELOCITY)*(1+0.5*goal_rad); |
... | ... | |
234 | 287 |
min_idx = i; |
235 | 288 |
} |
236 | 289 |
} |
290 |
/* |
|
291 |
if (min_dist > LOOK_AHEAD) { |
|
292 |
printf("toooooo far away \n"); |
|
293 |
return min_idx; |
|
294 |
} |
|
295 |
*/ |
|
237 | 296 |
//printf("%d min %f\n", min_idx, min_dist); |
238 | 297 |
//getchar(); |
239 | 298 |
goal_idx = -1; |
240 | 299 |
err = LOOK_AHEAD_ERR_THRES; |
241 |
while(goal_idx == -1 && ctr < 3) {
|
|
300 |
while(ctr < 3) { |
|
242 | 301 |
for (i = min_idx; i < len; i++) { |
302 |
#ifdef CIRCLE |
|
303 |
if (i == len-1) |
|
304 |
i = 0; |
|
305 |
#endif |
|
243 | 306 |
temp = DIST(ref->x[i], ref->y[i], robot.x, robot.y); |
244 | 307 |
if (abs(temp - LOOK_AHEAD) < err) { |
245 | 308 |
goal_idx = i; |
... | ... | |
250 | 313 |
ctr++; |
251 | 314 |
} |
252 | 315 |
while(1) { |
253 |
//printf("eol\n");
|
|
316 |
printf("eol\n"); |
|
254 | 317 |
exit(0); |
255 | 318 |
} |
256 | 319 |
return goal_idx; |
branches/encoders/code/behaviors/spline/server/speed_map.c | ||
---|---|---|
1 | 1 |
#include "speed_map.h" |
2 |
#include <stdlib.h> |
|
2 | 3 |
|
3 | 4 |
double robot_1[41] = |
4 | 5 |
{ |
branches/encoders/code/behaviors/spline/slave/slave.c | ||
---|---|---|
3 | 3 |
|
4 | 4 |
#define GROUP 1 |
5 | 5 |
#define MOTOR 0 |
6 |
#define ENCODER 1 |
|
6 |
#define ENCODER 132
|
|
7 | 7 |
|
8 |
#define LS 0 |
|
9 |
#define LD 1 |
|
10 |
#define RS 2 |
|
11 |
#define RD 3 |
|
8 |
void packet_receive (char type, int source, char* packet, int length); |
|
9 |
void ctrl(void); |
|
12 | 10 |
|
13 |
#define H0 0 |
|
14 |
#define L0 1 |
|
15 |
#define H1 2 |
|
16 |
#define L1 3 |
|
17 |
|
|
18 |
void packet_receive (char type, int source, unsigned char* packet, int length); |
|
19 |
|
|
20 | 11 |
PacketGroupHandler packetHandler = {GROUP, NULL, NULL, &packet_receive, NULL}; |
21 | 12 |
|
22 | 13 |
char buf[32]; |
23 |
int count = 0; |
|
24 |
int left_dir = FORWARD; |
|
25 |
int right_dir = FORWARD; |
|
26 |
int left_speed = 0; |
|
27 |
int right_speed = 0; |
|
14 |
long unsigned int count = 0; |
|
15 |
volatile int left_dir = FORWARD; |
|
16 |
volatile int right_dir = FORWARD; |
|
28 | 17 |
|
18 |
volatile int left_ref; |
|
19 |
volatile int right_ref; |
|
20 |
|
|
21 |
volatile int left_old; |
|
22 |
volatile int right_old; |
|
23 |
|
|
24 |
volatile int left_i = 0; |
|
25 |
volatile int right_i = 0; |
|
26 |
|
|
27 |
volatile int left_u; |
|
28 |
volatile int right_u; |
|
29 |
|
|
30 |
volatile int left_vel = 0; |
|
31 |
volatile int right_vel = 0; |
|
32 |
|
|
33 |
#define PL 1 |
|
34 |
#define DL 0.1 |
|
35 |
#define IL 0.1 |
|
36 |
|
|
37 |
#define PR 1.5 |
|
38 |
#define DR 0.2 |
|
39 |
#define IR 0.1 |
|
40 |
|
|
41 |
|
|
42 |
#define INTERVAL 50 |
|
43 |
|
|
29 | 44 |
/* receive motor speed from master: |
30 | 45 |
* left_speed left_dir right_speed right_dir |
31 | 46 |
* then sent raw encoder values back to master: |
32 | 47 |
* high_left low_left high_right low_right |
33 | 48 |
*/ |
34 |
void packet_receive (char type, int source, unsigned char* packet, int length) {
|
|
49 |
void packet_receive (char type, int source, char* packet, int length) { |
|
35 | 50 |
if (type != MOTOR) return; |
36 |
//orb_set_color(WHITE); |
|
37 |
left_dir = packet[LD]; |
|
38 |
left_speed = packet[LS]; |
|
39 |
right_dir = packet[RD]; |
|
40 |
right_speed = packet[RS]; |
|
41 |
sprintf(buf, "Received: %d %d %d %d\n", packet[LS], packet[LD], packet[RS], packet[RD]); |
|
51 |
|
|
52 |
left_ref = packet[0]; |
|
53 |
right_ref = packet[1]; |
|
54 |
|
|
55 |
sprintf(buf, "received: %d %d\n", left_ref, right_ref); |
|
42 | 56 |
usb_puts(buf); |
43 |
//motor1_set(packet[LD],packet[LS]); |
|
44 |
//motor2_set(packet[RD],packet[RS]); |
|
45 | 57 |
//orb_set_color(GREEN); |
46 | 58 |
} |
47 | 59 |
|
60 |
void ctrl() { |
|
61 |
int left_err = left_ref - left_vel; |
|
62 |
int right_err = right_ref - right_vel; |
|
63 |
|
|
64 |
left_err = left_vel == 2048 ? left_old : left_err; |
|
65 |
right_err = right_vel == 2048 ? right_old : right_err; |
|
66 |
|
|
67 |
left_i += left_err; |
|
68 |
left_u = (int)(PL*(float)left_err + DL*(float)(left_err - left_old) + IL*(float)left_i); |
|
69 |
left_old = left_err; |
|
70 |
|
|
71 |
right_i += right_err; |
|
72 |
right_u = (int)(PR*(float)right_err + DR*(float)(right_err - right_old) + IR*(float)right_i); |
|
73 |
right_old = right_err; |
|
74 |
|
|
75 |
if (left_u < 0) { |
|
76 |
left_dir = 0; |
|
77 |
left_u = -left_u; |
|
78 |
} |
|
79 |
else |
|
80 |
left_dir = 1; |
|
81 |
|
|
82 |
if (right_u < 0) { |
|
83 |
right_u = -right_u; |
|
84 |
right_dir = 0; |
|
85 |
} |
|
86 |
else |
|
87 |
right_dir = 1; |
|
88 |
|
|
89 |
left_u += 160; |
|
90 |
right_u += 160; |
|
91 |
|
|
92 |
left_u = left_u > 210 ? 210 : left_u; |
|
93 |
right_u = right_u > 210 ? 210 : right_u; |
|
94 |
} |
|
95 |
|
|
48 | 96 |
int main (void) { |
97 |
char encoder[2]; |
|
49 | 98 |
dragonfly_init(ALL_ON); |
50 | 99 |
usb_init(); |
51 | 100 |
encoders_init(); |
52 | 101 |
//usb_puts("xbee id "); |
53 | 102 |
//usb_putc(wl_get_xbee_id()); |
54 | 103 |
wl_init(); |
55 |
|
|
104 |
left_ref = 20; |
|
105 |
right_ref = 20; |
|
56 | 106 |
wl_register_packet_group(&packetHandler); |
57 | 107 |
//orb_set_color(RED); |
58 | 108 |
//motor1_set(FORWARD,230); |
59 | 109 |
//motor2_set(FORWARD,230); |
60 |
|
|
110 |
|
|
61 | 111 |
while (1) { |
62 |
int encoder_left = encoder_get_v(LEFT); |
|
63 |
int encoder_right = encoder_get_v(RIGHT); |
|
64 |
unsigned char encoder[4]; |
|
65 |
encoder[H0] = (encoder_left >> 8) & 0xFF; |
|
66 |
encoder[L0] = (encoder_left) & 0xFF; |
|
67 |
encoder[H1] = (encoder_right >> 8) & 0xFF; |
|
68 |
encoder[L1] = (encoder_right) & 0xFF; |
|
69 |
wl_send_global_packet(GROUP, ENCODER, encoder, 4, 0); |
|
70 |
sprintf(buf, "Sent (%d): %d %d\n", count++, encoder_left, encoder_right); |
|
71 |
usb_puts(buf); |
|
112 |
usb_puts("We Win\n"); |
|
113 |
//left_vel = encoder_get_v(0); |
|
114 |
//right_vel = encoder_get_v(1); |
|
115 |
delay_ms(1000); |
|
116 |
//if (!(count % INTERVAL)) { |
|
117 |
// wl_send_global_packet(GROUP, ENCODER, encoder, 2, 0); |
|
118 |
encoder[0] = left_vel; |
|
119 |
encoder[1] = right_vel; |
|
120 |
|
|
121 |
// usb_puti(left_vel); |
|
122 |
// sprintf(buf, "sent (%d): %d %d %d %d\n", count, left_vel, right_vel, encoder[0], encoder[1]); |
|
123 |
// usb_puts(buf); |
|
124 |
// usb_puti(encoder[0]); |
|
125 |
// } |
|
126 |
|
|
72 | 127 |
|
73 |
wl_do(); |
|
74 |
motor1_set(left_dir, left_speed); |
|
75 |
motor2_set(right_dir, right_speed); |
|
76 |
delay_ms(100); |
|
128 |
//ctrl(); |
|
129 |
|
|
130 |
// if (!(count % INTERVAL)) |
|
131 |
// wl_do(); |
|
132 |
|
|
133 |
// sprintf(buf, "motor (%d): %d %d %d %d\n", count, left_dir, left_ref, right_dir, right_ref); |
|
134 |
// usb_puts(buf); |
|
135 |
|
|
136 |
//motor1_set(left_dir, left_u); |
|
137 |
//motor2_set(right_dir, right_u); |
|
138 |
|
|
139 |
count++; |
|
140 |
delay_ms(1000); |
|
77 | 141 |
} |
78 | 142 |
} |
79 |
|
branches/encoders/code/behaviors/spline/master/master.c | ||
---|---|---|
6 | 6 |
|
7 | 7 |
#define GROUP 1 |
8 | 8 |
#define MOTOR 0 |
9 |
#define ENCODER 1 |
|
9 |
#define ENCODER 132
|
|
10 | 10 |
|
11 | 11 |
#define SENDER 1 |
12 | 12 |
#define RECEIVER 0 |
13 | 13 |
|
14 |
unsigned char data[4];
|
|
14 |
int id = -1;
|
|
15 | 15 |
|
16 |
char data[2]; |
|
17 |
|
|
16 | 18 |
sentCount = 0; |
17 | 19 |
char position = 0; |
18 | 20 |
|
19 |
void packet_receive (char type, int source, unsigned char* packet, int length);
|
|
21 |
void packet_receive (char type, int source, char* packet, int length); |
|
20 | 22 |
|
21 | 23 |
PacketGroupHandler packetHandler = {GROUP, 0, 0, &packet_receive, 0}; |
22 | 24 |
|
23 |
void packet_receive (char type, int source, unsigned char* packet, int length) {
|
|
25 |
void packet_receive (char type, int source, char* packet, int length) { |
|
24 | 26 |
|
25 | 27 |
if(type == ENCODER) |
26 |
{ |
|
28 |
{ |
|
29 |
if(id == -1) |
|
30 |
id = source; |
|
31 |
if(source != id) |
|
32 |
motor1_set(1, 200); |
|
27 | 33 |
usb_putc(packet[0]); |
28 | 34 |
usb_putc(packet[1]); |
29 |
usb_putc(packet[2]); |
|
30 |
usb_putc(packet[3]); |
|
31 |
} |
|
35 |
// usb_putc(packet[2]);
|
|
36 |
// usb_putc(packet[3]);
|
|
37 |
}
|
|
32 | 38 |
|
33 | 39 |
} |
34 | 40 |
|
... | ... | |
49 | 55 |
lcd_puts("starting init"); |
50 | 56 |
data[0] = usb_getc(); |
51 | 57 |
data[1] = usb_getc(); |
52 |
data[2] = usb_getc(); |
|
53 |
data[3] = usb_getc(); |
|
58 |
//data[2] = usb_getc();
|
|
59 |
//data[3] = usb_getc();
|
|
54 | 60 |
|
55 | 61 |
lcd_puts("Done with init\n"); |
56 | 62 |
|
57 |
wl_send_global_packet(GROUP, MOTOR, data, 4, 0);
|
|
63 |
wl_send_global_packet(GROUP, MOTOR, data, 2, 0);
|
|
58 | 64 |
} |
59 | 65 |
else |
60 | 66 |
{ |
... | ... | |
67 | 73 |
{ |
68 | 74 |
data[0] = usb_getc(); |
69 | 75 |
data[1] = usb_getc(); |
70 |
data[2] = usb_getc(); |
|
71 |
data[3] = usb_getc(); |
|
72 |
wl_send_global_packet(GROUP, MOTOR, data, 4, 0);
|
|
73 |
} |
|
76 |
//data[2] = usb_getc();
|
|
77 |
//data[3] = usb_getc();
|
|
78 |
wl_send_global_packet(GROUP, MOTOR, data, 2, 0);
|
|
79 |
}
|
|
74 | 80 |
|
75 | 81 |
wl_do(); |
76 | 82 |
} |
Also available in: Unified diff