Робо-сумо: интеллектуальные бои роботов

nrgsdnftljv5waitpfgsyj2bi1a.jpeg


(с)

Каждый год около тысячи команд со всей Японии вступают в ожесточенное сражение на турнире роботов. В этом состязании вы не увидите бензопил, факелов и электрических разрядов — словом, ничего из того, что приходит в голову, когда вы слышите фразу «битва роботов».

Речь идет не просто о битве — это робо-сумо, которое ценят за особые качества: за элегантность, простоту и возможность проявить интеллект в стратегии. Соревнование проходит на круглом металлическом ринге диаметром всего 1,5 м, по периметру которого нарисована белая линия шириной 5 см. Робот, пересекший эту границу, считается проигравшим. И в этой кажущейся простоте кроется бездна возможностей.

Расскажем, как «битва роботов» стала интеллектуальным соревнованием для программистов, и дадим подробную инструкцию по сборке робо-сумоиста.


ek0of6voomon9zwae1knc5eqxi0.jpeg


(с)

Глаза робота — датчики инфракрасного излучения. Степень ИК-отражения измеряется светочувствительным элементом. Белый цвет границы выбран не случайно — он отражает больше света, чем черная поверхность ринга.

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

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



Помимо перечисленных преимуществ, у ИК-датчиков есть и недостаток — поле зрения остается узким, за счет чего появляется множество слепых зон, использование которых в атаке — основная стратегия высокоманевренных роботов.

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

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

Однако чтобы запутать противника некоторые бойцы выбрасывают белые флаги с одной или с двух сторон корпуса. Заманивая противника к флагу, они атакуют его уязвимую сторону и выталкивают с ринга.

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

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



Битва роботов сумоистов — это не просто бодание. Многие из них оснащены бульдозерным отвалом с острым краем. Он позволяет приподнять соперника и вынести его за пределы площадки или даже нанести серьезный урон. Правда, это орудие снижает маневренность бойца.

В человеческом сумо главным оружием борца служит его внушительная масса. Как ни странно, у роботов масса тоже играет «весомую роль».

Несмотря на то что, согласно правилам, длина робота (любой стороны) не превышает 20 см, а вес должен быть не более 3 кг, робо-сумоист может «весить» несколько десятков килограмм. Этот «вес» достигается за счет магнитов. Да, техника порой может практически «прилипать» к полу, поскольку в основе ринга металлическая поверхность.


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

Главное для сумо-роботов — стратегия, записанная в виде кода. От нее зависит и выбор железа. Часто роботы двигаются настолько быстро, что за их передвижениями трудно уследить. Однако в основе сверхманевренного поведения лежит строгая логика программы. Рассмотрим, по каким принципам она создается.


1u8my2ak5xjtimpvwbylekjndli.jpeg


Обратимся к опыту экспертов с площадки hackster.io, подготовивших исчерпывающий гайд по созданию типового робота-сумоиста.

В проекте используются следующие комплектующие:

  • контроллер CytronTechnologies × 1;
  • инфракрасный датчик (3—80 см) × 5;
  • набор силиконовых колес JSumo (52 х 30 мм) × 2;
  • модуль отслеживания ИК-линии × 2;
  • DC мотор-редуктор (12 В, 380 об/мин) × 4;
  • LiPo-аккумулятор (11,1 В, 1300 мАч) × 1.


g5dboqmnosekv6amnb9bmm08a8e.jpeg


1. Контроллер


Вы можете использовать Arduino Uno, Mega или Nano. Также потребуется плата для подключения всех датчиков. Можно, конечно, создать свою собственную плату расширения и подключить все контакты к Arduino, или купить готовую плату и подключить все электронные компоненты.

flt3nchzsgz_89yjctjw7bm8wm8.jpeg


2. Двигатель


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

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

Двигатель с цилиндрической зубчатой передачей и планетарной передачей, в которых выходной вал расположен параллельно двигателю.

