def test(self): cfc = CompoundFunctionContainer(13) t0 = {"source": "initial", "target": "s1"} t1 = { "trigger": "a", "source": "s1", "function": cfc.compound, "targets": "s2 s3", } t2 = {"trigger": "b", "source": "s2", "target": "final"} t3 = {"trigger": "b", "source": "s3", "target": "final"} stm = Machine(name="stm", transitions=[t0, t1, t2, t3], obj=None) _ = stmpy.get_graphviz_dot(stm) driver = Driver() driver.add_machine(stm) driver.start(keep_active=False) driver.send("a", "stm", args=["hi"], kwargs={"b1": "bbb"}) driver.send("b", "stm") driver.wait_until_finished()
def test(self): terminate = Terminate() t0 = {"source": "initial", "target": "s_1"} t1 = { "trigger": "t", "source": "s_1", "target": "s_2", "effect": "action" } stm_terminate = Machine(name="stm_terminate", transitions=[t0, t1], obj=terminate) terminate.stm = stm_terminate scheduler = Driver() scheduler.add_machine(stm_terminate) scheduler.start(max_transitions=2, keep_active=False) scheduler.send("t", "stm_terminate") scheduler.wait_until_finished() _ = stmpy.get_graphviz_dot(stm_terminate) _ = scheduler.print_status() self.assertTrue(True)
def __init__(self, driver: Driver, serverAPI: ServerAPI, py_audio: PyAudio): self.logger = logging.getLogger("WalkieTalkie") self.players = {} # userID -> audio player object self.serverAPI = serverAPI self.driver = driver self.py_audio = py_audio self.queue = [] self.max_current_priority = -1 MQTT_BROKER = 'mqtt.item.ntnu.no' MQTT_PORT = 1883 # create MQTT client self.logger.info( f'Connecting to MQTT broker {MQTT_BROKER} at port {MQTT_PORT}') self.mqtt_client = mqtt.Client() self.mqtt_client.on_connect = self.on_connect self.mqtt_client.on_message = self.on_message self.mqtt_client.connect(MQTT_BROKER, MQTT_PORT) self.mqtt_client.loop_start() self.update_subscriptions() # Create state machine self.state_machine = Machine(name="queue_manager", transitions=self._get_transitions(), states=self._get_states(), obj=self) driver.add_machine(self.state_machine)
def test(self): tick1 = EntryExitSelfLogic() t0 = {"source": "initial", "target": "s1"} t1 = { "trigger": "b", "source": "s1", "target": "s1", "effect": "add('b')" } t2 = { "trigger": "done", "source": "s1", "target": "final", "effect": "add('c')", } s1 = {"name": "s1", "do": "do_action('a')"} stm = Machine(name="stm", transitions=[t0, t1, t2], states=[s1], obj=tick1) tick1.stm = stm _ = stmpy.get_graphviz_dot(stm) driver = Driver() driver.add_machine(stm) driver.start() driver.wait_until_finished()
def test(self): t0 = { "source": "initial", "target": "s1", "effect": "start_timer('t1', 1000)", } t1 = { "trigger": "a", "source": "s1", "target": "s1", "effect": "stop_timer('t1')", } t2 = {"trigger": "b", "source": "s1", "target": "final"} stm = Machine(name="stm", transitions=[t0, t1, t2], obj=None) _ = stmpy.get_graphviz_dot(stm) driver = Driver() driver.add_machine(stm) driver.start(keep_active=False) driver.send("a", "stm") driver.send("b", "stm") driver.wait_until_finished()
def test(self): print(__name__) debug_level = logging.DEBUG logger = logging.getLogger(__name__) logger.setLevel(debug_level) ch = logging.StreamHandler() ch.setLevel(debug_level) formatter = logging.Formatter( "%(asctime)s - %(name)-12s - %(levelname)-8s - %(message)s") ch.setFormatter(formatter) logger.addHandler(ch) # terminate = Terminate() t0 = {"source": "initial", "target": "s1"} t1 = {"trigger": "b", "source": "s1", "target": "s2"} t2 = {"trigger": "a", "source": "s2", "target": "final"} s1 = {"name": "s1", "a": "defer", "a2": "defer", "a3": "defer"} s2 = {"name": "s2", "a2": "defer", "a3": "defer"} stm_terminate = Machine(name="stm", transitions=[t0, t1, t2], states=[s1, s2], obj=None) # terminate.stm = stm_terminate _ = stmpy.get_graphviz_dot(stm_terminate) print(_) def unwrap(queue): s = [] if queue is None: return s for event in queue: if event is not None: s.append(event["id"]) return s driver = Driver() driver.add_machine(stm_terminate) driver.start(max_transitions=30, keep_active=False) driver.send("a", "stm") driver.send("a2", "stm") driver.send("a3", "stm") print("Events {}".format(unwrap(driver._event_queue.queue))) print(stm_terminate.state) print("Defers {}".format(unwrap(stm_terminate._defer_queue))) print(driver._max_transitions) driver.send("b", "stm") print("Events {}".format(unwrap(driver._event_queue.queue))) print(stm_terminate.state) print("Defers {}".format(unwrap(stm_terminate._defer_queue))) print(driver._max_transitions) driver.wait_until_finished() print(stm_terminate.state) self.assertTrue(True)
def __init__(self, driver: Driver, py_audio: PyAudio): self.logger = logging.getLogger("WalkieTalkie") self.py_audio = py_audio self.state_machine = Machine( name="audio_player_" + str(id(self)), # Unique identifier for each audio player object transitions=self._get_transitions(), states=self._get_states(), obj=self) driver.add_machine(self.state_machine)
def __init__(self, mqttAPI: MqttAPI, driver: Driver, py_audio: PyAudio, serverAPI: ServerAPI): self.logger = logging.getLogger("WalkieTalkie") self.serverAPI = serverAPI # Define private variables self._recording = False # Save references self.mqttAPI = mqttAPI self.py_audio = py_audio # Create state machine self.state_machine = Machine(name="audio_recorder", transitions=self._get_transitions(), states=self._get_states(), obj=self) driver.add_machine(self.state_machine)
def test(self): busy = Busy() t0 = {"source": "initial", "target": "s_busy", "effect": "on_busy"} t1 = { "trigger": "busy", "source": "s_busy", "target": "s_busy", "effect": "on_busy", } stm_busy = Machine(name="busy", transitions=[t0, t1], obj=busy) busy.stm = stm_busy scheduler = Driver() scheduler.add_machine(stm_busy) scheduler.start(max_transitions=5) scheduler.wait_until_finished() self.assertTrue(True)
def test(self): t0 = {"source": "initial", "target": "s1"} t1 = { "trigger": "a", "source": "s1", "function": self.compound, "targets": "final", } stm = Machine(name="stm", transitions=[t0, t1], obj=None) _ = stmpy.get_graphviz_dot(stm) driver = Driver() driver.add_machine(stm) driver.start(keep_active=False) driver.send("a", "stm", args=["hi"], kwargs={"b1": "bbb"}) driver.wait_until_finished()
def test(self): two = TwoMethods() t0 = {"source": "initial", "target": "s_1"} t1 = { "trigger": "t", "source": "s_1", "target": "s_2", "effect": "m1;m2" } stm_two = Machine(name="stm_two", transitions=[t0, t1], obj=two) two.stm = stm_two scheduler = Driver() scheduler.add_machine(stm_two) scheduler.start(max_transitions=2) print("scheduler started") scheduler.send("t", "stm_two") scheduler.wait_until_finished() self.assertTrue(True)
def test(self): tick1 = EntryExitSelfLogic() t0 = {"source": "initial", "target": "s1"} t1 = { "trigger": "b", "source": "s1", "target": "s1", "effect": "add('b')" } t2 = { "trigger": "c", "source": "s1", "target": "final", "effect": "add('c')" } s1 = { "name": "s1", "a": "add('a')", "entry": "add('entry')", "exit": "add('exit')", } stm = Machine(name="stm", transitions=[t0, t1, t2], states=[s1], obj=tick1) tick1.stm = stm _ = stmpy.get_graphviz_dot(stm) driver = Driver() driver.add_machine(stm) driver.start(max_transitions=30, keep_active=False) driver.send("a", "stm") driver.send("b", "stm") driver.send("c", "stm") driver.wait_until_finished()
def test_tick(): logger = logging.getLogger("stmpy.Driver") logger.setLevel(logging.INFO) ch = logging.StreamHandler() ch.setLevel(logging.INFO) formatter = logging.Formatter( "%(asctime)s - %(name)s - %(levelname)s - %(message)s") ch.setFormatter(formatter) logger.addHandler(ch) scheduler = Driver() tick = Tick() t0 = {"source": "initial", "target": "s_tick", "effect": "on_init"} t1 = { "trigger": "tick", "source": "s_tick", "target": "s_tock", "effect": "on_tick", } t2 = { "trigger": "tock", "source": "s_tock", "target": "s_tick", "effect": "on_tock", } stm_tick = Machine(name="stm_tick", transitions=[t0, t1, t2], obj=tick) # the object may need the stm to add events and control timers tick.stm = stm_tick scheduler.add_machine(stm_tick) scheduler.start(max_transitions=3) scheduler.wait_until_finished()
raspi = RasPi() #TRANSITIONS #To the state where RasPi listens for signals from Beacon t0 = {'source': 'initial', 'target': 'receiver'} t1 = {'trigger': 't', 'source': 'receiver', 'target': 'transmitter'} t2 = {'trigger': 't', 'source': 'transmitter', 'target': 'receiver'} #STATES #The receiver state where RasPi listens for signals receiver = {'name': 'receiver', 'entry': 'listen'} #The transmitter state where RasPi transmit message to the mqtt-broker transmitter = {'name': 'transmitter', 'entry': 'send'} #STATE MACHINE machine = Machine(name='raspi', transitions=[t0, t1, t2], obj=raspi, states=[receiver, transmitter]) raspi.stm = machine #Setting up and starting the driver driver = Driver() driver.add_machine(machine) driver.start()
class WalkieTalkie: def __init__(self, transitions, states, debug): self.payload = {} self._logger = logging.getLogger(__name__) self._logger.info('logging under name {}.'.format(__name__)) self._logger.info('Starting Component') self.debug = debug self.app = None self.lock = Lock() self.recorder = Recorder(self) self.text_to_speech = Speaker() self.overwrote_last = False self.uuid = uuid4().hex if self.debug: self.uuid = "122ec9e8edda48f8a6dd290747acfa8c" self.channel = "{server}{uuid}".format(server=MQTT_TOPIC_BASE,uuid=self.uuid) self.name = "jonas" stm_walkie_talkie_name = "{}_walkie_talkie".format(self.name) walkie_talkie_machine = Machine(transitions=transitions, states=states, obj=self, name=stm_walkie_talkie_name) self.stm = walkie_talkie_machine recognizer_stm = get_state_machine('stm_recognizer', [stm_walkie_talkie_name]) self.stm_driver = Driver() self.stm_driver.add_machine(walkie_talkie_machine) self.stm_driver.add_machine(recognizer_stm) self.stm_driver.start() self._logger.debug('Component initialization finished') def create_gui(self): self.app = gui("Walkie Talkie", "320x568", bg='yellow') self.app.setStretch("both") self.app.setSticky("") self.app.setBgImage("images/bg.gif") if self.debug == True: self.app.setInPadding([30,40]) self.app.setPadding([0,50]) self.app.addLabel("status", "State: STATUS", 0, 0) self.app.setLabelBg("status", "#3e3e3e") self.app.setLabelFg("status", "white") def on_button_pressed_start(label): label = label.lower() command = label if 'stop' in label: self.stop_recording() command = "stop" elif 'send <' in label: self.stm.send("send", kwargs={'action': 'send', 'argument': 'bob ross'}) command = "send" elif 'replay <' in label: self.stm.send("replay", kwargs={'action': 'replay', 'argument': 'bob ross'}) command = "replay" elif 'replay' in label: self.stm.send("replay") command = "replay" elif 'next' in label: self.stm.send("next") command = "next" elif 'play' in label: self.stm.send("play") command = "play" print("[ACTION]:", command) print("[STATE]:", self.stm.state) if self.debug == True: self.app.setPadding([0,0]) self.app.setInPadding([60,40]) self.app.startLabelFrame("Debug panel",1,0) self.app.setStretch("both") self.app.setSticky("news") self.app.addButton('Send <name>', on_button_pressed_start) self.app.addButton('Stop recording', on_button_pressed_start) self.app.addButton('Play', on_button_pressed_start) self.app.addButton('Replay', on_button_pressed_start) self.app.addButton('Next', on_button_pressed_start) self.app.addButton('Replay <name>', on_button_pressed_start) self.app.stopLabelFrame() else: self.app.addLabel("padding", "", 1, 0) self.update_led(False) self.update_status('LISTENING') self.app.go() def on_init(self): # Create and start MQTT client on init client = MQTT_Client(self) self.mqtt_client = client.client # for publishing/subscribing to broker client.stm = self.stm client.start(MQTT_BROKER, MQTT_PORT) self.mqtt_client.subscribe(self.channel) print("{uuid}: listening on channel {channel}".format(uuid=self.uuid, channel=self.channel)) # Create GUI in a new thread th = Thread(target=self.create_gui) th.start() # Text-to-speech def tts(self, text): th = Thread(target=self.text_to_speech.speak, args=[str(text)]) th.start() self._logger.debug(text) def force_stop(self): if self.recorder.playing: self.recorder.force_stop() while not self.recorder.terminated: pass def register(self): msg = { "command":"register", "uuid":self.uuid, "name":self.name } json_msg = json.dumps(msg) self.mqtt_client.publish(MQTT_TOPIC_OUTPUT, json_msg) print(self.uuid) def query_server(self, **kwargs): # check if recipient/sender is registered if kwargs.get("argument") and kwargs.get("action"): msg = { "command":"query", "device_id_from":self.uuid, "recipient_name": kwargs.get("argument") } json_msg = json.dumps(msg) self.mqtt_client.publish(MQTT_TOPIC_OUTPUT, json_msg) else: self.stm.send("time_out") ''' request: {"device_id_from": uuid, "recipient_name": name, "command" : "query" } response: {"device_id_from": sender, "recipient_name": name, "exists": true/false} ''' def start_recording(self): self.update_status("RECORDING") self.recorder.record() def stop_recording(self): self.update_status("STOP RECORDING") self.recorder.stop() # Parses server responses def parse_message(self, payload): if payload.get('command') == "message": self.stm.send("save_message", args=[payload]) elif payload.get('exists') == True: # if recipient exists self.recipient = payload.get("recipient_name") self.stm.send("query_ok") elif payload.get('exists') == False: # if recipient does not exists self.stm.send("query_not_found") elif payload.get('data'): self.stm.send('replay_save_message', args=[payload]) def threaded_save(self, lock, payload): lock.acquire() try: sender_name = payload.get('device_owner_name_from') self.tts(f"Received message from {sender_name}") # Retreive message from payload wf = payload.get('data') data = base64.b64decode(wf) # Get queue length and saves message in the FIFO order queue_number = len(os.listdir("message_queue")) with open(f'message_queue/{queue_number}.wav', 'wb') as fil: fil.write(data) self._logger.debug(f'Message saved to /message_queue/{queue_number}.wav') except: self._logger.error(f'Payload could not be read!') lock.release() self.iterate_queue(False) def save_message(self, payload): th = Thread(target=self.threaded_save, args=[self.lock,payload]) th.start() th.join() def play_replay_message(self, payload): try: # Retreive message from payload wf = payload.get('data') data = base64.b64decode(wf) with open(f'replay_message.wav', 'wb') as fil: fil.write(data) self._logger.debug(f'Message saved to replay_message.wav') self.recorder.play("replay_message.wav") self.stm.send("replay_finished") except: # Should never happen, but added as insurance so the program doesn't throw an error and stops self._logger.error(f'Payload could not be read!') self.stm.send("replay_finished") def print_timer(self): print(self.stm.get_timer('time_out')) def play_message(self): self.update_status("PLAYING") self.overwrote_last = False # Check queue length queue_folder = "message_queue" queue_length = len(os.listdir(queue_folder)) if self.check_message_queue(1): self._logger.info(f'Playing message 1/{queue_length}!') self.recorder.play(f"{queue_folder}/1.wav") if not self.overwrote_last: self.stm.send('message_played') self.update_led(False, 1) else: self.stm.send("queue_empty") def load_next_message_in_queue(self): # Iterates queue in FIFO order deleting the first file and shifting the filenames to the left if self.check_message_queue(2): # if there are more than 2, it is safe to iterate self.iterate_queue(True, True) else: self.iterate_queue(True, True) self.stm.send("queue_empty") def check_message_queue(self, i): # returns true if there are more than i messages left in queue if len(os.listdir("message_queue")) > i: return True return False def threaded_iterate(self, lock, remove): lock.acquire() queue_folder = "message_queue" num = 1 listdir = os.listdir(queue_folder) listdir.sort() for filename in listdir: if filename.split(".")[0] == "1" and num == 1 and remove: os.remove(f"{queue_folder}/{filename}") else: if filename != ".gitkeep": os.rename(f"{queue_folder}/{filename}", f"{queue_folder}/{num}.wav") num += 1 self.update_led(False) lock.release() def iterate_queue(self, remove, force=False): if force: self.overwrite_current_playing() th = Thread(target=self.threaded_iterate, args=[self.lock, remove]) th.start() th.join() # Request replay message from the server def get_latest_user_message(self): self.update_status("REPLAYING") name = self.recipient uuid = self.uuid msg = { "device_id_from": uuid, "device_owner_name_to": name, "command":"replay", } json_msg = json.dumps(msg) self.mqtt_client.publish(MQTT_TOPIC_OUTPUT, json_msg) def send_data(self): filename = self.recorder.filename byte_data = open(filename, 'rb') data = base64.b64encode(byte_data.read()) msg = { "device_id_from":self.uuid, "device_owner_name_to": self.recipient, "command": "message", "data": data.decode() } json_msg = json.dumps(msg) self.mqtt_client.publish(MQTT_TOPIC_OUTPUT,json_msg) def update_status(self, text): if self.app != None: label = "State:"+text self.app.setLabel("status", label) def update_led(self, is_error, queue_pad=0): if self.app != None: if is_error: self.app.setBgImage("images/bg_red.gif") else: if self.check_message_queue(1+queue_pad): # check if there are more than 1 messages in queue self.app.setBgImage("images/bg_green.gif") else: self.app.setBgImage("images/bg.gif") def vibrate(self): self.recorder.play("vibrate.wav") self._logger.debug("Walkie goes brrrrrr...") def stop(self): # stop the MQTT client self.mqtt_client.loop_stop() # stop the state machine Driver self.stm_driver.stop() def overwrite_current_playing(self): self.overwrote_last = True self.force_stop()
logger.setLevel(debug_level) ch = logging.StreamHandler() ch.setLevel(debug_level) formatter = logging.Formatter( "%(asctime)s - %(name)-12s - %(levelname)-8s - %(message)s") ch.setFormatter(formatter) logger.addHandler(ch) print(stmpy.__version__) speaker = Speaker() t0 = {"source": "initial", "target": "ready"} t1 = {"trigger": "speak", "source": "ready", "target": "speaking"} t2 = {"trigger": "done", "source": "speaking", "target": "ready"} s1 = {"name": "speaking", "do": "speak(*)", "speak": "defer"} stm = Machine(name="stm", transitions=[t0, t1, t2], states=[s1], obj=speaker) speaker.stm = stm driver = Driver() driver.add_machine(stm) driver.start() driver.send("speak", "stm", args=["My first sentence."]) driver.send("speak", "stm", args=["My second sentence."]) driver.send("speak", "stm", args=["My third sentence."]) driver.send("speak", "stm", args=["My fourth sentence."]) driver.wait_until_finished()
def __init__(self, plant_name, treshhold): self.sense = SenseHat() self._logger = logging.getLogger(__name__) logging.basicConfig(level=logging.INFO) print('logging under name {}.'.format(__name__)) self._logger.info('Starting humiditychecker') self.plant_name = plant_name self.treshhold = treshhold self.watering_machine = WateringMachine(plant_name, self) self.sense.show_message("Hello<3", text_colour=green) t0 = {'source': 'initial', 'target': 'check_idle'} t1 = { 'trigger': 't', 'source': 'check_idle', 'function': self.water_checking } t2 = { 'trigger': 'watering_done', 'source': 'watering_plant', 'effect': 'stop_timer("fallback");logg("Watering done"); ', 'target': 'check_idle' } t3 = { 'trigger': 'fallback', 'source': 'watering_plant', 'effedt': 'logg("State: check_idle");', 'target': 'check_idle' } check_idle = {'name': 'check_idle', 'entry': 'start_timer("t",4000);'} watering_plant = { 'name': 'watering_plant', 'entry': 'start_timer("fallback",20000);sendToDriver("water","Watering");logg("State: watering_plant")' } humidity_machine = Machine(transitions=[t0, t1, t2, t3], obj=self, states=[check_idle, watering_plant], name='humidityCheck') self.stm = humidity_machine broker, port = MQTT_BROKER, MQTT_PORT driver = Driver() driver.add_machine(self.stm) self.driver = driver myclient = MQTT_Client_1(driver, self, MQTT_BROKER, MQTT_PORT, self.plant_name) self.mqtt = myclient self.mqtt_client = myclient.client myclient.stm = self.stm myclient.stm_driver = driver self.driver.add_machine(self.watering_machine.stm) self.airhumid = AirHumidity(self.plant_name, self.mqtt) self.driver.add_machine(self.airhumid.stm) driver.start() myclient.start(broker, port)
class AudioHelper: def __init__(self): self.recorder = Recorder() t0_r = {'source': 'initial', 'target': 'ready'} t1_r = { 'trigger': 'start_recording', 'source': 'ready', 'target': 'recording' } t2_r = {'trigger': 'done', 'source': 'recording', 'target': 'ready'} s_ready = {'name': 'ready'} s_recording = { 'name': 'recording', 'do': 'record()', "stop": "stop_recording()" } self.stm_recording = Machine(name='stm_recording', transitions=[t0_r, t1_r, t2_r], states=[s_ready, s_recording], obj=self.recorder) self.recorder.stm = self.stm_recording self.speaker = Speaker() t0_s = {'source': 'initial', 'target': 'ready'} t1_s = {'trigger': 'speak', 'source': 'ready', 'target': 'speaking'} t2_s = {'trigger': 'done', 'source': 'speaking', 'target': 'ready'} s1_s = {'name': 'speaking', 'do': 'speak(*)', 'speak': 'defer'} self.stm_speaker = Machine(name='stm_speaker', transitions=[t0_s, t1_s, t2_s], states=[s1_s], obj=self.speaker) self.speaker.stm = self.stm_speaker self.driver = Driver() self.driver.add_machine(self.stm_recording) self.driver.add_machine(self.stm_speaker) self.driver.start() print('Audio Module ready') def play_audio_noStm(self, filename): # Open the sound file wf = wave.open(filename, 'rb') # Create an interface to PortAudio p = pyaudio.PyAudio() # Open a .Stream object to write the WAV file to # 'output = True' indicates that the sound will be played rather than recorded stream = p.open(format=p.get_format_from_width(wf.getsampwidth()), channels=wf.getnchannels(), rate=wf.getframerate(), output=True) # Read data in chunks data = wf.readframes(CHUNK) #self.playing = True # Play the sound by writing the audio data to the stream while (data != b''): #and self.playing: stream.write(data) data = wf.readframes(CHUNK) # Close and terminate the stream stream.close() p.terminate() def start_recording(self): #print("driver started") self.last_record = [] self.stm_recording.send('start_recording') def stop_recording(self): self.stm_recording.send("stop") def get_tmp_filename(self): #Returns the filename that is used for temp storage return FILENAME def get_recorded_samples(self): return b''.join(self.stm_recording._obj.getFrames()) def text_to_speech(self, text): self.stm_speaker.send('speak', args=[text])
class WalkieTalkie: t0 = {'source': 'initial', 'target': 'idle'} t1 = {'trigger': 'message', 'source': 'idle', 'target': 'play_message'} t2 = { 'trigger': 'cancel_btn', 'source': 'play_message', 'target': 'idle', 'effect': 'stop_playing()' } t3 = { 'trigger': 'message_played', 'source': 'play_message', 'target': 'idle', } t4 = { 'trigger': 'join_btn', 'source': 'idle', 'target': 'join_group', 'effect': 'join_group_f(*)' } t5 = { 'trigger': 'error_message', 'source': 'join_group', 'target': 'error', } t6 = { 'trigger': 'subscribed', 'source': 'join_group', 'target': 'idle', } t7 = { 'trigger': 'leave_btn', 'source': 'idle', 'target': 'leave_group', 'effect': 'leave_group_f(*)' } t8 = { 'trigger': 'error_message', 'source': 'leave_group', 'target': 'error', } t9 = { 'trigger': 'unsubscribed', 'source': 'leave_group', 'target': 'idle', } t10 = { 'trigger': 'recipient_btn', 'source': 'idle', 'target': 'select_group', 'effect': 'choose_recipient_group(*)' } t11 = { 'trigger': 'leave_recipient_btn', 'source': 'idle', 'target': 'select_group', 'effect': 'remove_recipient_group(*)' } t12 = { 'trigger': 't1', 'source': 'select_group', 'target': 'idle', } t13 = { 'trigger': 'cancel_btn', 'source': 'select_group', 'target': 'idle', } t14 = { 'trigger': 'record_btn', 'source': 'idle', 'target': 'record_message', } t15 = { 'trigger': 'cancel_btn', 'source': 'record_message', 'target': 'idle', } t16 = { 'trigger': 'record_btn', 'source': 'select_group', 'target': 'record_message', } t17 = { 'trigger': 'recording_saved', 'source': 'record_message', 'target': 'send_message', } t18 = { 'trigger': 'message_sent', 'source': 'send_message', 'target': 'idle', } t19 = { 'trigger': 'error_message', 'source': 'idle', 'target': 'error', } t20 = { 'trigger': 'error_message', 'source': 'select_group', 'target': 'error', } t21 = { 'trigger': 'error_message', 'source': 'record_message', 'target': 'error', } t22 = { 'trigger': 'error_message', 'source': 'send_message', 'target': 'error', } t24 = { 'trigger': 'connection_ok', 'source': 'error', 'target': 'idle', } t25 = { 'trigger': 't2', 'source': 'error', 'target': 'error', } t23 = { 'trigger': 'error_message', 'source': 'play_message', 'target': 'error', } #states idle = {'name': 'idle', 'entry': 'idle_state'} play_message = { 'name': 'play_message', 'entry': 'play_message_f', 'message': 'defer', } join_group = {'name': 'join_group', 'message': 'defer'} leave_group = {'name': 'leave_group', 'message': 'defer'} select_group = { 'name': 'select_group', 'entry': 'start_timer("t1", 1000)', 'message': 'defer' } record_message = { 'name': 'record_message', 'entry': 'record_message_f', 'message': 'defer', } send_message = { 'name': 'send_message', 'entry': 'send_message_f', 'message': 'defer' } error = { 'name': 'error', 'entry': 'test_connection; start_timer("t2", 3000)' } def __init__(self): #MQTT self.MQTT_BROKER = 'mqtt.item.ntnu.no' self.MQTT_PORT = 1883 self.topic_output = 'ttm4115/team_12/file' self.group_topics_base = 'ttm4115/team_12/groups/' self.voice_file_name = 'output.wav' self.message_file_name_base = 'input.wav' self.joined_groups = [] self.recipient_groups = [] self.all_groups = { "Doctors": False, "Nurses": False, "Surgeons": False, "Head Surgeon": False, "Janitors": False } self.recording = False #State machine self.stm = Machine(name='stm', transitions=[ self.t0, self.t1, self.t2, self.t3, self.t4, self.t5, self.t6, self.t7, self.t8, self.t9, self.t10, self.t11, self.t12, self.t13, self.t14, self.t15, self.t16, self.t17, self.t18, self.t19, self.t20, self.t21, self.t21, self.t22, self.t23, self.t24, self.t25 ], states=[ self.idle, self.play_message, self.join_group, self.leave_group, self.select_group, self.record_message, self.send_message, self.error ], obj=self) self.driver = Driver() self.driver.add_machine(self.stm) self.driver.start() #Voice recording self.Recorder = Recorder(self.driver) #Message playing self.player = Player(self.driver) #File sending self.FileSender = FileSenderComponent(self.driver, self.MQTT_BROKER, self.MQTT_PORT) #File receiving self.FileReceiver = FileReceiverComponent(self.driver, self.MQTT_BROKER, self.MQTT_PORT) #Errors self.error_message = 'ERROR: Connection lost' self.message_index = 0 self.create_gui() def create_gui(self): self.app = gui() self.app.setSize(600, 620) self.app.setBg('white', override=False, tint=False) self.app.startFrame("record", row=0, column=0) self.app.startLabelFrame('Record Message') self.app.addButton('Record', self.record_button) self.app.addButton('Save and Send recording', self.stop_recording) self.app.stopLabelFrame() self.app.stopFrame() self.app.startFrame("cancel", row=0, column=1) self.app.startLabelFrame('Cancel') self.app.addButton('Cancel', self.cancel_button) self.app.stopLabelFrame() self.app.stopFrame() self.app.startFrame("join_groups", row=20, column=0) self.app.startLabelFrame('Join Groups') self.app.addButton('Join Doctors', self.on_button_pressed_join_groups) self.app.addButton('Join Nurses', self.on_button_pressed_join_groups) self.app.addButton('Join Surgeons', self.on_button_pressed_join_groups) self.app.addButton('Join Important Information', self.on_button_pressed_join_groups) self.app.addLabel("joined_groups_title", "Joined Groups") self.app.addLabel("No Joined Groups") self.app.stopLabelFrame() self.app.stopFrame() self.app.startFrame("choose_recipient", row=40, column=0) self.app.startLabelFrame('Choose Recipient Group') self.app.addButton('Send to Doctors', self.on_button_pressed_recipient_group) self.app.addButton('Send to Nurses', self.on_button_pressed_recipient_group) self.app.addButton('Send to Surgeons', self.on_button_pressed_recipient_group) self.app.addButton('send to Important', self.on_button_pressed_recipient_group) self.app.addLabel("recipient_groups_title", "Recipient Groups") self.app.addLabel("No Recipient Groups") self.app.stopLabelFrame() self.app.stopFrame() self.app.startFrame("leave_group", row=20, column=1) self.app.startLabelFrame('Leave Groups') self.app.addButton('Leave Doctors', self.on_button_pressed_leave_groups) self.app.addButton('Leave Nurses', self.on_button_pressed_leave_groups) self.app.addButton('Leave Surgeons', self.on_button_pressed_leave_groups) self.app.addButton(' Leave Important information', self.on_button_pressed_leave_groups) self.app.stopLabelFrame() self.app.stopFrame() self.app.startFrame("remove_recipient", row=40, column=1) self.app.startLabelFrame('Remove Recipient Groups') self.app.addButton('Remove Doctors', self.on_button_pressed_remove_groups) self.app.addButton('Remove Nurses', self.on_button_pressed_remove_groups) self.app.addButton('Remove Surgeons', self.on_button_pressed_remove_groups) self.app.addButton('Remove Important Information', self.on_button_pressed_remove_groups) self.app.stopLabelFrame() self.app.stopFrame() self.app.startFrame("error_display", row=60, column=1) self.app.startLabelFrame('Error Display') self.app.addLabel("error_label", "No errors") self.app.addButton('Simulate connection lost', self.simulate_connection_lost) self.app.stopLabelFrame() self.app.stopFrame() self.app.go() def record_button(self): if len(self.recipient_groups) == 0: print("No recipient groups to send to") return self.recording = True self.driver.send('record_btn', 'stm') def cancel_button(self): #self.player.stop_playing_sound() self.driver.send('cancel_btn', 'stm') def stop_playing(self): self.player.stop_playing_sound() def on_button_pressed_join_groups(self, buttonTitle): group_name = buttonTitle.lower() if 'doctors' in group_name: group_name = 'doctors' elif 'nurses' in group_name: group_name = 'nurses' elif 'surgeons' in group_name: group_name = 'surgeons' elif 'important' in group_name: group_name = 'important' #self.join_group(group_name) if group_name not in self.joined_groups: self.driver.send('join_btn', 'stm', args=[group_name]) else: pass def on_button_pressed_leave_groups(self, buttonTitle): group_name = buttonTitle.lower() if 'doctors' in group_name: group_name = 'doctors' elif 'nurses' in group_name: group_name = 'nurses' elif 'surgeons' in group_name: group_name = 'surgeons' elif 'important' in group_name: group_name = 'important' #self.leave_group(group_name) if group_name in self.joined_groups: self.driver.send('leave_btn', 'stm', args=[group_name]) else: pass def on_button_pressed_recipient_group(self, buttonTitle): group_name = buttonTitle.lower() if 'doctors' in group_name: group_name = 'doctors' elif 'nurses' in group_name: group_name = 'nurses' elif 'surgeons' in group_name: group_name = 'surgeons' elif 'important' in group_name: group_name = 'important' #self.choose_recipient_group(group_name) self.driver.send('recipient_btn', 'stm', args=[group_name]) def on_button_pressed_remove_groups(self, buttonTitle): group_name = buttonTitle.lower() if 'doctors' in group_name: group_name = 'doctors' elif 'nurses' in group_name: group_name = 'nurses' elif 'surgeons' in group_name: group_name = 'surgeons' elif 'important' in group_name: group_name = 'important' #self.remove_recipient_group(group_name) self.driver.send('leave_recipient_btn', 'stm', args=[group_name]) def set_record_button_text(self): if self.recording: self.app.setButton('Record', 'Stop and Send') else: self.app.setButton('Record', 'Record') def simulate_connection_lost(self): print('Simulating connection lost') self.FileSender.disconnect() def play_message_f(self): print("Main state: Play message") next_file_name = 'input{}.wav'.format(self.message_index) self.player.play_sound_file(next_file_name) self.message_index += 1 def record_message_f(self): print("Main state: Record message") self.Recorder.start_recording() def idle_state(self): print("Main state: Idle") if self.recording: self.Recorder.stop_recording() self.recording = False self.set_record_button_text() def send_message_f(self): print("Main state: Send message") for group in self.recipient_groups: group_topic = '{0}{1}'.format(self.group_topics_base, group) self.FileSender.send_file(self.voice_file_name, group_topic) def stop_recording(self): self.Recorder.stop_recording() self.recording = False self.set_record_button_text() def join_group_f(self, groupName): if not groupName in self.joined_groups: print("joining group: {}".format(groupName)) self.FileReceiver.subscribe_to_topic('{0}{1}'.format( self.group_topics_base, groupName)) self.joined_groups.append(groupName) self.app.setLabel("No Joined Groups", ', '.join(self.joined_groups)) def choose_recipient_group(self, groupName): if not groupName in self.recipient_groups: self.recipient_groups.append(groupName) print("Choosing new recipient group: {}".format(groupName)) self.app.setLabel("No Recipient Groups", ', '.join(self.recipient_groups)) def remove_recipient_group(self, groupName): if groupName in self.recipient_groups: print("Removing group: {}".format(groupName)) self.recipient_groups.remove(groupName) self.app.setLabel("No Recipient Groups", ', '.join(self.recipient_groups)) def leave_group_f(self, groupName): if groupName in self.joined_groups: print("Leaving group: {}".format(groupName)) self.FileReceiver.unsubscribe_from_topic('{0}{1}'.format( self.group_topics_base, groupName)) self.joined_groups.remove(groupName) self.app.setLabel("No Joined Groups", ', '.join(self.joined_groups)) def test_connection(self): print('Testing connection') if self.FileReceiver.connected and self.FileSender.connected: self.driver.send('connection_ok', 'stm') self.app.setLabel("error_label", 'No errors') self.app.setLabelBg("error_label", 'white') print('Connection ok') else: self.app.setLabel("error_label", self.error_message) self.app.setLabelBg("error_label", 'red') print('Connection lost, resetting components and reconnecting') self.FileReceiver = FileReceiverComponent(self.driver, self.MQTT_BROKER, self.MQTT_PORT) self.FileSender = FileSenderComponent(self.driver, self.MQTT_BROKER, self.MQTT_PORT)
class BikeRack: def __init__(self, name, mqtt_broker, mqtt_port): """ Start the component. ## Start of MQTT We subscribe to the topic(s) the component listens to. The client is available as variable `self.client` so that subscriptions may also be changed over time if necessary. The MQTT client reconnects in case of failures. ## State Machine driver We create a single state machine driver for STMPY. This should fit for most components. The driver is available from the variable `self.driver`. You can use it to send signals into specific state machines, for instance. """ # TODO Make the mqtt topics into bike/$name/command (input) and bike/$name (output). # Something wrong happened trying to do so. self.MQTT_TOPIC_INPUT = 'bike/' #, name, '/command' self.MQTT_TOPIC_OUTPUT = 'bike/' #, name # Get the logger object for the component self._logger = logging.getLogger(__name__) print('Logging under name {}.'.format(__name__)) # ::: DEBUGGING ::: # logging.DEBUG: Most fine-grained logging, printing everything # logging.INFO: Only the most important informational log items # logging.WARN: Show only warnings and errors. # logging.ERROR: Show only error messages. debug_level = logging.DEBUG logger = logging.getLogger(__name__) logger.setLevel(debug_level) ch = logging.StreamHandler() ch.setLevel(debug_level) formatter = logging.Formatter( '%(asctime)s - %(name)-12s - %(levelname)-8s - %(message)s') ch.setFormatter(formatter) logger.addHandler(ch) # END DEBUGGING self._logger.info('Starting Component') # Create a new MQTT client self._logger.debug('Connecting to MQTT broker {} at port {}'.format( mqtt_broker, mqtt_port)) self.mqtt_client = mqtt.Client() # Callback methods self.mqtt_client.on_connect = self.on_connect self.mqtt_client.on_message = self.on_message # Connect to the broker self.mqtt_client.connect(mqtt_broker, mqtt_port) # Subscribe to proper topic(s) of your choice self.mqtt_client.subscribe(self.MQTT_TOPIC_INPUT) # Start the internal loop to process MQTT messages self.mqtt_client.loop_start() # We start the stmpy driver, without any state machines for now self.driver = Driver() self.driver.start(keep_active=True) self._logger.debug('Component initialization finished') # Active machines self.active_machines = {} self.name = name # Add test_lock lock_name = "en" self._logger.debug(f'Create machine with name: {lock_name}') lock_stm = BikeLock(self.driver, self, lock_name) self.driver.add_machine(lock_stm.stm) self.active_machines[lock_name] = lock_name self._logger.debug("Start driver") self.driver.start() # TEST END def stop(self): """ Stop the component. """ # Stop the MQTT client self.mqtt_client.loop_stop() # Stop the state machine Driver self.driver.stop() def on_connect(self, client, userdata, flags, rc): # We just log that we are connected self._logger.debug('MQTT connected to {}'.format(client)) def check_available(self): for name in self.active_machines: if self.driver._stms_by_id[name].state == "available": return True def on_message(self, client, userdata, msg): """ Processes incoming MQTT messages. We assume the payload of all received MQTT messages is an UTF-8 encoded string, which is formatted as a JSON object. The JSON object contains a field called `command` which identifies what the message should achieve. As a reaction to a received message, we can for example do the following: * create a new state machine instance to handle the incoming messages, * route the message to an existing state machine session, * handle the message right here, * throw the message away. """ self._logger.debug('Incoming message to topic {}'.format(msg.topic)) payload = json.loads(msg.payload) command = payload.get('command') self._logger.debug(f"Have detected this command: {command}") if command == "check_driver": self._logger.debug(f"State Machine: {self.driver.print_status()}") if self.check_available(): self.mqtt_client.publish(self.MQTT_TOPIC_OUTPUT, self.driver.print_status()) # Assumes payload with ``lock_name`` and ``nfc_tag`` elif command == "reserve": for name in self.active_machines: if self.driver._stms_by_id[name].state == "available": self._logger.debug(f"Reserving lock with id: {name}") kwargs = {"nfc_tag": payload.get("value")} self.driver.send(message_id='reserve', stm_id=name, kwargs=kwargs) self.mqtt_client.publish( self.MQTT_TOPIC_OUTPUT, f'Reserved lock with name {name}') self.mqtt_client.publish( self.get_stm_by_name(name)._obj.get_nfc_tag()) self._logger.debug( self.get_stm_by_name(name)._obj.get_nfc_tag()) return self._logger.debug("No locks available in this rack") self.mqtt_client.publish(self.MQTT_TOPIC_OUTPUT, f'No locks available') elif command == "add_lock": lock_name = payload.get("lock_name") self._logger.debug(f"Add lock with name: {lock_name}") lock_stm = BikeLock(self.driver, self, lock_name) self.driver.add_machine(lock_stm.stm) self.active_machines[lock_name] = lock_name # Assumes payload with``nfc_tag`` and ``lock_name`` elif command == "nfc_det": self._logger.debug("running nfc_det") self.nfc_det(nfc_tag=payload.get("value"), lock_name=payload.get("lock_name")) elif command == "check_state": name = payload.get("name") self._logger.debug( f"Machine: {name}, is in state: {self.get_stm_by_name(name).state}" ) self.mqtt_client.publish( self.MQTT_TOPIC_OUTPUT, f"Machine: {name}, is in state: {self.get_stm_by_name(name).state}" ) # Catch message without handler else: self._logger.debug(f"Command: {command} does not have a handler") def res_expired(self, nfc_tag): self.mqtt_client.publish(self.MQTT_TOPIC_OUTPUT, f'Reservetion timed out for {nfc_tag}') def nfc_det(self, nfc_tag, lock_name): self._logger.debug( f"Detected NFC-tag with value: {nfc_tag} presented to lock: {lock_name}" ) self._logger.debug(self.get_stm_by_name(lock_name).state) kwargs = {"nfc_tag": nfc_tag} self.driver.send(message_id='nfc_det', stm_id=lock_name, kwargs=kwargs) # Getter for stm_by name def get_stm_by_name(self, stm_name): if self.driver._stms_by_id[stm_name]: self._logger.debug(f"Getting stm with name: {stm_name}") return self.driver._stms_by_id[stm_name] # Did not find machine with ``stm_name`` self._logger.error(f"Error: did not find stm with name: {stm_name}") return None
def test(self): # print(stmpy.__version__) logger = logging.getLogger("stmpy") logger.setLevel(logging.DEBUG) ch = logging.StreamHandler() ch.setLevel(logging.DEBUG) formatter = logging.Formatter( "%(asctime)s - %(name)s - %(levelname)s - %(message)s") ch.setFormatter(formatter) logger.addHandler(ch) tick1 = Tick() t0 = { "source": "initial", "target": "active", "effect": "start_timer('tick', 1000); print('initial1')", } #'effect': 'print("initial1")'} t1 = { "trigger": "tick", "source": "active", "target": "active", "effect": "start_timer('tick', 1000); print('timeout1')", } #'effect': 'print("timeout1")'} stm_tick_1 = Machine(name="stm_tick_1", transitions=[t0, t1], obj=tick1) tick1.stm = stm_tick_1 tick2 = Tick() t0 = { "source": "initial", "target": "active", "effect": "start_timer('tick', 2000); print('initial2')", } #'effect': 'print("initial2")'} t1 = { "trigger": "tick", "source": "active", "target": "active", "effect": "start_timer('tick', 1000); print('timeout2')", } stm_tick_2 = Machine(name="stm_tick_2", transitions=[t0, t1], obj=tick2) tick2.stm = stm_tick_2 driver1 = Driver() driver1.start(max_transitions=6, keep_active=True) print("driver state: active {} and thread alive {} ".format( driver1._active, driver1.thread.is_alive())) driver1.add_machine(stm_tick_1) print(driver1.print_status()) driver1.add_machine(stm_tick_2) print(driver1.print_status()) driver1._wake_queue() print("driver state: active {} and thread alive {} ".format( driver1._active, driver1.thread.is_alive())) # driver1.start(max_transitions=6, keep_active=True) print(driver1.print_status()) # driver2 = Driver() # driver1.add_machine(stm_tick_2) # driver2.start(max_transitions=10) driver1.wait_until_finished()
class WalkieTalkie: """ The component to send and receive voice messages. """ def __init__(self): # setting the standard channel as 0 and ID as default self.channel = 0 self.ID = "default" # the output dir is where received recordings are stored self.output_dir = "../player/" self.record_dir = "../recordings/" self.channel_dir = self.output_dir + str(self.channel) self.fileNameList = [] self.messageList = [] # cleaing the player list self.create_channel_folder(self.output_dir, self.record_dir) #Burde vi ha create_player_folder for konsistent?? self.clear_player_folder(self.output_dir) # get the logger object for the component self._logger = logging.getLogger(__name__) print('logging under name {}.'.format(__name__)) self._logger.info('Starting Component') # create a new MQTT client self._logger.debug('Connecting to MQTT broker {} at port {}'.format(MQTT_BROKER, MQTT_PORT)) self.mqtt_client = mqtt.Client() # callback methods self.mqtt_client.on_connect = self.on_connect self.mqtt_client.on_message = self.on_message self.mqtt_client.on_disconnect = self.on_disconnect # Connect to the broker try: self.mqtt_client.connect(MQTT_BROKER, MQTT_PORT) except: print("Connection fails") sys.exit(1) self.mqtt_client.loop_start() ''' #Testing the on_disconnect function time.sleep(10) self.mqtt_client.disconnect() # disconnect gracefully self.mqtt_client.loop_stop() # stops network loop time.sleep(5) self.mqtt_client.connect() ''' # recorder recorder = Recorder.create_machine('stm_recorder', self) self.recorder = recorder stm_recorder = recorder.stm # player player = Player.create_machine('stm_player', self) self.player = player stm_player = player.stm # creating driver, attaching machines self.driver = Driver() self.driver.add_machine(stm_recorder) self.driver.add_machine(stm_player) # starting driver self.driver.start(keep_active = True) self.create_gui() print("Bye!") def create_channel_folder(self, output_dir, record_dir): if not os.path.exists(output_dir): os.mkdir(output_dir) if not os.path.exists(record_dir): os.mkdir(record_dir) for i in range(MAX_CHANNELS): path = output_dir + str(i) if not os.path.exists(path): os.mkdir(path) def clear_player_folder(self, output_dir): for i in range(MAX_CHANNELS): for f in os.listdir(output_dir + str(i)): if f.endswith(".wav"): os.remove(os.path.join(output_dir+str(i), f)) def set_channel_path(self): self.channel_dir=self.output_dir +str(self.channel) def on_connect(self, client, userdata, flags, rc): print(mqtt.connack_string(rc)) if(rc == 0): self.mqtt_client.subscribe(MQTT_TOPIC_INPUT + str(self.channel)) self.mqtt_client.subscribe(MQTT_TOPIC_INPUT+ str(self.channel)+"/ACK") self._logger.debug('MQTT connected to {}'.format(client)) self.client_id = client else: print(mqtt.connack_string(rc)) def on_disconnect(self, client, userdata, rc): if(rc == 0): print("Disconnected gracefully.") else: print("Unexpected disconnection.") self.app.setLabel("delivered", text = "Connection lost: Waiting to reconnect \n and resend latest message") # Runs when WalkieTalkie receives a message def on_message(self, client, userdata, msg): print("A message is received") self._logger.debug('Incoming message to topic {}'.format(msg.topic)) #message_payload_received = json.load(io.BytesIO(msg.payload)) if(msg.payload): message_payload_received = json.loads(msg.payload) # Check correct channel if(str(msg.topic) == MQTT_TOPIC_OUTPUT + str(self.channel) and message_payload_received): dataToByteArray = base64.b64decode(bytearray(bytes(message_payload_received['data'], "utf-8"))) print("client_id: " + message_payload_received['ID']) # Check that message is not sent to self if (message_payload_received['ID'] != self.ID): temp_file = message_payload_received['ID'] + str(strftime(" %Y-%m-%d %H-%M-%S", gmtime())) + ".wav" self.temp_file = temp_file f = open(os.path.join(self.channel_dir, self.temp_file), 'wb') f.write(dataToByteArray) print("Data written to file") f.close() self.driver.send('start', 'stm_player', args=[os.path.join(self.channel_dir, self.temp_file)]) time.sleep(1) self.messageList = [ Message(path) for path in os.listdir(self.channel_dir) if path.endswith(".wav") ] self.fileNameList = [ m.path for m in self.messageList] print(self.fileNameList) self.app.changeOptionBox("Choose message", self.fileNameList) # Sending ack package_ack = {'message_id': message_payload_received['Msg_ID'], 'sender': message_payload_received['ID']} payload_ack = json.dumps(package_ack) self.mqtt_client.publish(str(msg.topic)+"/ACK", payload_ack, qos=2) # Checks for ACK if (str(msg.topic) == MQTT_TOPIC_INPUT+ str(self.channel)+"/ACK"): if(message_payload_received['message_id'] == self.recorder.get_latest_file()): if(message_payload_received['sender'] == self.ID): print("Message delivered with ID: "+ message_payload_received['message_id'] + " and sender: " + message_payload_received['sender']) self.app.setLabel("delivered","Message delivered") self.app.setLabelFg("delivered","green") def send_message(self): print("Sending a new message") #self.mqtt_client.connect(MQTT_BROKER, MQTT_PORT) path = self.recorder.get_latest_file() f = open(path, "rb") imagestring = f.read() f.close() imageByteArray = bytearray(imagestring) imageByteArrayString = str(base64.b64encode(imageByteArray), "utf-8") package = {'ID': self.ID, 'data': imageByteArrayString, 'Msg_ID': path} payload = json.dumps(package) mqtt_msg = self.mqtt_client.publish(MQTT_TOPIC_OUTPUT + str(self.channel), payload, qos = 2) timestamp = time.time() print("Sending the message took: {} ".format(time.time()-timestamp)) self.app.setLabel("delivered",text = "Sending") self.app.setLabelFg("delivered","orange") time.sleep(1) # catching the exception thrown by mqtt when no acc is given. ## TODO: Her kan vi kanskje ha Message failed rød tekst? Hvis Catch error. # Creates the appJar GUI def create_gui(self): BUTTON_WIDTH = 30 self.app = gui("Walkie-Talkie", "300x500") #set username def on_button_name(title): self.ID = self.app.getEntry("NameEntry") self.app.setLabel("NameLabel", "User: "******"User ID changed") #channel up def on_button_pressed_increase(title): self.mqtt_client.unsubscribe(MQTT_TOPIC_INPUT + str(self.channel)) self.mqtt_client.unsubscribe(MQTT_TOPIC_INPUT+ str(self.channel)+"/ACK") self.channel = (self.channel + 1)% MAX_CHANNELS self.set_channel_path() self.mqtt_client.subscribe(MQTT_TOPIC_INPUT + str(self.channel)) self.mqtt_client.subscribe(MQTT_TOPIC_INPUT+ str(self.channel)+"/ACK") self.app.setLabel("Channel",text="Connected to channel: {}".format(self.channel)) #channel up def on_button_pressed_decrease(title): self.mqtt_client.unsubscribe(MQTT_TOPIC_INPUT + str(self.channel)) self.mqtt_client.unsubscribe(MQTT_TOPIC_INPUT+ str(self.channel)+"/ACK") self.channel = (self.channel - 1) % MAX_CHANNELS self.set_channel_path() self.mqtt_client.subscribe(MQTT_TOPIC_INPUT + str(self.channel)) self.mqtt_client.subscribe(MQTT_TOPIC_INPUT+ str(self.channel)+"/ACK") self.app.setLabel("Channel",text="Connected to channel: {}".format(self.channel)) #start recording def on_button_pressed_start(title): self.driver.send('start', 'stm_recorder') print("Start recording") #Stop recording and send message def on_button_pressed_stop(title): self.driver.send('stop', 'stm_recorder') time.sleep(1) self.send_message() print("Stop recording") #resend latest message def on_button_pressed_resend(title): if os.listdir(self.record_dir) != []: self.send_message() else: print("You have no messages. ") #Replay chosen message def on_button_pressed_replay(title): play_list = self.fileNameList if play_list: tmp = self.app.getOptionBox('Choose message') self.driver.send('replay', 'stm_player', args=[os.path.join(self.channel_dir, tmp)]) else: print("You have no messages. ") def voiceToText(title): play_list = self.fileNameList if play_list: tmp = self.app.getOptionBox('Choose message') r = sr.Recognizer() lyd=sr.AudioFile(os.path.join(self.channel_dir, tmp)) with lyd as source: audio = r.record(source) try: s = r.recognize_google(audio) self.app.setLabel("message","Message: " + s) except Exception as e: print("Exception: "+str(e)) else: print("You have no messages. ") # Choose ID self.app.addLabel("NameLabel", "User: "******"Names") self.app.addLabel("NameEntryLabel", "Name: ", 1, 0) self.app.addEntry("NameEntry", 1, 1) self.app.setEntrySubmitFunction("NameEntry", on_button_name) self.app.stopLabelFrame() # Choose channel self.app.startLabelFrame('Change channel:') self.app.addLabel("Channel",text="Connected to channel: {}".format(self.channel), colspan=2) self.app.setLabelWidth('Channel', int(BUTTON_WIDTH*(5/3))) self.app.addButton('Increase', on_button_pressed_increase, 1, 0) self.app.setButtonWidth('Increase', BUTTON_WIDTH) self.app.addButton('Decrease', on_button_pressed_decrease, 1 , 1) self.app.setButtonWidth('Decrease', BUTTON_WIDTH) self.app.stopLabelFrame() # Start and stop recording self.app.startLabelFrame('Send messages') self.app.addButton('Start recording', on_button_pressed_start, 1, 0) self.app.setButtonWidth("Start recording", BUTTON_WIDTH) self.app.addButton('Stop and send', on_button_pressed_stop, 1, 1) self.app.setButtonWidth('Stop and send', BUTTON_WIDTH) #resend and exit button self.app.addButton('Resend', on_button_pressed_resend, colspan=2) self.app.setButtonWidth('Resend', BUTTON_WIDTH*2) self.app.addButton('Exit system', sys.exit, colspan=3) self.app.setButtonWidth('Exit system', BUTTON_WIDTH*2) self.app.addLabel("delivered", "") self.app.stopLabelFrame() # Replay last received message self.app.startLabelFrame('Replay message:') self.app.addOptionBox("Choose message", self.fileNameList, colspan=2) self.app.setOptionBoxWidth('Choose message', BUTTON_WIDTH) self.app.addButton('Replay', on_button_pressed_replay, 1, 0) self.app.setButtonWidth('Replay', BUTTON_WIDTH) self.app.addButton('Text Message', voiceToText, 1, 1) self.app.setButtonWidth('Text Message', BUTTON_WIDTH) self.app.stopLabelFrame() #Voice to text self.app.startFrame("message frame") self.app.setBg("white") self.app.addLabel("message", "No message data...") self.app.stopFrame() self.app.go() self.stop() def stop(self): """ Stop the component. """ self.mqtt_client.loop_stop() # Stop the state machine Driver self.driver.stop()