smartpi 0.1.26__py3-none-any.whl → 0.1.28__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- smartpi/__init__.py +1 -1
- smartpi/base_driver.py +8 -24
- smartpi/gui.py +70 -238
- {smartpi-0.1.26.dist-info → smartpi-0.1.28.dist-info}/METADATA +1 -1
- {smartpi-0.1.26.dist-info → smartpi-0.1.28.dist-info}/RECORD +7 -7
- {smartpi-0.1.26.dist-info → smartpi-0.1.28.dist-info}/WHEEL +0 -0
- {smartpi-0.1.26.dist-info → smartpi-0.1.28.dist-info}/top_level.txt +0 -0
smartpi/__init__.py
CHANGED
smartpi/base_driver.py
CHANGED
|
@@ -575,46 +575,30 @@ def shut_down():
|
|
|
575
575
|
serial_lock.release() #释放线程锁
|
|
576
576
|
fcntl.flock(ser.fileno(), fcntl.LOCK_UN) # 释放进程锁
|
|
577
577
|
time.sleep(0.5)
|
|
578
|
-
|
|
579
|
-
def
|
|
578
|
+
|
|
579
|
+
def power_button_detec() -> bytes:
|
|
580
580
|
serial_lock.acquire() #获取线程锁
|
|
581
581
|
fcntl.flock(ser.fileno(), fcntl.LOCK_EX) # 进程锁,阻塞其他进程
|
|
582
582
|
response =process_received_data()
|
|
583
583
|
if response:
|
|
584
584
|
receive_data = response[4:-3]
|
|
585
|
-
if receive_data[0]==0XFF and receive_data[1]==
|
|
585
|
+
if receive_data[0]==0XFF and receive_data[1]==0XFD:
|
|
586
586
|
serial_lock.release() #释放线程锁
|
|
587
587
|
fcntl.flock(ser.fileno(), fcntl.LOCK_UN) # 释放进程锁
|
|
588
|
-
return
|
|
589
|
-
|
|
590
|
-
buffer.clear()
|
|
588
|
+
return 1
|
|
589
|
+
elif receive_data[0]==0XFF and receive_data[1]==0XFE:
|
|
591
590
|
serial_lock.release() #释放线程锁
|
|
592
591
|
fcntl.flock(ser.fileno(), fcntl.LOCK_UN) # 释放进程锁
|
|
593
|
-
return
|
|
594
|
-
else:
|
|
595
|
-
serial_lock.release() #释放线程锁
|
|
596
|
-
fcntl.flock(ser.fileno(), fcntl.LOCK_UN) # 释放进程锁
|
|
597
|
-
return False
|
|
598
|
-
|
|
599
|
-
def exit_program() -> bool:
|
|
600
|
-
serial_lock.acquire() #获取线程锁
|
|
601
|
-
fcntl.flock(ser.fileno(), fcntl.LOCK_EX) # 进程锁,阻塞其他进程
|
|
602
|
-
response =process_received_data()
|
|
603
|
-
if response:
|
|
604
|
-
receive_data = response[4:-3]
|
|
605
|
-
if receive_data[0]==0XFF and receive_data[1]==0XFD:
|
|
606
|
-
serial_lock.release() #释放线程锁
|
|
607
|
-
fcntl.flock(ser.fileno(), fcntl.LOCK_UN) # 释放进程锁
|
|
608
|
-
return True
|
|
592
|
+
return 2
|
|
609
593
|
else:
|
|
610
594
|
buffer.clear()
|
|
611
595
|
serial_lock.release() #释放线程锁
|
|
612
596
|
fcntl.flock(ser.fileno(), fcntl.LOCK_UN) # 释放进程锁
|
|
613
|
-
return
|
|
597
|
+
return 0
|
|
614
598
|
else:
|
|
615
599
|
serial_lock.release() #释放线程锁
|
|
616
600
|
fcntl.flock(ser.fileno(), fcntl.LOCK_UN) # 释放进程锁
|
|
617
|
-
return
|
|
601
|
+
return 0
|
|
618
602
|
|
|
619
603
|
def buf_clear():
|
|
620
604
|
buffer.clear()
|
smartpi/gui.py
CHANGED
|
@@ -1,255 +1,87 @@
|
|
|
1
|
-
|
|
2
|
-
import
|
|
3
|
-
from tkinter import font as tkfont
|
|
4
|
-
import os
|
|
5
|
-
import select
|
|
6
|
-
import struct
|
|
7
|
-
import threading
|
|
1
|
+
import socket
|
|
2
|
+
import json
|
|
8
3
|
import time
|
|
9
4
|
|
|
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
|
-
EV_SYN = 0x00
|
|
47
|
-
EV_ABS = 0x03
|
|
48
|
-
|
|
49
|
-
# 绝对轴定义
|
|
50
|
-
ABS_MT_POSITION_X = 0x35
|
|
51
|
-
ABS_MT_POSITION_Y = 0x36
|
|
52
|
-
ABS_MT_TRACKING_ID = 0x39
|
|
53
|
-
|
|
54
|
-
# 持续读取触摸事件
|
|
55
|
-
while not _exit_triggered:
|
|
56
|
-
try:
|
|
57
|
-
# 使用select等待数据可读
|
|
58
|
-
r, w, e = select.select([fd], [], [], 0.1)
|
|
59
|
-
|
|
60
|
-
if fd in r:
|
|
61
|
-
data = os.read(fd, EVENT_SIZE * 10)
|
|
62
|
-
data_len = len(data)
|
|
63
|
-
pos = 0
|
|
64
|
-
|
|
65
|
-
while pos + EVENT_SIZE <= data_len:
|
|
66
|
-
# 解析事件
|
|
67
|
-
tv_sec, tv_usec, etype, code, value = struct.unpack(EVENT_FORMAT, data[pos:pos+EVENT_SIZE])
|
|
68
|
-
pos += EVENT_SIZE
|
|
69
|
-
|
|
70
|
-
if etype == EV_ABS:
|
|
71
|
-
if code == ABS_MT_POSITION_X:
|
|
72
|
-
_x_cache = value
|
|
73
|
-
_touch_x = value
|
|
74
|
-
elif code == ABS_MT_POSITION_Y:
|
|
75
|
-
_y_cache = value
|
|
76
|
-
_touch_y = value
|
|
77
|
-
elif code == ABS_MT_TRACKING_ID:
|
|
78
|
-
if value >= 0:
|
|
79
|
-
_touch_pressed = True
|
|
80
|
-
_touch_x = _x_cache
|
|
81
|
-
_touch_y = _y_cache
|
|
82
|
-
else:
|
|
83
|
-
_touch_pressed = False
|
|
84
|
-
|
|
85
|
-
# 同步事件
|
|
86
|
-
elif etype == EV_SYN:
|
|
87
|
-
if _touch_pressed:
|
|
88
|
-
_touch_x = _x_cache
|
|
89
|
-
_touch_y = _y_cache
|
|
90
|
-
|
|
91
|
-
except BlockingIOError:
|
|
92
|
-
pass
|
|
93
|
-
except OSError as e:
|
|
94
|
-
if e.errno != 11: # 忽略EAGAIN错误
|
|
95
|
-
print(f"读取错误: {e}")
|
|
96
|
-
break
|
|
97
|
-
except Exception as e:
|
|
98
|
-
print(f"触摸读取异常: {e}")
|
|
99
|
-
break
|
|
100
|
-
# 关闭设备
|
|
101
|
-
os.close(fd)
|
|
102
|
-
|
|
103
|
-
def _run_gui():
|
|
104
|
-
"""运行GUI主循环"""
|
|
105
|
-
global _root, _canvas
|
|
106
|
-
|
|
107
|
-
# 创建GUI
|
|
108
|
-
_root = tk.Tk()
|
|
109
|
-
_root.title("Touch GUI")
|
|
110
|
-
_root.geometry("480x800")
|
|
111
|
-
_root.attributes('-fullscreen', True)
|
|
112
|
-
|
|
113
|
-
_canvas = tk.Canvas(_root, width=480, height=800, bg="white")
|
|
114
|
-
_canvas.pack(fill=tk.BOTH, expand=True)
|
|
115
|
-
|
|
116
|
-
_create_fonts()
|
|
117
|
-
|
|
118
|
-
# 定期检查退出按钮点击
|
|
119
|
-
def check_exit_periodically():
|
|
120
|
-
if _exit_triggered:
|
|
121
|
-
_root.quit()
|
|
122
|
-
return
|
|
123
|
-
_root.after(100, check_exit_periodically)
|
|
124
|
-
|
|
125
|
-
check_exit_periodically()
|
|
126
|
-
|
|
127
|
-
# 启动主循环
|
|
128
|
-
_root.mainloop()
|
|
129
|
-
|
|
130
|
-
def init():
|
|
131
|
-
"""初始化GUI"""
|
|
132
|
-
# 启动GUI线程
|
|
133
|
-
gui_thread = threading.Thread(target=_run_gui, daemon=True)
|
|
134
|
-
gui_thread.start()
|
|
135
|
-
|
|
136
|
-
# 启动触摸事件读取线程
|
|
137
|
-
touch_thread = threading.Thread(target=_read_touch_events, daemon=True)
|
|
138
|
-
touch_thread.start()
|
|
5
|
+
class _gui_client:
|
|
6
|
+
def __init__(self, host="127.0.0.1", port=65167):
|
|
7
|
+
self.sock = socket.create_connection((host, port))
|
|
8
|
+
self.clear()
|
|
9
|
+
|
|
10
|
+
def _send(self, cmd):
|
|
11
|
+
self.sock.sendall((json.dumps(cmd) + "\n").encode())
|
|
12
|
+
time.sleep(0.1)
|
|
13
|
+
|
|
14
|
+
def show_text(self, x, y, text, color="black", size=16):
|
|
15
|
+
self._send({"type": "text", "x": x, "y": y, "text": text, "color": color, "size": size})
|
|
16
|
+
|
|
17
|
+
def print(self, text):
|
|
18
|
+
self._send({"type": "print", "text": text})
|
|
19
|
+
|
|
20
|
+
def println(self, text):
|
|
21
|
+
self._send({"type": "println", "text": text})
|
|
22
|
+
|
|
23
|
+
def show_image(self, x, y, path, width, height):
|
|
24
|
+
self._send({"type": "image", "x": x, "y": y, "path": path, "width": width, "height": height})
|
|
25
|
+
|
|
26
|
+
def draw_line(self, x1, y1, x2, y2, color="black", width=1):
|
|
27
|
+
self._send({"type": "line", "x1": x1, "y1": y1, "x2": x2, "y2": y2, "color": color, "width": width})
|
|
28
|
+
|
|
29
|
+
def fill_rect(self, x, y, w, h, color="black"):
|
|
30
|
+
self._send({"type": "fill_rect", "x": x, "y": y, "w": w, "h": h, "color": color})
|
|
31
|
+
|
|
32
|
+
def draw_rect(self, x, y, w, h, width, color="black"):
|
|
33
|
+
self._send({"type": "draw_rect", "x": x, "y": y, "w": w, "h": h, "width": width, "color": color})
|
|
34
|
+
|
|
35
|
+
def fill_circle(self, cx, cy, r, color="black"):
|
|
36
|
+
self._send({"type": "fill_circle", "cx": cx, "cy": cy, "r": r, "color": color})
|
|
37
|
+
|
|
38
|
+
def draw_circle(self, cx, cy, r, width, color="black"):
|
|
39
|
+
self._send({"type": "draw_circle", "cx": cx, "cy": cy, "r": r, "width": width, "color": color})
|
|
139
40
|
|
|
140
|
-
|
|
41
|
+
def clear(self):
|
|
42
|
+
self._send({"type": "clear"})
|
|
43
|
+
|
|
44
|
+
def finish(self):
|
|
45
|
+
self.sock.close()
|
|
141
46
|
|
|
142
|
-
#
|
|
47
|
+
# 创建全局实例
|
|
48
|
+
_client_instance = _gui_client()
|
|
49
|
+
|
|
50
|
+
# 将类方法提升为模块级别的函数
|
|
143
51
|
def show_text(x, y, text, color="black", size=16):
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
52
|
+
_client_instance.show_text(x, y, text, color, size)
|
|
53
|
+
|
|
54
|
+
def print(text):
|
|
55
|
+
_client_instance.print(text)
|
|
56
|
+
|
|
57
|
+
def println(text):
|
|
58
|
+
_client_instance.println(text)
|
|
59
|
+
|
|
60
|
+
def show_image(x, y, path, width, height):
|
|
61
|
+
_client_instance.show_image(x, y, path, width, height)
|
|
147
62
|
|
|
148
63
|
def draw_line(x1, y1, x2, y2, color="black", width=1):
|
|
149
|
-
|
|
150
|
-
_root.after(0, lambda: _canvas.create_line(x1, y1, x2, y2, fill=color, width=width))
|
|
64
|
+
_client_instance.draw_line(x1, y1, x2, y2, color, width)
|
|
151
65
|
|
|
152
66
|
def fill_rect(x, y, w, h, color="black"):
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
67
|
+
_client_instance.fill_rect(x, y, w, h, color)
|
|
68
|
+
|
|
156
69
|
def draw_rect(x, y, w, h, width, color="black"):
|
|
157
|
-
|
|
158
|
-
_root.after(0, lambda: _canvas.create_rectangle(x, y, x+w, y+h, width=width, outline=color))
|
|
70
|
+
_client_instance.draw_rect(x, y, w, h, width, color)
|
|
159
71
|
|
|
160
72
|
def fill_circle(cx, cy, r, color="black"):
|
|
161
|
-
|
|
162
|
-
_root.after(0, lambda: _canvas.create_oval(cx-r, cy-r, cx+r, cy+r, fill=color, outline=""))
|
|
73
|
+
_client_instance.fill_circle(cx, cy, r, color)
|
|
163
74
|
|
|
164
75
|
def draw_circle(cx, cy, r, width, color="black"):
|
|
165
|
-
|
|
166
|
-
_root.after(0, lambda: _canvas.create_oval(cx-r, cy-r, cx+r, cy+r, width=width, outline=color))
|
|
167
|
-
|
|
168
|
-
def fill_polygon(points, color):
|
|
169
|
-
"""填充多边形"""
|
|
170
|
-
if _canvas:
|
|
171
|
-
_root.after(0, lambda: _canvas.create_polygon(points, fill=color, outline=""))
|
|
76
|
+
_client_instance.draw_circle(cx, cy, r, width, color)
|
|
172
77
|
|
|
173
78
|
def clear():
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
def
|
|
181
|
-
return
|
|
182
|
-
|
|
183
|
-
def get_touchscreen():
|
|
184
|
-
return _touch_pressed
|
|
185
|
-
|
|
186
|
-
#检测区域范围内是否按下 返回:1:按下;0:没按下
|
|
187
|
-
def get_xy_touch(x1,y1,x2,y2):
|
|
188
|
-
if get_touchscreen():
|
|
189
|
-
x = get_touch_x()
|
|
190
|
-
y = get_touch_y()
|
|
191
|
-
if x1 <= x <= x2 and y1 <= y <= y2:
|
|
192
|
-
return 1
|
|
193
|
-
else:
|
|
194
|
-
return 0
|
|
195
|
-
else:
|
|
196
|
-
return 0
|
|
197
|
-
|
|
198
|
-
def should_exit():
|
|
199
|
-
"""检查是否应该退出程序"""
|
|
200
|
-
return _exit_triggered
|
|
201
|
-
|
|
202
|
-
def draw_exit_button():
|
|
203
|
-
"""绘制退出按钮"""
|
|
204
|
-
if not _canvas:
|
|
205
|
-
return
|
|
206
|
-
|
|
207
|
-
# 退出按钮位置 - 底部中间
|
|
208
|
-
button_width = 100
|
|
209
|
-
button_height = 80
|
|
210
|
-
x1 = 480//2 - button_width//2
|
|
211
|
-
y1 = 800 - button_height - 20
|
|
212
|
-
x2 = 480//2 + button_width//2
|
|
213
|
-
y2 = 800 - 20
|
|
214
|
-
|
|
215
|
-
# 绘制朝向左边的蓝色三角形
|
|
216
|
-
triangle_size = 50
|
|
217
|
-
center_x = (x1 + x2) // 2
|
|
218
|
-
center_y = (y1 + y2) // 2
|
|
219
|
-
|
|
220
|
-
# 三角形顶点坐标 - 朝向左边的三角形
|
|
221
|
-
points = [
|
|
222
|
-
center_x - triangle_size//2, center_y, # 左顶点
|
|
223
|
-
center_x + triangle_size//2, center_y - triangle_size//2, # 右上顶点
|
|
224
|
-
center_x + triangle_size//2, center_y + triangle_size//2 # 右下顶点
|
|
225
|
-
]
|
|
226
|
-
|
|
227
|
-
_root.after(0, lambda: _canvas.create_polygon(points, fill="blue", outline=""))
|
|
228
|
-
|
|
229
|
-
def check_exit_button(x, y):
|
|
230
|
-
"""检查是否点击了退出按钮"""
|
|
231
|
-
# 退出按钮位置 - 底部中间
|
|
232
|
-
button_width = 100
|
|
233
|
-
button_height = 80
|
|
234
|
-
x1 = 480//2 - button_width//2
|
|
235
|
-
y1 = 800 - button_height - 20
|
|
236
|
-
x2 = 480//2 + button_width//2
|
|
237
|
-
y2 = 800 - 20
|
|
238
|
-
|
|
239
|
-
if x1 <= x <= x2 and y1 <= y <= y2:
|
|
240
|
-
global _exit_triggered
|
|
241
|
-
_exit_triggered = True
|
|
242
|
-
return True
|
|
243
|
-
return False
|
|
244
|
-
|
|
245
|
-
#判断有无按下退出按键 返回:1:按下;0:没按下
|
|
246
|
-
def exit_button():
|
|
247
|
-
x = get_touch_x()
|
|
248
|
-
y = get_touch_y()
|
|
249
|
-
pressed = get_touchscreen()
|
|
250
|
-
draw_exit_button()
|
|
251
|
-
if pressed and check_exit_button(x,y):
|
|
252
|
-
return 1
|
|
253
|
-
else:
|
|
254
|
-
return 0
|
|
79
|
+
_client_instance.clear()
|
|
80
|
+
|
|
81
|
+
def finish():
|
|
82
|
+
_client_instance.finish()
|
|
83
|
+
|
|
84
|
+
# 可选:如果希望仍然可以使用类创建新实例
|
|
85
|
+
def create_client(host="127.0.0.1", port=65167):
|
|
86
|
+
return _gui_client(host, port)
|
|
255
87
|
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
smartpi/__init__.py,sha256=
|
|
2
|
-
smartpi/base_driver.py,sha256=
|
|
1
|
+
smartpi/__init__.py,sha256=jfBxodXnOKynv0a2moORso7YKZjdwbyIjWdR3N3yvsY,55
|
|
2
|
+
smartpi/base_driver.py,sha256=Nup2dkW2mURpl6wazsK1CIjkDdyTI0zR2e94SCwfU1Y,24396
|
|
3
3
|
smartpi/color_sensor.py,sha256=YXJjknYjp7teTZsHYZRAWgi73CH0MhBp1go9y0Inxyo,498
|
|
4
4
|
smartpi/cw2015.py,sha256=1lAF-pi_ye_ya1AZQS1sjbgsDf7MThO5IAskKsNGBzA,5695
|
|
5
5
|
smartpi/flash.py,sha256=-pUqg6FSVoBiLFKqrG9B4dFqn8lICnQsSPJr_MtZLIU,4132
|
|
6
|
-
smartpi/gui.py,sha256=
|
|
6
|
+
smartpi/gui.py,sha256=HaupXWg5cWw_n86ge8IxARrvL3gpcDCNRwATK9irwH8,2960
|
|
7
7
|
smartpi/humidity.py,sha256=nZwiBtMWKNipVM83ymajZACPHxkC2vUJjDMmCOPN9lw,499
|
|
8
8
|
smartpi/led.py,sha256=flvN7EJfP6VDTSiC93w1uR8pRxcZD9w2vLXA1GbJTo8,538
|
|
9
9
|
smartpi/light_sensor.py,sha256=MayyVikWcXQfjeZrtYRnwYgHBDzu2g-mfJLpdd29EG8,1852
|
|
@@ -14,7 +14,7 @@ smartpi/temperature.py,sha256=VT79CYA41q1d_4AM-Y0eIMeIw7AtCkSXjWVws6Yx5yE,462
|
|
|
14
14
|
smartpi/touch_sensor.py,sha256=P57RRQlqY0KexpMi-ydqwF5albOKCBOGb0Rb6zeVTqk,440
|
|
15
15
|
smartpi/trace.py,sha256=tut7BMbq87ShaR5eNuv7PZtAEz9DS5_BDf0_muIZ-tQ,4577
|
|
16
16
|
smartpi/ultrasonic.py,sha256=kmVpUfvE1oHoqgv92ZU6Fi-sO6DSwm10ssKsImNeOkY,624
|
|
17
|
-
smartpi-0.1.
|
|
18
|
-
smartpi-0.1.
|
|
19
|
-
smartpi-0.1.
|
|
20
|
-
smartpi-0.1.
|
|
17
|
+
smartpi-0.1.28.dist-info/METADATA,sha256=qruw894MPGjH8BBu9H3XtYYzckjRbwcbkVOnv88Bcu4,311
|
|
18
|
+
smartpi-0.1.28.dist-info/WHEEL,sha256=oiQVh_5PnQM0E3gPdiz09WCNmwiHDMaGer_elqB3coM,92
|
|
19
|
+
smartpi-0.1.28.dist-info/top_level.txt,sha256=PoLhUCmWAiQUg5UeN2fS-Y1iQyBbF2rdUlizXtpHGRQ,8
|
|
20
|
+
smartpi-0.1.28.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|