-9j2s5x0gtegpfde2nxjxrm-gc8.jpeg


Двигатель с червячной передачей. Выходной вал здесь расположен перпендикулярно. Этот вариант может быть предпочтительнее, поскольку в роботе останется больше места для других компонентов.

pt4yujcxbkaj9opjvjhux-o1iyq.jpeg


Двухколесный привод против четырехколесного


Привод на четыре колеса определенно даст больше возможностей в толкании робота-оппонента. Однако его мобильность ниже, чем у двухколесного. И все же в этом демонстрационном проекте использовался полный привод.

3. Колеса


jva2yxjwj1tfbv23hcb5mxwtzum.jpeg


На рынке не так много вариантов хорошей резины для сумо-робота. Инженеры остановили свой выбор на силиконовых колесах производства Jsumo. Однако вы можете использовать колеса от игрушечной машинки.

Обратите внимание на крепление — убедитесь, что выбранное колесо совпадает с размером отверстия, соответствующего выходному валу двигателя. В этом проекте используется 6-миллиметровый вал, соответственно, колесо имеет 6-миллиметровое отверстие.

4. Датчики


t152u19gnj9qysuht_pzcdegvh4.jpeg


Для обнаружения объектов можно использовать как инфракрасные датчики, так и, например, ультразвуковые.

Эксперты рекомендуют начинать атаку, когда расстояние до противника не более 60 см. Таким образом, можно размещать датчик с диапазоном чувствительности до 1 м.

vqe66d1chq4snljxlawfnxuj30o.jpeg


Для этого робота установили три инфракрасных датчика — по одному на сторону.

ffl_rzkqyuc0rh_a01nkk65kjle.jpeg


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

5. Батарея


mnn_mytyprs9rzom7bfxh2dkdka.jpeg


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

6. Шасси робота


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

vw2essnx2b_kognkrzp6ewxijji.jpeg


Поскольку 3D-печать более экономична, диайвайщики поделились файлами для домашней печати.

eqwzefn44wv0rel76tbftaqumeo.jpeg


7. Сборка


На диаграмме и в таблице ниже представлен обзор проводных соединений для робота-сумо.

c6xkzv3frpxbywkar-q3n0w9gjq.jpeg


3jm9m8cq7h3htbvldjo8qrtb9cm.jpeg


Для начала следует припаять два провода (рекомендуемый размер — 16—18 AWG) к клемме двигателя, чтобы затем подключить его к контроллеру.

dj0sfbhufflgr7upuyoh4nhhsgi.jpeg


Далее все двигатели и датчики требуется спаять с проводами.

s77qtrxyy2zzicdk-wwz2rnlvyo.jpeg


Теперь переходим к сборке внутри корпуса. С помощью болтов M3x10 установите двигатели на нижний корпус.

je3fnoqttd6oyj1c7vg7zshxqwo.jpeg


Установите инфракрасные датчики с правой и левой стороны.

5vdxn-rpz0sw4za6yskcba91cag.jpeg


Закрепите обод колеса с помощью винта M4, затем наденьте силиконовую ленту.

Установочный винт необходимо закрепить на плоской части круглого вала двигателя.

romcabxwooiznvut63xyfm59ij4.jpeg


Затем с помощью самореза установите краевой датчик в нижней части отвала.

21ylkjt-lmxt0smqmrnbxxnjjx8.jpeg


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

junhv-45aeai6rmzntv9qoq-s0m.jpeg


Соберите отвал с нижним кожухом, используя болты и гайки M6x20.

lsbtn78muttxvjmhzyn3w_bba3y.jpeg


Установите инфракрасные датчики на переднем держателе, прежде чем прикрепить его к нижнему корпусу.

2ggsfxsyoiwiuwwda0qum4wjwsw.jpeg


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

ijo4r0s8yph7u3b8o-glzq3xcve.jpeg


Закрепите поддерживающую опору для печатной платы.

kfd5xngllb_twbih3uhoquqyumc.jpeg


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

