95 lines
3.8 KiB
Python
95 lines
3.8 KiB
Python
|
# Модуль машины состояний (конечный автомат)
|
|||
|
|
|||
|
import speaker # Для разговоров
|
|||
|
import datetime # Для времени
|
|||
|
from pyowm import OWM # использование OpenWeatherMap для получения данных о погоде (pip install pyowm)
|
|||
|
|
|||
|
machine = None # Конечный автомат
|
|||
|
current_state = None # Текущее состояние
|
|||
|
weather_api_key = None # Ключ для OpenWeatherMap
|
|||
|
|
|||
|
def init(assistant_name):
|
|||
|
"""Инициализирует конечный автомат"""
|
|||
|
global machine
|
|||
|
global current_state
|
|||
|
global weather_api_key
|
|||
|
|
|||
|
with open("weatherApiKey.txt", "r") as key:
|
|||
|
weather_api_key = key.read()
|
|||
|
|
|||
|
current_state = "Начало"
|
|||
|
machine = {
|
|||
|
"Начало":{
|
|||
|
assistant_name.lower(): switchToListen
|
|||
|
},
|
|||
|
"Слушаю задание":{
|
|||
|
"время": switchToTime,
|
|||
|
"погода": switchToWeather
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
def work():
|
|||
|
"""Обрабатывает конечный автомат"""
|
|||
|
global machine
|
|||
|
global current_state
|
|||
|
|
|||
|
speaker.speak(f"Доброго времени суток! Ассистент начинает работу")
|
|||
|
while(True):
|
|||
|
word = input().lower() # Пока считаем с клавиатуры предложение
|
|||
|
# Если ассистент знает такое слово для перехода
|
|||
|
if (word in machine[current_state].keys()):
|
|||
|
# Выполняем действия и переход в новое состояние
|
|||
|
current_state = machine[current_state][word]()
|
|||
|
else:
|
|||
|
# иначе переспросим
|
|||
|
speaker.speak("Я не понял, пожалуйста повторите")
|
|||
|
print("Сейчас автомат в: " + current_state)
|
|||
|
|
|||
|
|
|||
|
|
|||
|
# Переход на "Слушаю задание"
|
|||
|
def switchToListen():
|
|||
|
speaker.speak("Слушаю")
|
|||
|
return "Слушаю задание"
|
|||
|
|
|||
|
# Переход на "Говорю время" и возвращаюсь в "Начало"
|
|||
|
def switchToTime():
|
|||
|
now = datetime.datetime.now()
|
|||
|
speaker.speak(f"Сейчас {now.hour} часов, {now.minute} минут")
|
|||
|
return "Начало"
|
|||
|
|
|||
|
# Переход на "Вопрос локации погоды"
|
|||
|
def switchToWeather():
|
|||
|
global weather_api_key
|
|||
|
|
|||
|
speaker.speak("Дома?")
|
|||
|
word = input().lower() # Пока считаем с клавиатуры предложение
|
|||
|
if (word == "да"):
|
|||
|
location = "Home"
|
|||
|
else:
|
|||
|
speaker.speak("Назовите локацию")
|
|||
|
location = input().lower() # Пока считаем с клавиатуры предложение
|
|||
|
|
|||
|
try:
|
|||
|
open_weather_map = OWM(weather_api_key)
|
|||
|
|
|||
|
# запрос данных о текущем состоянии погоды
|
|||
|
weather_manager = open_weather_map.weather_manager()
|
|||
|
observation = weather_manager.weather_at_place(location)
|
|||
|
weather = observation.weather
|
|||
|
|
|||
|
except:
|
|||
|
speaker.speak("Извините. Ошибка запроса к серверу погоды")
|
|||
|
traceback.print_exc() # Вывод трейсбека для отладки
|
|||
|
return "Начало"
|
|||
|
|
|||
|
# разбивание данных на части для удобства работы с ними
|
|||
|
status = weather.detailed_status
|
|||
|
temperature = weather.temperature('celsius')["temp"]
|
|||
|
wind_speed = weather.wind()["speed"]
|
|||
|
pressure = int(weather.pressure["press"] / 1.333) # переведено из гПА в мм рт.ст.
|
|||
|
|
|||
|
speaker.speak(f"Сейчас на улице {temperature} градусов, скорость ветра {wind_speed} метров в секунду, давление {pressure} миллиметров ртутного столба")
|
|||
|
|
|||
|
return "Начало"
|