Пользователь
0,0
рейтинг
21 декабря 2011 в 16:40

Android + Arduino + 4 колеса из песочницы

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

Как развивалось помешательство, я решил описать в статье. Получилось длинно, но может кому-нибудь будет интересно. Думаю, статья ориентирована на тех, кто ещё не практиковался в робототехнике.

Вот что получилось в результате. Видео винтажное, снималось владельцем iPhone, а они ведь затейники, ну вы знаете. Звук я оставил закадровый сознательно, чтоб всё жужжало как взаправду.




Лирика


Последующая пара абзацев исключительно лирическая, и может быть пропущена суровым техническим читателем.

Началось всё с обеда в офисе. Нас было несколько человек, и одна сотрудница спросила, есть ли у кого-нибудь хобби. Мы подумали, подумали и вдруг поняли, что хобби-то ни у кого и нет. Есть, конечно, тяга к программированию, есть занятия спортом, семьи и друзья, но так чтобы домики из спичек клеить, кораблики вырезать или марки собирать – нет, такого не оказалось. Не знаю, от жадности или другого какого чувства, но мысль об отсутствии любимого дела застряла в моей голове. Подъём, дорога на работу, работа, дорога домой, максимум часик с семьёй (у всех же дела!), сон… Ночью, видимо, происходит какой-то сброс, и наутро начинается новая итерация. Та сотрудница как будто воткнула проводок с обратной связью мне в голову. И не только мне. Пострадавших за тем обедом, как вскоре выяснилось, стало двое. Темой, интересующей нас обоих, оказалась робототехника. В детстве я был радиолюбителем, институт закончил по специальности «роботы, робототехнические системы и комплексы», сейчас я разработчик ПО. Такое хобби просто создано для меня. Где я был раньше?

В офисе мы выступили с призывом сделать роботов и провести РобоБитву, но больше желающих не нашлось. Были сочувствующие, но участников так и осталось двое. Мы решили, что каждый сделает своего робота и в назначенную дату (срок получился, примерно, два месяца), мы схлестнёмся в сражении. Чувство прекрасного и неприятие насилия заставили нас отказаться от кувалд, болгарок и прочих орудий дикарей в пользу ИК-пушки и ИК-приёмника. Хоть со временем идея РобоБитвы и перестала меня трогать, потому что теперь у меня был робот (моя прелесть, естественно) и масса планов по его развитию, надо признать, факт проведения РобоБитвы, очень подстегнул меня по срокам. Это был прекрасный мотиватор, он заставлял выискивать время и спешить.

Архитектура


Ну, теперь к делу. Я хотел бы описать, как продвигалось изготовление моего робота, с какими проблемами я столкнулся, как я их решал и самый частый вопрос ко мне: сколько денег мне всё это стоило.

Первоначально я предполагал, что для системы управления (в будущем мозга) робота я буду использовать платформу Arduino. Мой «противник» двигался по этому же пути. Тема была новая для нас, поэтому порывшись в интернете, мы обнаружили, что в мире Arduino есть всё: Ethernet Shield, Bluetooth Shield, Motor Shield, гироскопы, акселерометры и целая куча других сенсоров и плат сопряжения, которые могут пригодиться гикам вроде нас. Но чем больше я выискивал полезных узлов для своего робота, тем больше я убеждался в том, что это у меня уже есть. В смартфоне. У меня HTC Sensation с ОС Android 2.3.4 на борту. И там уже есть: Bluetooth, WiFi (даже WiFi роутер), камера, фонарь, огромный дисплей, звук, микрофон, microUSB, память, гироскоп, компас. И вот тут я решил, что мозг моего робота переедет в смартфон. А Arduino будет выполнять функции спинного мозга. Пусть принимает команды, исполняет их и собирает данные с сенсоров, чтобы потом передать их в мозг.

У такого архитектурного решения есть большой минус – кажется, в конце статьи мне придётся включить стоимость моего смартфона в стоимость робота, но смартфон у меня уже был, а пройти мимо плюсов, которые он мне подарил, я не смог. К тому же по работе мне была интересна тема программирования под ОС Android, и такое решение пришлось как нельзя кстати. К автономным действиям мой робот ещё не готов, это тема дальнейшего развития проекта, поэтому родился ещё один слой в управлении роботом – простая клиентская программа, которая формирует команды управления и передаёт их через TCP-сокет в Android-приложение. Такая программа может быть написана под любую платформу, лишь бы можно было установить соединение через TCP-сокет. Сейчас я написал простенькое .NET-приложение с использованием XNA. Для управления роботом я использую геймпэд от XBOX 360.

Функции


Приблизительно набросаю кто чем занят.

Функции Arduino-скетча:
  1. Установление соединения с Android-приложением.
  2. Приём и исполнение команд, полученных от Android-приложения.
  3. Приём сигналов от сенсоров робота и передача этих сигналов в Android-приложение.

Функции Android-приложения:
  1. Установление соединения с Arduino-скетчем.
  2. Установление соединения с .NET-приложением.
  3. Приём команд от .NET-приложения.
  4. Исполнение части принятых команд, не предназначенных для уровня Arduino. Например, проигрывание звуков, включение фары (вспышка фотокамеры), смена мордочек на дисплее смартфона и т.д.
  5. Передача команд в Arduino.
  6. Приём сигналов сенсоров от Arduino.
  7. Реагирование на сигналы сенсоров. Например, проигрывание звука при «попадании» выстрела из ИК-пушки в моего робота.
  8. Передача сигналов сенсоров в .NET-приложение.

Функции .NET-приложения:
  1. Установление соединения с Android-приложением.
  2. Обработка ввода (геймпэд XBOX 360).
  3. Формирование команд.
  4. Передача команд в Android-приложение.
  5. Приём сигналов сенсоров от Android-приложения.
  6. Отображение текущего состояния робота.

С программной реализацией функций больших проблем у меня не возникло, разве что для меня было новым программирование на Java (уровень Android-приложения), но это мои личные трудности. Скетчи на Arduino никаких трудностей не вызвали – очень простой язык (Wiring), вполне сносная среда разработки. С чем пришлось повозиться, так это с управлением роботом. Приложение я писал на C#, и оно пока без затей и очень простое, но алгоритмы управления роботом пришлось дорабатывать дважды – я не сразу смог добиться хорошей управляемости роботом. Но это я забегаю вперёд, напишу об этом ниже.