ejyjj0z96-8ysqplipog6neme4c.jpeg


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

f4xy521dq26dqntjh7iw61snxrk.jpeg


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

e_q8jjwaexdvykcdzvhaxx6gbba.jpeg


Наконец, подключите аккумулятор.

tdlroezeyszwejm5pybh3mgqpwk.jpeg


Сумо-робот готов!

8. Калибровка датчиков


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

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

Максимальный диапазон чувствительности датчика поиска противника — 80 см. В этом проекте робот не должен реагировать на объект, который находится на расстоянии 60—80 см, поэтому диапазон чувствительности уменьшают на 20 см.


Для этого нужно поставить робота «лицом» к плоской поверхности белого цвета на расстоянии 60 см и настраивать датчик до тех пор, пока светодиодный индикатор не погаснет. Более подробно процедура показана на видео.

p2g9nzdafssby3tkvlrxl0obm4y.jpeg


Датчики края настраиваются с помощью отвертки через отверстие в отвале.

С помощью софта можно отобразить сигналы двух краевых датчиков на светодиоды D0 и D1.


Это нужно для того, чтобы убедиться, что датчик дает высокий выходной сигнал, когда воспринимает белую поверхность, и низкий — на поверхности черного цвета (обратите внимание на светодиоды на D0 и D1 в видео выше).

9. Программирование


Поскольку контроллер робота URC10 совместим с Arduino UNO, для программирования используется Arduino IDE. Вы можете взять готовый пример кода.

Единственная библиотека, используемая в проекте, — CytronMotorDrivers.

Если не знаете, как включить библиотеку или загрузить пример кода, обратитесь к мануалу URC10.

Программу сумо-робота в основном можно разделить на четыре части:

  • старт выступления;
  • поиск;
  • атака;
  • отступление.
void loop() {
  // Обнаружение края слева.
  if (!digitalRead(EDGE_L)) {
    // Отступить и сделать разворот вправо.
    backoff(RIGHT);
 
    // Переключить направление поиска.
    searchDir ^= 1;
  }
 
  // Обнаружение края справа.
  else if (!digitalRead(EDGE_R)) {
    // Отступить и сделать разворот влево.
    backoff(LEFT);
 
    // Переключить направление поиска.
    searchDir ^= 1;
  }
 
  // Край не обнаружен.
  else {
    // Продолжать поиск, если противник не обнаружен.
    if ( digitalRead(OPPONENT_FC) &&
         digitalRead(OPPONENT_FL) &&
         digitalRead(OPPONENT_FR) &&
         digitalRead(OPPONENT_L) &&
         digitalRead(OPPONENT_R) ) {
      search();
    }
 
    // Атаковать, если противник находится в поле зрения.
    else {
      attack();
    }
  }
 
 
  // Остановить робота при нажатии кнопки.
  if (!digitalRead(BUTTON)) {
    // Остановить моторы.
    motorL.setSpeed(0);
    motorR.setSpeed(0);
 
    // Цикл.
    while (1);
  }
}


Стратегия старта зависит от правил соревнования. Робот может начать двигаться только через 5 секунд, а иногда — за 1 секунду.

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

В этом примере робот запрограммирован перемещаться и атаковать противника сбоку, как только игра начнется.

void startRoutine() {
  // Задержка.
  delay(1000);
 
  // Повернуть направо на 45 градусов.
  motorL.setSpeed(255);
  motorR.setSpeed(0);
  delay(180);
 
  // Двигаться прямо.
  motorL.setSpeed(255);
  motorR.setSpeed(255);
  delay(450);
 
  // Поворачивать налево, пока противник не будет обнаружен.
  motorL.setSpeed(-0);
  motorR.setSpeed(255);
  uint32_t startTimestamp = millis();
  while (digitalRead(OPPONENT_FC)) {
    // Выйти, если противник не найден после истечения времени ожидания.
    if (millis() - startTimestamp > 400) {
      break;
    }
  }
 
}



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

