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 import Queue
34 from datetime import datetime
35 from python_qt_binding.QtCore import Qt, Signal
36 try:
37 from python_qt_binding.QtGui import QDialog, QLabel, QTextBrowser, QVBoxLayout
38 except:
39 from python_qt_binding.QtWidgets import QDialog, QLabel, QTextBrowser, QVBoxLayout
40 import threading
41 import time
42 import traceback
43
44 import rospy
45
46 from master_discovery_fkie.master_discovery import Discoverer
47 from master_discovery_fkie.udp import DiscoverSocket, QueueReceiveItem
48 import node_manager_fkie as nm
49 from node_manager_fkie.common import utf8
50
51
53
54 TIMEOUT = 0.1
55
56 display_clear_signal = Signal()
57 display_append_signal = Signal(str)
58 status_text_signal = Signal(str)
59 network_join_request = Signal(int)
60
61 - def __init__(self, default_mcast_group, default_port, networks_count, parent=None):
62 '''
63 Creates an input dialog.
64 @param default_port: the default discovery port
65 @type default_port: C{int}
66 @param networks_count: the count of discovering ports
67 @type networks_count: C{int}
68 '''
69 QDialog.__init__(self, parent=parent)
70 threading.Thread.__init__(self)
71 self.default_port = default_port
72 self.setObjectName('NetworkDiscoveryDialog')
73 self.setAttribute(Qt.WA_DeleteOnClose, True)
74 self.setWindowFlags(Qt.Window)
75 self.setWindowTitle('Network Discovery')
76 self.resize(728, 512)
77 self.verticalLayout = QVBoxLayout(self)
78 self.verticalLayout.setObjectName("verticalLayout")
79 self.verticalLayout.setContentsMargins(1, 1, 1, 1)
80
81 self.display = QTextBrowser(self)
82 self.display.setReadOnly(True)
83 self.verticalLayout.addWidget(self.display)
84 self.display_clear_signal.connect(self.display.clear)
85 self.display_append_signal.connect(self.display.append)
86 self.display.anchorClicked.connect(self.on_anchorClicked)
87
88 self.status_label = QLabel('0 messages', self)
89 self.verticalLayout.addWidget(self.status_label)
90 self.status_text_signal.connect(self.status_label.setText)
91 self._msg_counts = dict()
92
93 self._networks_count = networks_count
94 self._running = True
95 self._received_msgs = 0
96 self._discovered = dict()
97 self._hosts = dict()
98 self.mutex = threading.RLock()
99 self.sockets = []
100 with self.mutex:
101 try:
102 for p in range(networks_count):
103 msock = DiscoverSocket(default_port + p, default_mcast_group)
104 self.sockets.append(msock)
105 msock.settimeout(self.TIMEOUT)
106 except Exception as e:
107 self.display.setText(utf8(e))
108 self.setDaemon(True)
109 self.start()
110
135
137 self.parent().masterlist_service.refresh(self.parent().getMasteruri(), False)
138 while (not rospy.is_shutdown()) and self._running:
139 with self.mutex:
140 for msock in self.sockets:
141 received = True
142 while received:
143 try:
144 recv_item = msock.receive_queue.get(False)
145 self._received_msgs += 1
146 self.on_heartbeat_received(recv_item.msg, recv_item.sender_addr, (recv_item.via == QueueReceiveItem.MULTICAST))
147 except Queue.Empty:
148 received = False
149 status_text = 'received messages: %d' % (self._received_msgs)
150 self.status_text_signal.emit(status_text)
151
152 time.sleep(3)
153
157
159 self._running = False
160 with self.mutex:
161 for p in range(len(self.sockets)):
162 try:
163 self.sockets[p].close()
164 except:
165 pass
166
168 self.display_clear_signal.emit()
169 text = '<div style="font-family:Fixedsys,Courier,monospace; padding:10px;">\n'
170 for index, addr_dict in self._discovered.items():
171 text = ''.join([text, 'Network <b>', utf8(index), '</b>: <a href="', utf8(index), '">join</a><dl>'])
172 for addr, (hostname, ts) in addr_dict.items():
173 text = ''.join([text, '<dt>', self._getTsStr(ts), ' <b><u>', utf8(hostname), '</u></b> ', utf8(addr), ', received messages: ', str(self._msg_counts[hostname]), '</dt>\n'])
174 text = ''.join([text, '</dl><br>'])
175 text = ''.join([text, '</div>'])
176 self.display_append_signal.emit(text)
177
179 dt = datetime.fromtimestamp(timestamp)
180 diff = time.time() - timestamp
181 diff_dt = datetime.fromtimestamp(diff)
182 before = '0 sec'
183 if (diff < 60):
184 before = diff_dt.strftime('%S sec')
185 elif (diff < 3600):
186 before = diff_dt.strftime('%M:%S min')
187 elif (diff < 86400):
188 before = diff_dt.strftime('%H:%M:%S std')
189 else:
190 before = diff_dt.strftime('%d Day(s) %H:%M:%S')
191 return ''.join([dt.strftime('%H:%M:%S'), ' (', before, ')'])
192
194 self._updateDisplay()
195 try:
196 self.network_join_request.emit(int(url.toString()))
197 except:
198 print traceback.format_exc(1)
199