Мой план


Сроки я посчитал достаточно сжатыми или это я такой медленный, поэтому я составил себе следующий план:
  1. Освоение контроллера Arduino.
  2. Сборка тележки, монтаж на ней электроники.
  3. Программирование Arduino, автономное выполнение команд.
  4. Управление тележкой через USB ПК.
  5. Подключение Arduino к Android-смартфону.
  6. Передача команд от ПК смартфону.
  7. Пушка и датчики попадания.
  8. Окончательная сборка.
  9. Причёсывание, документирование.

Освоение контроллера Arduino


Первый пункт плана мне был нужен для «разогрева». Надо было понять, что такое Arduino, установить среду разработки, освоиться с новым языком, написать пару тестовых скетчей. Для экспериментов я приобрёл уже готовый набор «Матрёшка X». Прошу не воспринимать ссылку как коммерческую рекламу, но Амперка оказался очень удобным ресурсом. Там много обучающей информации, видеоуроки, форум. Наигравшись со светодиодиками, пришла пора двинуться дальше.

Сборка тележки, монтаж на ней электроники


Что я хотел от мобильной платформы робота: чтобы она была достаточно маленькой для удобного маневрирования в квартире, чтобы она была резвой и чтобы встреченные ей ковры, порожки и провода от удлинителей не были для неё непроходимым препятствием. Ну и ещё, естественно, должно быть достаточно места для электроники Arduino и смартфона. Подо всё это замечательно подошла вот такая четырёхколёсная платформа.

В комплект платформы из электрики, кроме четырёх двигателей с редукторами, идут тумблер и разъём внешнего питания. Разъём совместим с разъёмом питания Arduino Uno и очень пригодился потом при тестировании.

Вот моё первое фото тележки:
Фото тележки

Здесь установлено пять батареек формата AA в держателе, идущем в комплекте. Как выяснилось позже, батареек для четырёх двигателей, двух сервоприводов и электроники мне стало не хватать. И тут открылась вся прелесть моей тележки. Я разжился 12-ти вольтовыми Ni-MH аккумуляторными сборками. Так вот оказалось, что вместо штатного держателя на 5 AA в тележку могут поместиться две аккумуляторные сборки по десять банок AA в каждой. Это 20 банок AA! Сборки я включил параллельно, получив 12 В и 2200 mAh. Правда, теперь пришлось тратиться на зарядное устройство для этого мини-монстра. И опять пригодился разъём внешнего питания. Его я теперь использую и для зарядки аккумулятора робота.

Фото тележки c двумя аккумуляторными сборками

Дополнительный приятный бонус платформы – штатное место для крепления сервопривода.

Единственный недостаток тележки, с которым я столкнулся, это неплотная установка колёс на валы редукторов. При сборке крепление колёс казалось надёжным, но при первых же испытаниях робота на ковре колёса стали отваливаться. Конструкция колеса не предполагала его привинчивание – просто плотное прилегание, приклеивать колёса мне не хотелось, поэтому пришлось их высверливать и закреплять на валу редуктора обычными саморезами. Благо, отверстия в валах редукторов есть.

Доработка колёс

Программирование Arduino, автономное выполнение команд


Итак, на следующем шаге я хотел добиться от платформы движения. Для этого приобрёл “Motor Shield v3” от “Freeduino.ru”. Он позволяет управлять четырьмя двигателями постоянного тока или двумя шаговыми двигателями, а также на нём установлены разъёмы для двух сервоприводов. Кроме того, motor shield поддерживает SPI. Как мне тогда показалось замечательный вариант, даже избыточный – мне было нужно управление двумя сервоприводами и только двумя двигателями постоянного тока (для левой и правой стороны передние и задние двигатели соединены параллельно). Более того, у меня получилось управление двигателями и сервоприводами, и я даже закрыл этот пункт своего плана.



Проблемы с “Motor Shield v3” начались позже. Когда я для сопряжения со смартфоном приобрёл USB Host Shield от DFRobot, у меня начались конфликты по используемым цифровым выходам Arduno. Я пробовал и обычный режим управления этим motor shield, и SPI – лучшее чего я добился, это управление двигателями и сервоприводами, но больше свободных выходов у меня не оставалось. А ведь ещё надо было управлять ИК-пушкой. Насколько я понял, проблема была чисто программная. Библиотеки, которые я использовал, взяты там же, на freeduino.ru. Датированы они декабрём 2009 года. На сайте указано, что модификация библиотеки для работы с SPI не протестирована на шаговых двигателях, но в ближайшее время, они обещают это сделать. И Бог бы с ними, с этими шаговыми двигателями, только дата библиотеки 2009 год. Похоже, проект заброшен. Я честно посмотрел исходники, вздохнул, и понял, что вникать в это мне совсем не хочется. Как-нибудь в другой раз. Я, конечно, мог обойтись только одним сервоприводом, но очень уж не хотелось себя ограничивать.

По идее, для управления двумя двигателями мне нужно четыре ноги контроллера, ещё две мне нужны для сервоприводов, одна для стрельбы из ИК-пушки и четыре для управления USB Host Shield. Итого одиннадцать ног. Нулевую и первую ноги я использовать не стал – это TX и RX последовательного порта Arduino Uno. Вообще говоря, их можно использовать, но это предприятие рискованное, насколько я понял – надо быть готовым к перепрограммированию контроллера. Поэтому я оставил эти ноги в покое. Получается, я перебрал все тринадцать ног Arduino Uno. Вот только заставить “Motor Shield v3” использовать по две ноги на двигатель или четыре ноги SPI-шины мне не удалось.

Пришлось приобрести ещё один motor shield. Производитель DFRobot. Название не особенно оригинальное: “2A Motor Shield For Arduino”. Зато он прост и для управления ему нужны только четыре цифровых выхода Arduino (два из них должны быть с ШИМ). Даже готовая библиотека не нужна. Правда, на нём нет разъёмов для сервоприводов, но это уже мелочи.

Управление тележкой через USB ПК


На этом шаге я сформулировал систему команд робота и, можно сказать, получил почти финальную версию Arduino-скетча. При соединении через USB-порт Arduino подключается как обычный serial-порт. Команды в него можно передавать любым терминальным клиентом. Поначалу я использовал Serial Monitor, входящий в IDE Arduino. Вколачивать команды быстро надоело, и для тестов я написал WinForm-приложение с тремя ползунками (для управления двигателями и горизонтальным сервоприводом), которые позволили мне проверить свои скетчи и провести первые эксперименты с управляемостью роботом.



