-
Notifications
You must be signed in to change notification settings - Fork 3
/
client.py
108 lines (96 loc) · 3.36 KB
/
client.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
import io
import socket
import struct
import time
import picamera
import threading
import numpy as np
import cv2
from os.path import join
from control.controller import Controller
class SplitFrames(object):
def __init__(self, connection):
self.connection = connection
self.stream = io.BytesIO()
self.count = 0
def write(self, buf):
if buf.startswith(b'\xff\xd8'):
# Start of new frame; send the old one's length
# then the data
size = self.stream.tell()
if size > 0:
self.connection.write(struct.pack('<L', size))
self.connection.flush()
self.stream.seek(0)
self.connection.write(self.stream.read(size))
self.count += 1
self.stream.seek(0)
self.stream.write(buf)
def send_img(cs, contorller):
connection = cs.makefile('wb')
print('client: sending images')
try:
output = SplitFrames(connection)
# with picamera.PiCamera(resolution='VGA', framerate=30) as camera:
with picamera.PiCamera(resolution='VGA', framerate=30) as camera:
time.sleep(1)
camera.start_recording(output, format='mjpeg')
camera.wait_recording(10)
camera.stop_recording()
# Write the terminating 0-length to the connection to let the server know we're done
connection.write(struct.pack('<L', 0))
finally:
time.sleep(2)
connection.close()
cs.close()
print('connection closed')
def recv_data(s, contorller):
""" Wait for results from the server.
"""
print('client: ready to recv data')
pre_img_id = -1
first_start = True
while (True):
# try:
buffer = s.recv(1024)
if (buffer is not None):
img_id, dc, dm, cur, signal = unpackage_paras(buffer)
print('Received: ' + str(img_id))
if img_id <= pre_img_id:
# outdate data
continue
if first_start:
contorller.start()
first_start = False
make_decisiton_with(dc, dm, cur, signal, contorller)
pre_img_id = img_id # update
def unpackage_paras(buffer):
""" Unpackage the parameters from buffer.
@Paras:
buffer: str
The recv buffer.
Note that the default recv size should be 112 (np.array(13, dtype=float64))
@Returns:
image_id
distance_to_center
"""
num_of_paras = len(buffer) / 112
packaged_parameters = np.frombuffer(buffer, dtype=np.float64).reshape(14 * num_of_paras)
cur_paras = packaged_parameters[0:14]
image_id = int(cur_paras[0])
w_left = cur_paras[1:4]
w_right = cur_paras[4:7]
w_middle = cur_paras[7:10]
distance_to_center = cur_paras[10]
distance_at_middle = cur_paras[11]
radian = cur_paras[12]
curvature = cur_paras[13]
stop_signal = (np.all(w_left == np.zeros(3)) and np.all(w_right == np.zeros(3)))
return image_id, distance_to_center, distance_at_middle, curvature, stop_signal
def make_decisiton_with(dc, dm, cur, stop_signal, contorller):
print('making desicion with ', dc, dm, cur ,str(stop_signal))
if stop_signal:
# stop the car!
contorller.finish_control()
else:
contorller.make_decision(dc, dm, cur)