Ассистент для голосового управления компьютером

В этой статье мастер расскажет нам как сделать виртуального помощника для компьютера и его физическую аватар. Аватар выполняет некоторые действия, когда с ним разговариваешь. Например, двигает руками и головой. В конце статьи можно посмотреть видео с демонстрацией работы и сборки устройства.

Инструменты и материалы:
-Ардуино Нано;
-Сервопривод SG90 — 3шт;
-Ультразвуковой датчик HC-SR04;
-Лист ПВХ;
-Сервоколесо (для основания);
-Нож;
-Ножницы;
-Клеевой пистолет;
-Аэрозольная краска;
-Компьютер с ПО;

Шаг первый: принцип работы
Основной код или часть кода AI (искусственный интеллект) будет исполняться на компьютере. Это сделано потому, что компьютер поддерживает язык программирования python и имеет большую вычислительную мощность, чем маленький Arduino, а также, поскольку бот AI будет контролировать / автоматизировать некоторые задачи компьютера. Плата Arduino будет подключена к компьютеру с помощью USB-кабеля.

Идея состоит в том, чтобы запустить программу, которая будет выполнять преобразование речи в текст, обрабатывать текст, а также преобразовывать текст в речь. Т.е. робот будет слушать, понимать и отвечать. А также, его физическая копия, выполнять некоторые движения.
В качестве примера — если робот должен сказать ‘Hi/hello’, код Python отправит «h», а затем Arduino выполнит функцию hi ().

Шаг второй: печатная плата
Мастер разработал печатную плату, которую можно использовать для создания множества проектов. Она имеет слот для карт Micro SD, слот для модуля Bluetooth, внешний источник питания 5 В, и все это работает от Arduino Nano.
Печатную плату он заказал на специализированном сервисе, а пользователи могут скачать ее здесь.

Шаг третий: схема и монтаж
Затем мастер собирает плату согласно схемы.

Шаг четвертый: сборка бота
Для изготовления тела робота мастер использовал лист ПВХ, но можно использовать любой подходящий материал, например, картон.
Сначала он сделал туловище и установил в него плату и серводвигатели.

Одна рука была сделана как гаечный ключ, в другую руку установил и приклеил штекер.

Дальше сделал голову и установил в нее ультразвуковой датчик.

Установил рычаги сервоприводов, собрал робота и покрасил в желтый цвет.

Шаг пятый: программирование
Сначала нужно загрузите Python с этого сайта.
Можно использовать любую версию Python, мастер использует Python3.7.1.
После установки Python нужно будет запустить некоторые команды из командной строки / терминала, чтобы установить библиотеки для распознавания речи, поддержки звука, преобразования текста в речь, автоматизации браузера, последовательной связи. Выполняем эти команды:
 Показать / Скрыть текстpip install speechrecognition
pip install pyaudio
pip install pyttsx3
pip install pywhatkit
pip install pyserial

Затем загружает код.
 Показать / Скрыть текстauthor: ashraf minhaj
mail: ashraf_minhaj@yahoo.com
Last Edit: Nov 2020