Система команд простая: все команды пятисимвольные, причём первые два символа обозначают саму команду, а оставшиеся три символа – цифровые, определяют значение параметра. Например:
LF190 – левый двигатель вперёд (left forward) со скоростью 190 (скорость задаётся от 000 до 255);
HH045 – установить горизонтальный угол поворота головы (head horizontal) равным 45 градусам.

Подключение Arduino к Android-смартфону


Тут пришлось поучиться и помучиться. Сначала я думал, что подключение Arduino к Android пройдёт так же просто, как подключение к Windows. В Android-приложении получу serial-порт и буду писать в него команды для Arduino. Так запросто это сделать не получилось. Оказывается, COM-порт в Android-устройстве спрятан где-то далеко. Допускаю, что я что-то не понял – у меня не было времени на изыскания. Изучая вопрос, я нашёл проект “android-serialport-api”. Там даже есть раздел, посвящённый активации последовательного порта в телефонах HTC. И рассматриваются три модели: Dream, Magic и Hero. Моего тут нет. Что ещё меня остановило, так это то, что для активации первое, что надо сделать, это “Root your phone”. Я не рутовал свой телефон, и пока не очень-то собираюсь.

Поэтому, я пошёл по другому найденному мной, и уже изрядно протоптанному всеми пути: Android Open Accessory Development Kit. В DevGuide всё достаточно подробно описано, единственное, что мне не понравилось, так это какой-то безумный пример DemoKit, приведённый там. Пример включает в себя всё что только можно и сразу: и соединение, и определение подключения, и передачу данных, и приём, и управление несколькими светодиодами, и двигателями, и работу с джойстиком, и довольно навороченные (по крайней мере, для меня) activity в Android-приложении. Не осилив с первого захода исходный код примера, я нашёл его упрощённый вариант и всё сразу встало на свои места.

Купив и установив USB Host Shield от DFRobot, мне удалось передавать команды от моего Android-приложения в Arduino-скетч, но тут меня накрыло сразу двумя проблемами. Одна описана выше – это какой-то конфликт с моим первым motor shield (уверен, проблема в библиотеке управления motor shield от freeduino.ru). А вот вторую я так и не смог пока решить. Будет здорово, если кто-нибудь подскажет что делать. USB Host Shield является хостом в USB-соединении (извините за это умозаключение). Это значит, что питание поступает от USB Host Shield к смартфону. И мой смартфон-переросток начинает объедать и так часто страдающую недоеданием от батарейки типа Крона или пяти AA батареек тележку. Так родилась идея поставить аккумуляторы. 12 В и 2200 мАч это большое подспорье в деле питания двигателей, сервоприводов и смартфона, но мне очень хочется исключить смартфон из этой пищевой цепочки. В опциях телефона ничего найти не удалось. Похоже, программного решения без опять рутирования телефона не будет. Тогда мне оставалось только аппаратное решение проблемы. USB-кабель содержит четыре линии: питание, земля, линия передачи и линия приёма. Первая идея – перерезать питание – провалилась. После этого смартфон перестаёт определять соединения с USB хостом. Опять копаясь в интернете, я нашёл человека, решившего эту проблему. Simon Monk добился отключения зарядки своего Nexus One при подключении к USB Host Shield в аналогичной связке с Arduino. Для этого он в разрез линии питания USB-кабеля установил резистор на 1 кОм. Это сопротивление он получил эмпирически, когда определение подключения (accessory detection) уже срабатывало, а заряд телефона ещё не начинался.

Я поставил в разрез линии килоомный резистор и попробовал подключить смартфон. Подключение обнаружилось, и сразу началась зарядка аккумулятора смартфона. Тогда я поставил переменный резистор на 10 кОм. Эффект тот же. Теперь добавил последовательно ещё 10 кОм – accessory detection не произошло. И зарядка не началась. Был миг триумфа, я начал медленно понижать сопротивление переменным резистором, и на 16-ти килоомах смартфон обнаружил Arduino. Одновременно началась зарядка смартфона. Крах. Я ещё поколдовал немного, отписался Саймону в комментарии к его посту, так там последний комментарий и висит от Дмитрия и пока сдался. В конце концов, с 2200 мАч как-нибудь перезимуем.

На чём Саймон заостряет внимание, и я к нему полностью присоединяюсь, так это на том, что эксперименты с кабелем и собственным телефоном все мы делаем на свой страх и риск. Я должен был это сказать.

Внеплановый сюрприз – помехи по питанию Arduino


Итак, я получил следующую конфигурацию: смартфон с моим тестовым приложением подключен к трём этажам плат – USB Host Shield, Motor Shield и Arduino Uno. Моё тестовое приложение на смартфоне отправляет команды тележке для вращения двигателей в разных режимах (смена скорости, направления) и поворота сервопривода на разные углы. И тут вдруг опять крах. Иногда команды выполняются, а иногда тележка ведёт себя как сумасшедшая – то крутит колёсами в разные стороны, то мотает сервоприводом, причём ничего общего с переданными командами эти припадки не имеют.

Странно было то, что раньше я с этой проблемой не сталкивался. Изучая её, я понял: в новой конфигурации питание производится от одного источника – и питание двигателей, и питание электроники. А ранее я всегда запитывал Arduino отдельным источником: или батарейкой Крона, или USB-кабелем от ПК. Эксперимент с дополнительным источником питания подтвердил мою теорию. Судя по всему, по питанию Arduino идут наводки от работающих двигателей. Я посмотрел, что об этом пишут. Люди с такой проблемой встречаются, как я понял, в мире квадрокоптероводов она есть, это мир мощных электродвигателей, и, возможно, меня затянуло в него из-за включения моих двигателей двумя параллельными парами. Ток удвоился, помехи усилились, и мою тележку потянуло к квадрокоптерам.

