«То, что вы узнаете сегодня, может изменить будущее»
В настоящее время все больше и больше устройств могут управляться голосом с помощью таких сервисов, как Google Home и Amazon Alexa. Я решил набрать обороты, пройдя курс Alexa в codecademy и добавив голосовое управление в свой Infiniti G35 2006 года, казалось, это хороший способ проверить то, что я узнал. В этом руководстве мы припаяем пульт к вашему автомобилю, чтобы возможности управления ограничились возможностями пульта (на данный момент). Для выполнения этого проекта вам потребуется некоторый опыт работы с паяльником, Raspberry Pi (RPi), Amazon Alexa, AWS Lambda, Javascript / NodeJS / NodePackageManager и базовое понимание электрических цепей или готовность учиться на ходу. . Я сам все еще новичок и уверен, что есть лучший / более понятный способ сделать это, поэтому любые отзывы приветствуются.
Вот что вы можете ожидать, когда сделаете это
А теперь приступим :)
Хорошо, обо всем по порядку, вот что вам понадобится:
- 1x Raspberry Pi с установленной Raspbian OS (я использовал модель 3 B)
- 1x печатная плата (PCB)
- транзисторы (желательно NPN). Я использовал S9014, но 2N2222 тоже подойдет.
- резисторы (я использовал 330 Ом). Вот хорошее видео о том, как рассчитать номинал резистора на основе используемых транзисторов.
- Перемычки
- Провода AWG 22
- Мужской отрыв головой
- дополнительный автомобильный пульт (купил себе этот)
- USB-микрофон (я использовал PS Eye, потому что планирую использовать и камеру, но подойдет любой usb-микрофон, такой как этот)
- Динамик, который подключается через порт 3,5 мм
- Паяльник, припой, флюс, припой (по желанию)
- "кусачки"
- Мультиметр
- Power bank (опционально)
Пусть вас не перегрузит количество необходимых материалов. Звучит много, но некоторые предметы можно приобрести вместе в виде пакета, и они будут доставлены в избытке, поэтому они пригодятся для будущих проектов.
Часть 0: программирование дополнительного автомобильного пульта ДУ
Прежде чем мы зайдем слишком далеко, убедитесь, что вы можете запрограммировать запасной пульт дистанционного управления на свой автомобиль. Если ваш автомобиль является самопрограммируемым (как и мой), вы можете перейти по этой ссылке или для так называемого программирования ключей по этой ссылке. Если ваш автомобиль НЕ является самопрограммируемым, вы можете найти слесаря или обратиться к вашему дилеру.
Часть 1: настройка Alexa на Raspberry PI
Подключите динамик к Raspberry PI и убедитесь, что он работает (например, воспроизведите случайное видео на YouTube). После этого следуйте этому или этому руководству, чтобы установить клиент Alexa на свой Pi. Скорее всего, по пути вы столкнетесь с известной проблемой неверного запроса, и вот вы можете ее исправить. Если вы все сделали правильно, вы должны услышать приветствие от Алексы. На этом похлопайте себя по плечу и переходите ко 2 части :)
Часть 2: настройка микрофона
Если вы выбрали PS Eye, вам сначала нужно установить пакет motion, набрав
sudo apt-get install motion
в терминале, как описано в этой отличной статье.
Когда закончите, введите
arecord -l
Вы должны увидеть свое устройство в списке CAPTURE Hardware Devices.
Это означает, что USB-микрофон / камера подключены к «карте 1», «устройству 0». Теперь продолжайте и попробуйте что-нибудь записать, набрав
arecord --device=hw:1,0 --format S16_LE --rate 44100 -c1 test.wav
а затем воспроизведите его, набрав
aplay --device=plughw:1,0 test.wav
Если вы смогли услышать свою запись, немного поиграйте с Alexa и переходите к части 3, в противном случае проверьте это и / или это для устранения неполадок.
Часть 3. Собираем схему
На данный момент у вас уже должен быть работающий сервис Alexa на вашем Raspberry Pi и вы готовы поговорить о некоторых схемах. Это, наверное, самая сложная и трудоемкая часть, поэтому терпение - ключ к успеху :)
Заявление об ограничении ответственности: я ни в коем случае не являюсь экспертом в области построения схем. Большую часть материала, необходимого для этого проекта, я изучил в процессе, так что если вы похожи на меня, мы находимся в одной лодке :) Должен признать, что в процессе обучения я сжег 2 светодиода и 1 транзистор. Пусть текущий поток течет вместе с ними.
Чтобы отправлять команды в машину, нам нужно имитировать нажатие кнопок на пульте дистанционного управления. Здесь в игру вступают транзисторы. Как работают транзисторы NPN, выходит за рамки этого руководства, но если вам интересно узнать, я настоятельно рекомендую это видео. Короче говоря, транзистор будет действовать как переключатель, который открывается, чтобы пропустить ток (как если бы кнопка была нажата), а затем закрывается (кнопка отпускается).
Шаг 3.1: тестирование
Перед тем как приступить к пайке, протестируем транзистор на макете.
Здесь 3,3 В, поступающие от RPi, поступают на коллектор транзистора (короткий красный провод) и через резистор на базу (средний). Анод светодиода (более длинная ножка) подключен к ножке эмиттера, а катод (более короткая ножка) подключен к GND (синий провод). Если вы вытащите резистор, светодиод должен погаснуть, потому что база транзистора не имеет тока, поэтому она закрыта - ток не проходит от коллектора к эмиттеру. Вот карта GPIO для справки (3,3 В = 3 В 3 на схеме)
Шаг 3.2: пайка печатной платы
Обрежьте и зачистите провода. Я выбрал красный для VCC, черный для GND и зеленый для сигналов управления.
Припаяйте разъемы к печатной плате. Они будут использоваться для связи с RPi. Также припаиваем резисторы.
Припаиваем провода
Спаяйте вместе разъемы с резисторами, а затем резисторы с проводами на задней стороне печатной платы.
Я также решил добавить светодиод, чтобы проверить, включена ли плата. Этот шаг не обязателен
С помощью перемычек подключите разъем VCC к 3,3 В GPIO на RPi, а землю - к GND. Если вы припаяли светодиод, как я, он должен загореться. На этом пайка печатной платы завершена, перейдем к пульту дистанционного управления.
Шаг 3.3: автомобильный пульт
Разберите запасной пульт дистанционного управления. Отметьте, какая кнопка что делает (блокировка, разблокировка, багажник и т. Д.)
Теперь распаяйте настоящие кнопки
Припаяйте красный (VCC) и черный (GND) провода, идущие от печатной платы, к пульту дистанционного управления, где раньше была батарея. Теперь у нас должно быть постоянное питание от RPi. Припаяйте транзисторы в места, где раньше были кнопки, подключив ножку коллектора транзистора к VCC, а ножку эмиттера к земле (я использовал мультиметр для определения VCC). Обратите внимание, что это, скорее всего, плохая практика, поскольку транзисторы также должны быть припаяны к печатной плате, но для простоты я сделал это так
Затем припаяйте зеленые провода к основанию резисторов и используйте перемычки для подключения заголовков к контактам GPIO, которые будут отвечать за отправку сигналов на пульт. Я выбрал GPIO 16, 20 и 21 для блокировки, разблокировки и ствола соответственно. Вот снова картография
Не забудьте очистить кожу ватным тампоном и медицинским спиртом. 50%, вероятно, не очень хорошо, так как он содержит больше воды, чем более высокий процент, но на данный момент подойдет
Часть 4: настройка сервера localhost и ngrok
Мы будем запускать локальный сервер NodeJS / Express, который предоставляет конечные точки для связи с Alexa.
Прежде всего, если у вас еще не установлен NodeJS на Raspberry PI, сделайте это. Затем запустите эти команды в терминале на Raspberry PI:
mkdir my-car-server && cd my-car-server npm init touch index.js mkdir routes && cd routes touch rest.js cd ..
С этого момента вы можете редактировать код с помощью nano, набрав в терминале
nano index.js
или используйте Geany IDE из меню приложений - ›Программирование -› Geany
Команда npm init должна была создать файл package.json внутри каталога my-car-server. Откройте его и вставьте следующие зависимости:
"dependencies": { "express": "^4.16.2", "nodemon": "^1.17.1", "onoff": "^2.0.0", }
затем беги
npm install
это установит вышеуказанные зависимости (эй, капитан, очевидно!)
Вот мое git репо, если хотите взглянуть / клонировать. В противном случае откройте index.js и вставьте:
const express = require('express'); const path = require('path'); const http = require('http'); const bodyParser = require('body-parser'); const port = 4200; const app = express(); const server = http.createServer(app); app.locals.title = "Your title"; const rest = require('./routes/rest'); app.use('/rest', rest); app.set('view engine', 'ejs'); server.listen(port, () => console.log(`listening on ${port}`)); module.exports = app;
Файл index.js теперь содержит все необходимое для запуска локального сервера. Теперь нам нужно создать фактические конечные точки, с которыми может разговаривать Alexa.
Перейдите в каталог routes и откройте rest.js. Вставьте следующее:
const express = require('express'); const router = express.Router(); const path = require('path'); const GPIO = require('onoff').Gpio; const carLock = new GPIO(16, 'out'); const carUnlock = new GPIO(20, 'out'); const carTrunk = new GPIO(21, 'out'); carLock.writeSync(0); carUnlock.writeSync(0); carTrunk.writeSync(0); router.get('/lock', (req, res, next) => { carLock.writeSync(1); setTimeout(() => { carLock.writeSync(0); }, 1000); console.log("lock car received"); res.send(200); }); router.get('/unlock', (req, res, next) => { carUnlock.writeSync(1); setTimeout(() => { carUnlock.writeSync(0); }, 1000); console.log("unlock car received"); res.sendStatus(200); }); router.get('/trunk', (req, res, next) => { carTrunk.writeSync(1); setTimeout(() => { carTrunk.writeSync(0); }, 1000); console.log("trunk received"); res.sendStatus(200); }); router.get('/windows', (req, res, next) => { console.log("windows received"); carUnlock.writeSync(1); setTimeout(() => { carUnlock.writeSync(0); res.sendStatus(200); }, 6000); }); module.exports = router;
Пульт дистанционного управления моей машины поддерживает
- Замок
- Разблокировать
- Сундук
- Тревога
- Windows опущена (удерживайте разблокировку несколько секунд)
Настройте код в соответствии с вашими удаленными возможностями. Чтобы имитировать нажатие кнопки, я установил вывод GPIO на высокий уровень (writeSync (1)) на определенное время (1000, 2000, 6000 мс), а затем на низкий (writeSync (0)).
Это очень простой пример, который не включает никаких мер безопасности. В идеале вам нужно, чтобы Alexa отправляла какой-то токен с каждым запросом в конечную точку. Затем сервер проверяет его и либо выполняет код, либо отправляет обратно статусный код HTTP 401 Unauthorized.
Теперь вернитесь к my-car-server из окна терминала и запустите сервер, набрав
node index.js
Вы должны увидеть сообщение в окне терминала:
listening on 4200
Это замечательно, НО прямо сейчас сервер работает локально, что означает, что он виден только внутри вашей локальной сети. У вас есть 2 варианта (о которых я знаю), чтобы раскрыть его:
Эти службы туннелируют данные извне на созданный вами локальный сервер.
Выберите один и следуйте документации, чтобы установить и запустить его. Я лично предпочитаю ngrok, потому что у меня возникли проблемы с отключением соединения по локальному туннелю. С другой стороны, localtunnel позволяет вам выбирать доменные имена бесплатно, в то время как ngrok генерирует случайные, если вы не платите за подписку (5 долларов в месяц дает вам 3 зарезервированных домена)
Часть 5: настройка функции AWS Lambda
Я предполагаю, что вы прошли курс Amazon Alexa в codecademy, на который я ссылался ранее в статье и который уже в некоторой степени знаком с Lambda. Войдите в консоль AWS, перейдите в Lambda и создайте новую функцию. Выберите Чертежи - ›alexa-skill-kit-sdk-factskill -› и нажмите Настроить.
Заполните основную информацию и выберите существующую роль с именем lambda_basic_execution. Нажмите Создать функцию. Вы должны попасть на экран конфигурации функций. Добавьте триггер, обратите внимание на ARN и убедитесь, что для региона установлено значение Северная Вирджиния (верхний правый угол).
Прокрутите вниз до редактора кода, сотрите весь код и вставьте следующее:
"use strict"; var Alexa = require("alexa-sdk"); var https = require('https'); const myCar = "Infinit G35"; const api = "https://yourdomain.ngrok.io/rest"; var handlers = { "LockIntent": function () { let alexa_this = this; https.get(`${api}/lock`, function(res) { res.on('data', (d) => { }); res.on('end', function(res) { alexa_this.response.speak("Your car is locked"); alexa_this.emit(':responseReady'); }); }); }, "UnlockIntent": function () { let alexa_this = this; https.get(`${api}/unlock`, res => { res.on('data', (d) => { }); res.on('end', function(res) { alexa_this.response.speak("Your car is unlocked"); alexa_this.emit(':responseReady'); }); }) }, "TrunkIntent": function () { let alexa_this = this; https.get(`${api}/trunk`, res => { res.on('data', (d) => { }); res.on('end', function(res) { alexa_this.response.speak("Trunk is open"); alexa_this.emit(':responseReady'); }); }) }, "WindowsIntent": function () { let alexa_this = this; https.get(`${api}/windows`, res => { res.on('data', (d) => { }); res.on('end', function(res) { alexa_this.response.speak("Windows down"); alexa_this.emit(':responseReady'); }); }) }, "LaunchRequest": function () { this.response.speak("Hello. You can say lock, unlock or trunk to interact with " + myCar); this.emit(':responseReady'); } }; exports.handler = function(event, context, callback){ var alexa = Alexa.handler(event, context); alexa.registerHandlers(handlers); alexa.execute(); };
Опять же, код не идеален и служит просто базовым примером. Настройте его в соответствии с вашими потребностями и сохраните.
Часть 6: настройка навыка Alexa
Давайте войдем в Консоль разработчика набора навыков Alexa и создадим новый навык. После того, как вы заполнили основную информацию о навыках, вы должны увидеть экран создания навыков. Продолжайте и добавляйте желаемые намерения. Вот как выглядит мой:
После этого нажмите «Построить модель» и перейдите в подменю конечной точки. Установите переключатель в положение AWS Lambda ARN и вставьте ARN, который вы записали на предыдущем шаге, в поле Default Region:
На этом этапе навык должен быть полностью установлен, но рекомендуется сначала проверить его, поэтому, если сборка готова, перейдите в меню Тест и введите / произнесите некоторые высказывания, которые вы добавили в намерения ранее:
Это оно! Теперь у вас все готово! Молодец товарищ!
Часть 7: тестирование на вашем автомобиле
Вы дошли до последней главы, поздравляю! На этот раз похлопайте себя по плечу обеими руками, и давайте закончим, ладно?
Вы можете либо отправиться в свою машину и проверить его там, либо сначала провести несколько тестов на макетной плате, подключив светодиоды к контактам GPIO (не забудьте вставить резисторы между ними!), Которые мы установили ранее, и проверить, загораются ли они. вверх на основе ваших голосовых команд. Твой выбор :)
Прежде чем отправиться в машину, обязательно настройте точку доступа WIFI на своем телефоне и подключите к нему Raspberry Pi, чтобы он автоматически подключался позже. На данный момент это подойдет, но если вы планируете оставить Alexa в машине, возможно, вы захотите инвестировать в что-то вроде AT&T Velocity. Самый дешевый план включает 2 ГБ данных на 90 дней за 25 долларов, которых должно хватить для взаимодействия с Alexa.
Я использовал блок питания для питания Raspberry PI, но вы также можете включить его от розетки 12 В в машине, если у вас есть адаптер.
Дальнейшее развитие
Я планирую продолжить работу над этим проектом, добавив распознавание лиц и управление другими вещами, такими как кондиционер, радио, освещение и т. Д. В идеале я бы хотел иметь возможность запускать / останавливать машину, но механическая коробка передач, иммобилайзер и блокировка рулевого колеса делают это очень трудно реализовать :( Если у вас есть какие-либо идеи, пожалуйста, поделитесь ими. Кроме того, если у вас есть какие-либо видео / фотографии того, что вы создали на основе этой статьи, я определенно хотел бы их увидеть! Ура!