void search() {
  // Двигаться по кругу.
  if (searchDir == LEFT) {
    motorL.setSpeed(100);
    motorR.setSpeed(255);
  } else {
    motorL.setSpeed(255);
    motorR.setSpeed(100);
  }
}



При обнаружении противника одним из пяти датчиков, робот поворачивается в его сторону и на полной скорости атакует.

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

void attack() {
  uint32_t attackTimestamp = millis();
  // Противник впереди по центру.
  // Двигаться прямо на полной скорости.
  if (!digitalRead(OPPONENT_FC)) {
    motorL.setSpeed(255);
    motorR.setSpeed(255);
  }
 
  // Противник впереди слева.
  // Повернуть налево.
  else if (!digitalRead(OPPONENT_FL)) {
    motorL.setSpeed(0);
    motorR.setSpeed(255);
  }
 
  // Противник впереди справа.
  // Повернуть направо.
  else if (!digitalRead(OPPONENT_FR)) {
    motorL.setSpeed(255);
    motorR.setSpeed(0);
  }
 
  // Противник сбоку слева.
  // Поворачивать влево до тех пор, пока противник не окажется впереди.
  else if (!digitalRead(OPPONENT_L)) {
    motorL.setSpeed(-150);
    motorR.setSpeed(150);
    while (digitalRead(OPPONENT_FC)) {
      // Выйти, если противник не найден.
      if (millis() - attackTimestamp > 400) {
        break;
      }
    }
  }
 
  // Противник сбоку справа.
  // Поворачивать вправо до тех пор, пока противник не окажется впереди.
  else if (digitalRead(OPPONENT_R) == 0) {
    motorL.setSpeed(150);
    motorR.setSpeed(-150);
    while (digitalRead(OPPONENT_FC)) {
      // Выйти, если противник не найден.
      if (millis() - attackTimestamp > 400) {
        break;
      }
    }
  }
}



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

void backoff(uint8_t dir) {
  // Остановить двигатели.
  motorL.setSpeed(0);
  motorR.setSpeed(0);
  delay(100);
 
  // Реверс.
  motorL.setSpeed(-255);
  motorR.setSpeed(-255);
  delay(200);
 
  // Остановить двигатели.
  motorL.setSpeed(0);
  motorR.setSpeed(0);
  delay(100);
 
  // Повернуться.
  if (dir == LEFT) {
    motorL.setSpeed(-150);
    motorR.setSpeed(150);
  } else {
    motorL.setSpeed(150);
    motorR.setSpeed(-150);
  }
  delay(100);
 
  // Начать искать противника
  // Установить тайм-аут после короткого периода.
  uint32_t uTurnTimestamp = millis();
  while (millis() - uTurnTimestamp < 300) {
    // Противник будет обнаружен, если сработает один из датчиков.
    if ( !digitalRead(OPPONENT_FC) ||
         !digitalRead(OPPONENT_FL) ||
         !digitalRead(OPPONENT_FR) ||
         !digitalRead(OPPONENT_L) ||
         !digitalRead(OPPONENT_R) ) {
      // Остановить двигатели.
      motorL.setSpeed(0);
      motorR.setSpeed(0);
      delay(100);
 
      // Вернуться в основной цикл.
      return;
    }
  }
 
  // Если противник не найден, нужно двигаться вперед и продолжать поиск в основном цикле.
  motorL.setSpeed(255);
  motorR.setSpeed(255);
  delay(200);
}



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


У вас уже есть опыт сборки робота для аналогичных состязаний? Поделитесь в комментариях выигрышными стратегиями.
DIY-сборка робота: https://www.hackster.io/cytron-technologies/building-a-sumo-robot-45d703

Всеяпонский национальный конкурс роботов по сумо: http://www.fsi.co.jp/sumo/en/index.html

Иллюстрированный набор правил: http://www.robotroom.com/SumoRules.html

© Habrahabr.ru