Я открыл тему на форуме в Амперке, но люди с подобными проблемами там не сталкивались. Мне ужасно не хотелось использовать два источника питания – это как-то странно. Я понимал, что мне достаточно поставить фильтр на вход по питанию Arduino, но моих технических способностей на это уже не хватало, да и время на дальнейший поиск уже давно закончилось. Единственное, что мне удалось найти из решений подобных проблем, здесь. Я решил рискнуть и купил DC-DC преобразователь TEN 8-1221. Входные 12В преобразователь превращает в +5В и -5В с общим контактом по 0,8А каждый. Я сделал общим -5В и получил +5В и +10В. 10В пошли на питание Arduino и через его стабилизатор на USB Host и микросхемы Motor Shield-а. А 5В я использовал для питания сервоприводов, чтобы немного разгрузить стабилизатор Arduino. Также как и раньше, всё те же 12В я подал на клеммы motor shield для внешней запитки двигателей. Но теперь я надеялся на фильтр, встроенный в DC-DC преобразователь. Мне повезло, и мои надежды оправдались. Теперь тележка прилежно исполняла все команды тестового Android-приложения.

Передача команд от ПК смартфону


Здесь, на моё счастье, всё прошло гладко. Идея была такая: для взаимодействия ПК и смартфона нужен либо внешний WiFi-роутер, либо сам HTC Sensation может выступать в роли роутера. Это удобно, тогда управлять роботом можно хоть в лесу. Я намеренно выбрал WiFi, а не Bluetooth или, например, XBee из-за своих далеко идущих планов. Для связи Android-приложение открывает серверный сокет, далее .NET приложение устанавливает соединение и передаёт команды роботу. Всё было просто.

Полезной опцией моего телефона оказалось то, что его можно перевести в режим «самолёта», при этом будут отключены все средства связи, а затем включить WiFi-роутер. Не знаю, ошибка ли это разработчиков или заложенная полезность, но мне нравится. Я могу отключить GSM, 3G, Bluetooth и при этом пользоваться WiFi. Я даже не стал делать Android-сервис, а обошёлся Android-приложением.

Пушка и датчики попадания


Тут тоже всё получилось без затей. Роль пушки выполняет ИК-светодиод TSAL4400, а для фиксации попадания я использовал фотоприёмник TSOP31236. ИК-светодиод работает на 100мА, и пиковых 200мА. Максимальный допустимый ток на цифровом выходе Arduino — 40 мА. Поэтому, рекомендую поставить транзистор, для управления ИК-светодиодом. Обвязка фотоприёмника указана в его datasheet.

Посылку ИК-сигнала (выстрел) и обработку приёма ИК-сигнала (попадание) я выполняю, естественно, в Arduino-скетче. Для этого использую библиотеку IRremote.

Для сужения пучка ИК-излучения я поместил светодиод в металлическую трубку (я использовал часть секции сломанной телескопической антенны).

Фото пушки

Окончательная сборка


К этому моменту все основные и аппаратные и программные проблемы были решены, но я умудрился найти себе ещё одни грабли. Так получилось, что до этого у меня был только один сервопривод (DF05BB с углом поворота 180 градусов). Голова моего робота должна поворачиваться в горизонтальной и вертикальной плоскости, поэтому я озаботился покупкой второго сервопривода. Точно такого же я не нашёл, но нашёл более мощный с углом поворота 360 градусов. Я подумал, прекрасный вариант для горизонтальной плоскости. Когда купил, оказалось, что я не обратил внимание на два слова в описании: «continius rotaiting». Это значит, что сервы крутятся не на 360 градусов, а просто крутятся. Можно управлять скоростью и направлением их вращения, но углом поворота управлять нельзя. Раньше я не знал о существовании таких сервоприводов. Пришлось искать другой, благо в Амперке появился к тому времени мой первый сервопривод.

Следующий шаг — установка вертикального сервопривода и крепления для телефона. Как я уже писал, для крепления горизонтального привода на тележке уже есть штатное установочное место, а для вертикального я приобрёл специальный кронштейн.

Крепление сервоприводов

Крепление сервоприводов

Для установки моего телефона идеально подошёл держатель для HTC Sensation: HTC Z710e (Z710ECAR01). Его я покупал специально для робота. Шляпки винтов для крепления к кронштейну вертикального сервопривода получились утопленными и ничем не вредят задней стенке корпуса телефона.

Крепление держателя телефона

Свободного места под держателем телефона оказалось немного, и не всякий microUSB разъём там умещался. Поместился разъём фирменного USB-кабеля от HTC, к тому же сам кабель довольно мягкий. Пришлось его укоротить. На другой конец я поставил разъём USB-A (male) для подключения к USB Host Shield.

Теперь об ИК-пушке и ИК-приёмнике. Крепление для ствола пушки сделано из подручных средств: для этой роли прекрасно подошла деталь от полуигрушечной струбцины. Я закрепил её слева на держателе телефона, чтобы пушка не мешала наклонам головы робота и использованию «аппаратных» кнопок смартфона, если они вдруг понадобятся (кнопки находятся справа). Как я уже писал, ствол сделан из телескопической антенки, а её секции зафиксированы термоусадочной трубкой. С ИК-приёмником особо мудрствовать не стал — в таком виде он нужен мне только для проведения РобоБитвы, а затем его можно снять (вообще-то и пушку тоже). Поэтому приёмник я просто прилепил двусторонним скотчем на спине робота.

Ну и пара слов об электронике. Для монтажа DC-DC преобразователя я купил плату для прототипирования Proto Shield, заодно на ней распаял обвязку ИК-приёмника для отсекания ложных срабатываний. На неё же установил разъёмы для сервоприводов и разъём питания всей моей электроники. 10-ти вольтовый выход DC-DC преобразователя выведен непосредственно на контакты Vcc и Gnd. Т.е. разъёмом питания Arduino Uno я не пользуюсь. 5-ти вольтовый выход DC-DC преобразователя выведен на разъёмы сервоприводов. Так получилось четыре «этажа» плат. Четвёртый этаж никак не хотел помещаться в тележку, пришлось ставить небольшие проставки, чтобы приподнять верхнюю панель платформы.

Причёсывание


Для выхода в свет роботёнку требовалось лицо и, конечно, хвост. Я тот ещё компьютерный художник, поэтому под рукой у меня только Paint. Кое-как нарисовал четыре рожицы: довольную, недовольную, злую и насмерть убитую. Затем подправил программу управления для смены настроений. Кстати, попробовав и то и другое, могу с уверенностью сказать, что программировать намного проще. Хвост закрутил из медной проволоки, запихнул в термоусадочную трубку и зажал между спиной и разъёмом USB. Добавил звуки выстрела и попадания. Надо бы ещё звуки под каждое настроение.