License: Copyright (C) Ashraf Minhaj.
General Public License (GPL3+)
"""

import speech_recognition as sr # voice recognition library
import random # to choose random words from list
import pyttsx3 # offline Text to Speech
import datetime # to get date and time
import webbrowser # to open and perform web tasks
import serial # for serial communication
import pywhatkit # for more web automation

# Declare robot name (Wake-Up word)
robot_name = 'jaundice'

# random words list
hi_words = ['hi', 'hello', 'yo baby', 'salam']
bye_words = ['bye', 'tata', 'hasta la vista']
r_u_there = ['are you there', 'you there']

# initilize things
engine = pyttsx3.init() # init text to speech engine
#voices = engine.getProperty('voices') #check for voices
#engine.setProperty('voice', voices[1].id) # female voice
listener = sr.Recognizer() # initialize speech recognition API

# connect with NiNi motor driver board over serial communication
try:
port = serial.Serial("COM15", 9600)
print("Phycial body, connected.")
except:
print("Unable to connect to my physical body")

def listen():
""" listen to what user says"""
try:
with sr.Microphone() as source: # get input from mic
print("Talk>>")
voice = listener.listen(source) # listen from microphone
command = listener.recognize_google(voice).lower() # use google API
# all words lowercase- so that we can process easily
#command = command.lower()
print(command)

# look for wake up word in the beginning
if (command.split(' ')[0] == robot_name):
# if wake up word found….
print("[wake-up word found]")
process(command) # call process funtion to take action
except:
pass

def process(words):
""" process what user says and take actions """
print(words) # check if it received any command

# break words in
word_list = words.split(' ')[1:] # split by space and ignore the wake-up word

if (len(word_list)==1):
if (word_list[0] == robot_name):
talk("How Can I help you?")
#.write(b'l')
return

if word_list[0] == 'play':
"""if command for playing things, play from youtube"""
talk("Okay boss, playing")
extension = ' '.join(word_list[1:]) # search without the command word
port.write(b'u')
pywhatkit.playonyt(extension)
port.write(b'l')
return

elif word_list[0] == 'search':
"""if command for google search"""
port.write(b'u')
talk("Okay boss, searching")
port.write(b'l')
extension = ' '.join(word_list[1:])
pywhatkit.search(extension)
return

if (word_list[0] == 'get') and (word_list[1] == 'info'):
"""if command for getting info"""
port.write(b'u')
talk("Okay, I am right on it")
port.write(b'u')
extension = ' '.join(word_list[2:]) # search without the command words
inf = pywhatkit.info(extension)
talk(inf) # read from result
return

elif word_list[0] == 'open':
"""if command for opening URLs"""
port.write(b'l')
talk("Opening, sir")
url = f"http://{''.join(word_list[1:])}" # make the URL
webbrowser.open(url)
return
elif word_list[0] == 'uppercut':
port.write(b'U')

elif word_list[0] == 'smash':
port.write(b's')

elif word_list[0] == 'punch':
port.write(b'p')

# now check for matches
for word in word_list:
if word in hi_words:
""" if user says hi/hello greet him accordingly"""
port.write(b'h') # send command to wave hand
talk(random.choice(hi_words))

elif word in bye_words:
""" if user says bye etc"""
talk(random.choice(bye_words))

def talk(sentence):
""" talk / respond to the user """
engine.say(sentence)
engine.runAndWait()

# run the app
while True:
listen() # runs listen one time

Дальше нужно запрограммировать Ардуино. Мастер использует Arduino.ide для программирования платы.

Как уже упоминалось ранее, программа Arduino ожидает последовательных данных. Если она получает какие-либо данные, она ищет сопоставление. Если данные совпадают с предопределенной командой, она выполняет команду.

Код можно скачать ниже.
 Показать / Скрыть текст/** JAUNDICE: AI Assistant robot with Arduino and Python **
*
* author: ashraf minhaj
* mail: ashraf_minhaj@yahoo.com
* Last Edit: Nov 2020
*
* License: Copyright (C) Ashraf Minhaj.
* General Public License (GPL3+)
*/

#include<Servo.h>

Servo head;
Servo l_hand;
Servo r_hand;

// define sonar sensor's pins
int trig = 4;
int echo = 5;

// received data
byte val = "";

void setup() {
// put your setup code here, to run once:
head.attach(2);
l_hand.attach(3);
r_hand.attach(4);

Serial.begin(9600); // for communicating via serial port with Python
}

void standby(){
// all motors to these positions
head.write(90);
int r_pos = 30;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
}

void hi(){
// all motors to these positions
head.write(90);

int i = 0;
for(i=30; i<= 170; i++){
r_hand.write(i);
delay(5);
}

for(i=170; i>= 100; i—){
r_hand.write(i);
delay(5);
}

for(i=100; i<= 170; i++){
r_hand.write(i);
delay(5);
}

for(i=170; i>= 30; i—){
r_hand.write(i);
delay(5);
}

standby();
}

void hands_up(){
// do this on every command (nothing much just move hands a bit)

//head.write(150);
//delay(300);
//head.write(90);

int i = 0;
for(i=30; i<= 170; i++){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}

delay(600);

for(i=170; i>= 30; i—){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}

}

void weight_lift(){
// lift weight using both hands
int i = 0;
for(i=30; i<= 170; i++){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}

for(int count=0; count<=4; count++){
for(i=170; i>= 60; i—){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}

for(i=60; i<= 170; i++){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}
}

for(i=170; i>= 30; i—){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}
}

void excited(){
return;
}

void look_left(){
// rotate hed to left
head.write(180);
}

void confused(){

for(int count=0; count<=1; count++){
head.write(30);
r_hand.write(170);
delay(700);
r_hand.write(30);
head.write(120);
l_hand.write(30);
delay(700);
l_hand.write(160);
}
standby();
}

void double_punch(){
// do a punch
int i = 0;
for(i=30; i>= 0; i—){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}
delay(2000);

int r_pos = 80;
int l_pos = map(r_pos, 0, 180, 180, 0);
l_hand.write(l_pos);
r_hand.write(r_pos);
delay(500);
standby();
}

void r_upper_cut(){
// make right upper-cut
int i = 0;
for(i=30; i<= 170; i++){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}

for(int count=0; count<=4; count++){
int i = 0;
for(i=170; i>= 60; i—){
r_hand.write(i);
delay(1);
}

for(i=60; i<= 170; i++){
r_hand.write(i);
delay(1);
}
}
standby();
delay(100);
}

void smash(){
// smash things
int i = 0;
for(i=30; i<= 170; i++){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(5);
}
delay(2000);
for(i=170; i>= 0; i—){
int r_pos = i;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(1);
}
delay(300);
int r_pos = 180;
int l_pos = map(r_pos, 0, 180, 180, 0);

l_hand.write(l_pos);
r_hand.write(r_pos);
delay(1000);
standby();
}

void eye_detect(){
// do something if eye sensor detect motion
return;
}

void loop() {
// put your main code here, to run repeatedly:
standby();

while(Serial.available() > 0) //look for serial data available or not
{
val = Serial.read(); //read the serial value

if(val == 'h'){
// do hi
hi();
}
if(val == 'p'){
// do hi
double_punch();
}
if(val == 'u'){
hands_up();
delay(3000);
}
if(val == 'l'){
standby();
look_left();
delay(2000);
}
if(val == 'U'){
// uppercut
r_upper_cut();
delay(2000);
}
if(val == 's'){
smash();
delay(2000);
}
}
}

После выполнения всех этих шагов мастер подключает Arduino к компьютеру с помощью USB-кабеля, а затем запускает программу python. Еще нужно добавьте правильный порт Arduino в код Python.

Все готово.

Источник (Source)

Становитесь автором сайта, публикуйте собственные статьи, описания самоделок с оплатой за текст. Подробнее здесь.

Источник: usamodelkina.ru

Понравилась статья? Поделиться с друзьями:
KIA