Хвост с всё такое

В принципе, с этим можно было уже и выходить. Но мне не давала покоя ещё одна вещь – управляемость роботом. Реализация вроде бы работоспособная, но что-то было не так. По традиции левый джойстик геймпэда управляет движением. Правый – обзором, т.е. вращением головы. Недочёты в управлении были и там и там.

Сначала для тех, кто не в курсе, пара слов о джойстиках. Джойстики геймпэда по крайней мере под XNA дают координаты x и y в диапазоне от -1 до +1. Точка (0, 0) соответствует центральному положению джойстика. Причём, крайние положения джойстика соответствуют окружности с радиусом равным 1.

Теперь об управлении движением. Рулевых колёс у тележки нет, поэтому поворот происходит как у гусеничной техники. Идею лучше всего объяснить на примере. Предположим, мы хотим сделать во время движения вперёд плавный поворот направо. Тогда левые колёса должны продолжать вращаться, не меняя скорости, а правые должны замедлиться. Джойстик будет в положении вперёд и вправо и вернёт координаты x и y в интервале от 0 до +1. Рассмотрим состояние джойстика как вектор с началом в точке (0, 0) и концом в (x, y). Идея заключается в том, чтобы представить модуль вектора как скорость левых двигателей, а произведение модуля на синус угла, который он образует с осью x, как скорость правых двигателей тележки. Ось x перпендикулярна направлению движения. Получается, что при углах, близких к 0 градусов (джойстик в правом положении), скорость правых двигателей будет нулевой, а если угол 90 градусов, скорость правых двигателей будет равна скорости левых.

К моменту «причёсывания» эта идея уже была воплощена. Более того, дополнительно уже был добавлен режим разворота, когда при зажиме левого триггера геймпэда и малых углах вектора с осью X работал другой алгоритм – двигатели на разных сторонах тележки вращались в разные стороны с одинаковыми скоростями, равными модулю вектора.

Но одной вещи не хватало для удобства управления. Значения скоростей по всей вышеописанной тригонометрии менялись от 0 до 1. Эти значения я пропорционально переводил в величины от 0 до 255 для задания ШИМ на двигателях. При малых значениях двигатели только гудели с разной тональностью, а затем довольно резко набирали скорость до максимума. И интуитивно это воспринималось как дискомфорт при управлении тележкой. Выход был в добавлении нелинейной зависимости. При малых значениях координаты, например x, f(x) должна быстро расти. По мере приближения x к 1 рост f(x) должен замедляться. То же самое для координаты y. Мне вполне подошла функция окружности с центром в точке (1, 0) и радиусом 1: f(x) = sqrt(2x — x^2). После добавления этого преобразования по обеим координатам управление стало менее резким и более предсказуемым.

А теперь о правом джойстике и вращении головой. Мой недочёт заключался в том, что координаты джойстика я преобразовывал в углы поворота головы пропорционально. Т.е. центральное положение джойстика соответствовало 90 градусам по горизонтали и 90 градусам по вертикали. Это направление взгляда вперёд. С вертикалью я вру, потому что я вводил программное ограничение по углу поворота по вертикали, и это было не 90 градусов, а середина от амплитуды вертикального отклонения. Но сейчас это не важно, будем считать 90 градусов, потому что мои сервоприводы поворачиваются от 0 до 180 градусов. И что получилось: при координате джойстика (1, 0) голова повёрнута вправо (0 градусов). При координате (0, 1) голова повёрнута вверх (0 градусов). Но если джойстик отклоняется не по горизонтали или вертикали, а по диагонали, голова уже не сможет добраться до нуля градусов ни по одному, ни по другому сервоприводу. Область джойстика окружность, поэтому, например, координата (1, 1) не будет доступна. Отсюда вывод: круговую область джойстика с центром в начале координат и диаметром равным 2 надо «растянуть» на квадратную область с тем же центром и стороной равной 2. Эту задачку я решил для первой половины первого квадранта (от 0 до 45 градусов), остальные решения получались отражениями. Короче говоря, получилось следующее:

x’ = sqrt(x^2 + y^2)
y’ = y * x’ / x
где (x’, y’) новые координаты, растянутые для квадрата, но только для первой половины первого квадранта.

Ну вот, пожалуй, все. Подправив управляемость, поехал хвалиться в офис.

Цена


Хотелось бы предупредить, если у вас есть желание получить удовольствие от процесса создания робота, проявить фантазию, похвастаться друзьям, пока ещё не поздно, советую перейти к заголовку «Планы и заключение». Этот раздел меня тревожит.

Сначала по стоимости деталей непосредственно робота:
Дата покупки Цена, руб. Наименование
21.10.2011 2 590 Четырёхколёсная платформа
21.10.2011 590 Сервопривод
21.10.2011 1 990 Матрёшка Х (Arduino Uno + детали для прототипирования)
26.10.2011 1 200 Сервопривод и кронштейн для него
01.11.2011 0 Аккумуляторные сборки 12В, 1100мАч 2 штуки (подарили)
01.11.2011 850 Держатель автомобильный для HTC Sensation
07.11.2011 1 690 USB Host Shield
21.11.2011 690 2A Motor Shield
21.11.2011 290 Proto Shield
01.12.2011 93 ИК-приёмник TSOP3123
01.12.2011 13 ИК-светодиод TSAL4400
01.12.2011 690 Сервопривод
05.12.2011 886 DC-DC преобразователь TEN 8-1221 TRACO
весь период 1 000 Мелочёвка (флюс, провода, термоусадочные трубки, батарейки и прочее)
Итого 12 572

Вот такая сумма. Цены Московские. Правда, детали можно заказывать и в китайских интернет-магазинах. Там цены отличаются поразительно: получается в два, а то и в три раза дешевле. Но приходится долго ждать. У меня было мало времени, хотя, надо признать, я бы и не вытерпел.

Теперь что я ещё купил или уже имел и без чего робот не поедет:
Дата покупки Цена, руб. Наименование
29.10.2011 1 290 Геймпэд XBOX 360
25.11.2011 3 850 Универсально зарядное устройство IMAX B5
давно 18 900 HTC Sensation (средняя цена по Москве на 19.12.2011 по Яндекс маркету)


Планы и заключение


После двух месяцев полуночной работы, когда я прошёл всё, что описано выше, жена спросила меня: «Нет, я всё понимаю, но что ты просто машинку радиоуправляемую не купишь?».

Пропущу абзац.

Да. Пока то, что у меня есть рано называть роботом. Я это понимаю. Но я думаю, что роботом оно будет. Следующая тема, которую мне интересно поднять, это передача видео и аудио потока от смартфона к ПК. Ну и обратно.

Что хотелось бы сделать дальше, это развивать автономность робота. Сейчас, когда готова мобильная платформа, на «плечах» робота довольно мощная «голова» с языком программирования высокого уровня, плюс можно найти уже готовые открытые алгоритмы распознавания звуков, образов, лиц, перспективы открываются головокружительные. Боюсь даже заглядывать так далеко. Если получится интересно, буду писать дальше.

Надеюсь, мой опыт, набитые мной шишки и подробная граблекарта кому-нибудь послужат.

UPD: Проект перенесён на сервис code.google.com. В семье и среди моих знакомых уже закрепилось имя робота Митя, поэтому проект так и назван: robot-mitya.
Я открыл для просмотра весь исходный код. Здесь все три уровня программирования робота: скетч для Arduino, Android-приложение и Windows-приложение. В качестве системы управления версиями используется Subversion. В папке tag содержится полностью рабочий релиз версии 1.0.0. Его работоспособность я проверял «с нуля» загружая с сервера исходные коды проектов, компилируя их и выполняя на роботе. В папке Trunk, как всегда, текущая ветка проекта.
Arduino-скетч написан на версии IDE arduino-0022. Версию IDE с используемыми мной библиотеками выложил в раздел downloads.
При написании Android-приложения использовалась среда разработки Eclipse IDE for Java Developers версии Indigo Service Release 1 с установленным плагином анализа кода Checkstyle. Единственная поблажка, которую я себе позволил в настройках Checkstyle, это увеличение максимальной длины строки с 80 до 160 символов. Остальные настройки оставил без изменений.
Для разработки Windows-приложения применялась Microsoft Visual C# 2010 Express. Для анализа качества кода использовался StyleCop. Express версия студии не поддерживает встраивания расширений, но использование StyleCop возможно, благодаря возможности его интеграции с MSBuild. Тема замечательно описана в статье StyleCop & C# Express.
Удачи!

Дзахов Дмитрий @DmitryDzz
карма
37,0
рейтинг 0,0
Реклама помогает поддерживать и развивать наши сервисы

Подробнее
Реклама

Самое читаемое

Комментарии (59)

  • 0
    Называть роботов именами становится традицией.
    • +3
      Старался удержать это в себе, но прорвалось из YouTube.
  • +1
    Круто! С радостью почитаю продолжение!
    Мимика у Мити очень интересная, я сам аж загрустил, как увидел на видео его грустную «мордашку».
    Жаль, что статья эта не вышла на день-два раньше…
    • 0
      Спасибо. Я боялся меня за размер статьи сразу застрелят. Хотя, всё ещё впереди.
  • +1
    А почему бы не использовать Bluetooth как канал связи с Arduino? Тогда можно смартфон как угодно крепить, пропало бы множество проблем и не говоря уже о превращении смартфона в джойстик робота.
    • 0
      Bluetooth это очень просто и хорошо, но совершенно не расширяемо =( видео например уже пердать не получится…
      • +2
        Arduino и не снимает видео, это задача смартфона.
        А для передачи сигналов управления и состояния датчиков между Arduino и Android-ом Bluetooth более чем хватит.
        • 0
          Более того, это позволяет избавиться от USB Host shield и проблемы с объеданием тележки сматрфоном )
        • +2
          Мне нравится Ваша идея по использованию Bluetooth. Поддерживаю и думаю, сейчас, я бы так и сделал.
          Но когда я всё это затевал, я думал, что хостом в USB-соединении будет смартфон. Когда эту задачу не осилил, я решил, что с проблемой отключения зарядки смартфона справлюсь без вопросов. Но увы, эту проблему я тоже не смог решить.
          Я осознано описывал все свои ошибки, т.к. уверен, что моя «граблекарта» поможет другим в принятии технических решений.
          • 0
            На самом деле я тоже поначалу на USB Host смотрел.

            Но отпугнула относительно высокая цена, хотелось как можно экономичнее. Да и беспроводная связь несколько больше возможностей давала (например, смартфон как джойстик к роботу).

            Поэтому обратил свой взор на Bluetooth и Wi-Fi (для прочих беспроводных вариантов необходимо значительное усложнение схемы или 2я Arduino, что под экономичность не попадает).

            При этом Bluetooth хоть и обладает незначительным радиусом действия (порядка 10 метров в самом простом варианте), тем не менее подкупает простотой установки и использования, не говоря уже про стоимость порядка 10$.

            Для самоходной платформы хочу Р/У машинку приспособить (купил вездеход Hariot — мало того, что довольно мощная платформа, так еще плавает и стреляет шариками (в моем варианте)).
            Это тебе и Motor Shield, и питание, и сигналы с Р/У пульта можно принимать.

            А установка смартфона позволяет уже и видео писать (спасибо SmartCam, а то уже хотел радио-камеру аналоговую покупать) и управлять по Fi-Wi, не говоря уже про прочие плюшки (GPS, акселерометр, мощный мозг, дисплей (особенно вкусно если есть фронтальная камера), запись / воспроизведение звуков и т.д.).
  • 0
    Как раз тем же занимаюсь)) только платформа из строго игрушечного джипа, а вместо телефона нетбук) и без пушки =(
    • 0
      С нетбуком открывается больше возможностей, в том числе для автономности робота :) Делитесь разработками, когла будет чем делиться!
  • 0
    Согласен, но у меня в дальнейших планах гонять видео и аудио потоки в двух направлениях. Так и так нужен компьютер на другом конце и канал пошире.
    • 0
      В свое времся прикрепил смарт к Р/У машинке и управлял, наблюдая через камеру за движением телефона.
      Для организации передачи видео использовал IP Webcam.
      Из минусов — высокая задержка изображения. По идее надо использовать аналоговую беспроводную камеру.
      • 0
        Сейчас смотрю в похожих приложения проскакивает SmartCam, надо будет попробовать.
        • +1
          Потестил SmartCam — задержка минимальна!
          Правда, разрешение пришлось до 240х160 опустить, но тем не менее этого более чем достаточно для передачи видео.
          А учитывая, что исходники открыты — функцию управления Arduino добавить не составит труда.
  • 0
    после просмотра видео, с начала подумал, что вы сделали искусственный интеллект на подобие собаки айбо, дочитав до контролера от xbox даже немного расстроился
    • 0
      Обязательно постараюсь поработать с ИИ, но эта тема бесконечная, поэтому сначала видео-аудио.
      • 0
        Зато и самая интересная, у меня примерно те же пожелания к своему роботу. Кстати, это робот, просто не автономный. По определению даже манипулятор на производстве, просто держащий заготовку и поворачивающий ее для вытачивания — тоже робот.
  • +1
    Веселый зверек получился.
    поделитесь кодом под Android? Как раз логика, которая появляется при доработке примеров до рабочего состояния и есть самое полезное.
    • +2
      Обязательно. Я планирую немного причесать код и выложить его на code.google.com.
    • 0
      Я выложил исходные коды и под Android, и под Arduino, и под Windows. В конец статьи добавлен раздел UPD с подробностями.
      • 0
        Здорово. кстати, а есть какой-то удобный человеческий интерфейс работы с google code? а то git и mercudrial требуют возни с файлами конфигурации, создают кучу дурацких файлов и папок в структуре проекта в отличие от SVN
        • 0
          А там разве не SVN?
          # Non-members may check out a read-only working copy anonymously over HTTP.
          svn checkout robot-mitya.googlecode.com/svn/trunk/ robot-mitya-read-only

          Кстати, не так давно и SVN (во всяком случае TortoiseSVN) в каждом каталоге создавал по служебной папке.
          • –1
            TortoiseSVN вообще неудобная штука. Ставил, не понравилось. Хочется инструмент, который будет лежать отдельно, без необходимости установки, хранить проекты в папке или файлике/базе, а не создавать кучу мусора в папке проекта.
            • 0
              Не знаю, лично мне TortoiseSVN очень даже нравится.
              Интегрируется с контекстным меню, перевод на Русский (в принципе не обязательно, но приятно), проект практически не засоряет (одна служебная папка не в счет, раньше в каждой папке по служебной было).

              В итоге не надо учить консольные команды, вызывается из любого файлового менеджера (если родное контекстное меню проводника показывается).

              Плюс простота установки и настройки. Поддержка в том числе и локальных проектов (файловый репозиторий, создается буквально в пару кликов). Что еще для счастья надо?
              • 0
                Поддерживаю! Давно работаем с ним. На мой взгляд, надо несколько сжиться с идеологией систем ведения версий, и всё встанет на свои места. А его возможность организовать локальный репозиторий вообще замечательна. Это уже не просто клиент SVN.
              • 0
                Я в последний раз пользовался им два года назад почти, тогда он требовал ставить git, сам был только оболочкой, работал только в explorer, никакого отдельного GUI вменяемого не было. Русификация же — абсолютное зло для разработчика, на мой взгляд.
                • 0
                  вернее не git, а какой-то консольный набор утилит
                  • 0
                    Ну и сейчас он — оболочка над Subversion.
                    Отдельного GUI так и нет, если не считать служебных утилит (а зачем? Вcпомнить SourceSafe от MS — спасибо хоть с VS интеграция, отдельное приложение запущенным держать было бы крайне неудобно).

                    На счет только explorer — любой файловый менеджер, умеющий вызывать «родное» контекстное меню вызывает и его (я Total Commander-ом пользуюсь).
                    И ставить Subversion он не требует, ставится вместе с ним.
                    Если не ошибаюсь, 2 года назад все так же и было.

                    Самое заметное изменения за все время что я им пользуюсь (порядка 3,5 лет) — служебные папки объединили в одну.

                    При этом TortoiseSVN с самого начала казался очень удобным.
                    • 0
                      поставил посмотреть :)
        • 0
          SabMakc прав, у меня используется репозиторий SVN. Google предлагает три варианта репозиториев. Мне привычен SVN, поэтому его и выбрал. Для работы использую Черепашку. В Eclipse — плагин Subversive SVN. В MS Visual C# Express студии, к сожалению, не ставятся расширения. В Arduino IDE некуда :). Поэтому приходится через Черепашку. У Вас, кажется, Delphi (я подглядел в комментариях Вашей последней статьи), для него тоже есть плагины, но мне не приходилось их использовать.
          • –1
            Я использовал RapidSVN в качестве клиента, вернее пробовал использовать, но в терминах этих версионных систем не разобрался. Сравнить изменения и документировать разницу версий в них неудобно и вообще непонятно как. А в остальном от них пользы не нашлось. В итоге проще архивировать версии просто RAR/ZIP. в итоге забросил использование систем версионности.
  • 0
    >>> жена спросила меня: «Нет, я всё понимаю, но что ты просто машинку радиоуправляемую не купишь?».
    ох уж эти женщины, им этого не понять )))

    >>> Пока то, что у меня есть рано называть роботом.
    Вы себя недооцениваете, получилось просто здоровски, особенно эти улыбочки, если детально проработать передачу эмоций, то будет просто обалденно. Например разогнался ехал, ехал, а тут бац преграда, загрустил, остановился, покрутился увидел создателя :D улыбнулся, поехал к нему завилял хвостиком ))) Увидел «врага», оскалился…
    Для распознавания образов мощности вашего телефончика должно быть достаточно, а тема это очень интересная, есть готовые решения. Темболее ваша связка уже позволяет решать задачи такого уровня.

    >>> Если получится интересно, буду писать дальше.
    Пишите обязательно! Очень интересно.

    Кстати, вместо дорогого смартфона можно тоже взять что-то китайское подешевле в случае чего и спалить не жалко и бюджет меньше будет.
    • 0
      Спасибо. Очень хорошая мысль с использованием эмоций. Кстати, аппаратно, у меня уже есть дальномер — пушка и приёмник. Их вполне можно использовать.
  • +2
    «ИК-светодиод работает на 100мА, и пиковых 200мА, поэтому его можно смело включать прямо на цифровой выход Arduino (без резистора), а обвязка фотоприёмника указана в его»

    Выход Mega168 не тянет более 40мА. Так что без ограничительного резистора включать его нельзя.
    • 0
      Вы совершенно правы, я ошибся. Причём сначала хотел сразу возразить, потом решил поднять эту тему. Вот здесь этот вопрос поднимается. Явного ответа я не увидел, но сомнение закралось. Заинтересовался, какой ток будет у горящего ИК-диода. Именно моего: TSAL4400. Воткнул его на второй пин и землю, написал и загрузил такой скетч:

      void setup() {
      pinMode(2, OUTPUT);
      digitalWrite(2, HIGH);
      }

      void loop() {
      }


      Замерил ток — 82 мА! Превышение допустимого тока в 2 раза! Последовательно включенное сопротивление в 80 Ом обеспечивает ток порядка 35 мА. Видимо, для этого светодиода лучше поставить транзистор, чтобы вывести его штатные 100 мА.
      • 0
        С транзистором вы можете сжечь его вообще. Тут надо ставить транзистор и ограничительный резистор, расчитанный таким образом:

        (Напряжение питания — 0.7 — Uпадения диода)/Iсветодиода

        0.7 — примерное падение на транзисторе
        напряжение падениян на светодиоде смотрите в его ДШ.
        • 0
          Конечно с резистором. Я имею в виду то, что ток всё-таки надо подтягивать до штатных 100 мА ИК-светодиода. Иначе радиус пушки будет ограничен. Мы с приятелем столкнулись с этим на стенде, когда подключали светодиод к пину Arduino через резистор.
    • 0
      Спасибо, топик я исправил.
  • +1
    Помехи от движков возникли не изза их мощи, а изза криво разведенной земли. По хорошему у движков земля должна быть своя, и ветка питания своя. Пусть и с одного источника, но браться должна она от клеммы батареи, тогда все броски движка замкнутся на батарею по большей части и не будут гулять по цифровым схемам.
    • 0
      Именно так и было. Всё нормализовалось только после гальванической развязки благодаря DC-DC преобразователю.
      • 0
        DC-DC не дает гальванической развязки.
        • 0
          Гм… Я так понимал, что DC-DC преобразователи дают гальваническую развязку. Посмотрел datasheet моего TEN 8-1221. Там написано: «Typical applications for these converters are battery operated equipment, instrumentation, communication and industrial electronics, everywhere where isolated, tightly regulated voltages are required and space is limited on the PCB».
          "… isolated… voltages ..." я понял как развязку.
  • +1
    Ура, я тоже решил делать на основе смартфона :). Классная статья!
  • +1
    Вот, что вам было нужно. Специально для Android.
    Arduino Mega ADK
    • 0
      Точно, но она попозже появилась. Или я не знал о ней ничего поначалу. Но её минус — размер. Я прикидывал по габаритам, любая Мега чуть ли не торчит краями из моей тележки. А Мега-сила в том, что ног у контроллера тьма. Вот тут меня брала зависть. Можно ведь, и манипулятором тогда озаботиться.
      • 0
        Есть Seeeduino Mega.
        По размерам — практически как стандартная плата.
  • 0
    Робитвы!
  • 0
    А где видео РобоБитвы? Или хотя бы какой её результат? Не верю, что никто её не снимал!
    • 0
      Ну, тут прокол. Действительно не снимали. В конце сделали фото.

      Коллективное фото

      Противник (фото 1)

      Противник (фото 2)
      • +4
        Вижу у противника одну критическую уязвимость — проезжая «впритык» его можно выключить )
  • 0
    По размышлении над статьёй и комментариями появилась пара идей. Я по робототехнике почти ничего не знаю, поэтому в случае неосуществимости чего-либо из мною перечисленного (в чём я серьёзно сомневаюсь), прошу об этом открыто сказать.
    Как я понимаю, в случае передачи данных по Wi-Fi, вполне можно передавать видео. Так почему бы не сделать полное управление с компьютера/ноута, где не нужен будет визуальный контакт с роботом? В случае вида от первого лица можно использовать встроенную камеру смартфона. А если хочется вид от третьего (Есть свои плюсы, например, больший радиус обзора) — на жёсткой фиксации вынести камеру назад сантиметров на 20 и чуть-чуть вверх. И с управлением не надо шибко мудрить, всё уже придумано до нас. Управление камерой (головой и пушкой, соответственно) с мыши, а телегой — независимо, с клавиатуры. {можно программно добавить скорость разгона и инерционность движения, чтобы не «с места в галоп» и тормозило постепенно}
    Ну и как фееричное дополнение — управление с планшета. Получается более активное, но и более интересное. Допустим, под левым пальцем управление телегой типа «джойстик», под правым — выстрел и смена настроений, а поворот головы — за счёт встроенного G-датчика (или GPS. Или компаса. Смотря что подойдёт). А на экран, конечно же, изображение с камеры робота. Сделав несколько таких можно устраивать настоящий дефматч.
    Если какие-то идеи заинтересовали — пишите мне, обсудим более подробно. Хотя обсуждать тут, наверное, для сообщества будет полезнее. ;-)
    • +1
      Думаю, будет интересно почитать про проект КиберЗона (roboforum.ru, офф. сайт).
      • 0
        Хммм… Интересная штука. Только мне не совсем нравится, что корпус полностью поворачивается. Хотелось бы, чтобы управление движением было независимое… Может, себе тоже такое хобби завести? ))
        • 0
          На сколько я читал, они и изначально были с поворотной головой.
          Но выяснилась проблема: очень неудобно управлять неподготовленному оператору, он не может определить, в какую сторону повернуто туловище, в какую — тело.
          В результате данную возможность оставили на светлое будущее.
          • 0
            Ага. В этом случае очень бы помогла «вынесенная камера». Из глаз — действительно сложно… если нет никаких меток.
  • 0
    Скажите, а можно использовать USB Host Shield без Arduino?

    Идея в том чтобы управлять датчиками и моторами напрямую из Android смартфона.
    • 0
      Им должен кто-то управлять. Нет, теоретически, USB Host Shield можно прикрутить к другому контроллеру, но только если есть большой спортивный интерес. А так, он ориентирован именно на Arduino.
      Мне кажется, Вашу задачу проще и дешевле решить именно с Arduino.
      Если Вас беспокоят габариты решения в моём роботе, то посмотрите такой вариант: Arduino Mini + Bluetooth Module.
      Я как раз жду именно из этого магазина такие штучки. Есть одна идея :)
      Если надумаете, почитайте ещё тут. У Arduino Mini есть особенности.

Только зарегистрированные пользователи могут оставлять комментарии. Войдите, пожалуйста.