Проект 5: Ультразвуковой дальномер RCWL-9610A
Введение
Представьте, что ваш робот Phobo может «видеть» препятствия на своём пути, как летучая мышь использует эхолокацию! В этом уроке мы научим Arduino измерять расстояние до объектов с помощью современного ультразвукового датчика RCWL-9610A.
RCWL-9610A — это электронные «глаза» вашего робота. Он посылает ультразвуковой сигнал (как писк летучей мыши, только мы его не слышим), сигнал отражается от препятствия и возвращается обратно. Arduino измеряет время и вычисляет расстояние до объекта.
Зачем это нужно?
Робот сможет объезжать препятствия
Робот не упадёт с края стола
Можно создать парковочный радар
Можно измерять уровень воды в баке
В будущем датчик будет вращаться на сервоприводе, сканируя пространство!
Примечание
Важно: В этом проекте впервые устанавливаем библиотеку AlashUltrasonic!
Что такое RCWL-9610A?
О датчике
RCWL-9610A — это современная версия популярного датчика HC-SR04, выпущенная в 2022 году. Это улучшенный модуль с дополнительными возможностями, но мы будем использовать его в классическом режиме GPIO, который полностью совместим со старым HC-SR04.
Главные преимущества RCWL-9610A перед старым HC-SR04:
✅ Гибкое питание: работает от 3V до 5V (старый HC-SR04 требует строго 5V)
✅ Больший радиус действия: до 450 см вместо 400 см
✅ 4 режима работы: GPIO (как HC-SR04), I2C, UART, 1-Wire
✅ Улучшенная схемотехника: более стабильные измерения, меньше помех
✅ Обратная совместимость: работает с любым кодом для HC-SR04
Примечание
О режимах работы: На обратной стороне модуля есть контактные площадки M1 и M2 для выбора режима. По умолчанию обе площадки не запаяны — это режим GPIO (Trig/Echo), который мы и будем использовать. В будущих продвинутых проектах можно переключить датчик на режим I2C или UART для экономии пинов Arduino.
Технические характеристики
Модель: RCWL-9610A (версия 2022 года)
Рабочее напряжение: 3V - 5V (мы используем 5V от Arduino)
Рабочий ток: 15 mA (очень экономичный!)
Рабочая частота: 40 кГц (ультразвук, не слышим ушами)
Дальность измерения: от 2 см до 450 см (4.5 метра!)
Точность: ±3 мм (очень точный!)
Угол обзора: 15° (узкий луч, как фонарик)
Режимы работы: GPIO / I2C / UART / 1-Wire (мы используем GPIO)
Размер: 45×20×15 мм
Вес: 9 грамм (лёгкий, как две карамельки)
Совместимость: 100% совместим с кодом для HC-SR04
Как работает датчик?
RCWL-9610A в режиме GPIO имеет 4 вывода:
VCC — питание +5V (красный провод)
Trig (Trigger) — запускает измерение (любой цвет)
Echo — принимает отражённый сигнал (любой цвет)
GND — земля, минус питания (чёрный провод)
Процесс измерения (в режиме GPIO):
Arduino подаёт короткий импульс (10 микросекунд) на вывод Trig
RCWL-9610A посылает 8 ультразвуковых импульсов частотой 40 кГц
Ультразвук летит до препятствия и отражается обратно
RCWL-9610A принимает отражённый сигнал и подаёт сигнал на вывод Echo
Arduino измеряет, сколько времени был активен сигнал Echo
По времени вычисляется расстояние
Формула:
Расстояние (см) = Время (микросекунды) / 58.2
Почему делим на 58.2? Скорость звука ~340 м/с, звук летит туда и обратно (×2), плюс перевод единиц. Но не волнуйтесь — библиотека всё посчитает за нас!
Примечание
Интересный факт: Летучие мыши используют такой же принцип! Они издают ультразвуковые писки и по эху «видят» мир. Это называется эхолокация. Наш робот Phobo будет использовать такую же технологию!
Установка библиотеки AlashUltrasonic
Библиотека — это готовый набор команд для работы с устройством.
Аналогия: Представьте, что вы готовите пельмени. Можно лепить их вручную (долго и сложно), а можно купить готовые замороженные и просто сварить (быстро и просто). Библиотека — это «готовые пельмени» для программиста! 🥟
Используем библиотеку AlashUltrasonic — поддерживает HC-SR04 и RCWL-9610A во всех режимах (GPIO, I2C, UART, 1-Wire).
Установка: Library Manager → поиск AlashUltrasonic → Install
Подробная инструкция по установке библиотек — см. Урок 1.
Подключение
Робот собран в Проекте 1. RCWL-9610A подключен к Sensor Shield:
Trig → D3
Echo → D7
Примечание
Режим GPIO: контакты M1 и M2 на обратной стороне датчика не запаяны.
Программирование
Теперь напишем программу, которая будет измерять расстояние и выводить его в монитор порта.
Код программы
Шаг 1: Откройте Arduino IDE
Шаг 2: Создайте новый скетч: Файл → Создать
Шаг 3: Скопируйте и вставьте следующий код:
/*
* Проект 5: Ультразвуковой дальномер RCWL-9610A
* Робот Phobo — Alash Electronics
*
* Датчик RCWL-9610A (режим GPIO) измеряет расстояние до препятствий
* и выводит результат в монитор порта
*/
#include <AlashUltrasonic.h> // Подключаем библиотеку
// Задаём номера пинов
const uint8_t TRIGGER_PIN = 3; // Trig на D3
const uint8_t ECHO_PIN = 7; // Echo на D7
// Создаём объект датчика
AlashUltrasonic sensor(TRIGGER_PIN, ECHO_PIN);
void setup() {
// Запускаем монитор порта со скоростью 9600
Serial.begin(9600);
// Инициализируем датчик
sensor.begin();
Serial.println("=== Робот Phobo: Ультразвуковой дальномер ===");
Serial.println("Измеряем расстояние до препятствий...");
Serial.println();
}
void loop() {
// Измеряем расстояние в сантиметрах
float distance = sensor.getDistance();
// Выводим результат в монитор порта
Serial.print("Расстояние: ");
Serial.print(distance);
Serial.println(" см");
// Задержка 500 мс (0.5 секунды) между измерениями
delay(500);
}
Объяснение кода
Давайте разберём код построчно:
1. Подключение библиотеки:
#include <AlashUltrasonic.h>
#include — команда «включить» библиотеку. Теперь мы можем использовать готовые функции для работы с RCWL-9610A (и HC-SR04).
2. Определение пинов:
const uint8_t TRIGGER_PIN = 3; // Trig на D3
const uint8_t ECHO_PIN = 7; // Echo на D7
const uint8_t — константа (неизменяемое значение) типа «беззнаковое 8-битное целое число»
TRIGGER_PIN и ECHO_PIN — имена констант (традиционно пишутся БОЛЬШИМИ_БУКВАМИ)
= 3 и = 7 — значения пинов на Arduino
Зачем так делать? Если позже захотим изменить пины, достаточно поменять цифры здесь, а не искать их по всему коду!
3. Создание объекта датчика:
AlashUltrasonic sensor(TRIGGER_PIN, ECHO_PIN);
AlashUltrasonic — тип объекта (класс из библиотеки)
sensor — имя нашего датчика (можно назвать как угодно)
(TRIGGER_PIN, ECHO_PIN) — передаём номера пинов через константы
Аналогия: Это как назвать своего робота-пылесоса «Вася» — теперь вы можете говорить «Вася, убери комнату», и он поймёт команду. Здесь мы создали датчик по имени sensor и сказали ему, к каким пинам подключён.
4. Функция setup() — выполняется один раз при включении:
void setup() {
Serial.begin(9600);
sensor.begin();
Serial.println("=== Робот Phobo: Ультразвуковой дальномер ===");
}
Serial.begin(9600) — запускает связь Arduino с компьютером со скоростью 9600 бит/сек
sensor.begin() — важно! Инициализирует датчик, настраивает пины Trig и Echo
Serial.println(...) — выводит текст в монитор порта
5. Функция loop() — повторяется бесконечно:
void loop() {
float distance = sensor.getDistance();
Serial.print("Расстояние: ");
Serial.print(distance);
Serial.println(" см");
delay(500);
}
float distance — создаём переменную для хранения расстояния (тип float — число с плавающей точкой, может быть 12.5, 34.8 и т.д.)
sensor.getDistance() — главная функция библиотеки! Измеряет расстояние и возвращает результат в сантиметрах
Serial.print(...) — выводит текст БЕЗ переноса строки
Serial.println(...) — выводит текст С переносом строки
delay(500) — ждёт 500 миллисекунд (0.5 секунды)
Примечание
Почему delay(500)? RCWL-9610A может измерять до 50 раз в секунду, но нам не нужно так часто. 2 измерения в секунду (каждые 500 мс) — оптимально для наблюдения за данными в мониторе порта.
Загрузка и тест
Загрузите код (без батарей!)
Откройте Serial Monitor (9600 baud)
В мониторе порта должны появиться строки:
=== Робот Phobo: Ультразвуковой дальномер ===
Измеряем расстояние до препятствий...
Расстояние: 45 см
Расстояние: 45 см
Расстояние: 23 см
Расстояние: 12 см
Расстояние: 12 см
Попробуйте: Поднесите руку к датчику — цифры должны уменьшаться. Отведите руку — цифры увеличиваются!
Эксперименты
Теперь, когда датчик работает, попробуем несколько интересных экспериментов с визуализацией в мониторе порта!
Эксперимент 1: Парковочный радар для робота
Задача: Создать систему парковки задним ходом для робота Phobo. Представьте, что робот едет назад к стене и датчик измеряет расстояние. Программа должна рекомендовать безопасную скорость движения и предупредить, когда нужно остановиться.
Логика работы:
Более 50 см: Можно ехать назад быстро (5 км/ч)
30-50 см: Средняя дистанция, снизить скорость (3 км/ч)
15-30 см: Близко к препятствию, ехать медленно (1 км/ч)
Менее 15 см: СТОП! Остановить машину
Полный код:
/*
* Эксперимент 1: Парковочный радар робота Phobo
* Измеряет расстояние и выводит рекомендуемую скорость
*/
#include <AlashUltrasonic.h>
const uint8_t TRIGGER_PIN = 3;
const uint8_t ECHO_PIN = 7;
AlashUltrasonic sensor(TRIGGER_PIN, ECHO_PIN);
void setup() {
Serial.begin(9600);
sensor.begin();
Serial.println("=== Phobo Parking Radar ===");
Serial.println("Система помощи при парковке задним ходом");
Serial.println();
}
void loop() {
float distance = sensor.getDistance();
// Выводим текущее расстояние
Serial.print("Расстояние до препятствия: ");
Serial.print(distance);
Serial.println(" см");
// Рекомендуемая скорость в зависимости от расстояния
if (distance < 2 || distance > 450) {
Serial.println("⚠️ Датчик вне диапазона!");
}
else if (distance >= 50) {
Serial.println("✅ Путь свободен! Можно ехать назад.");
Serial.println("🚗 Рекомендуемая скорость: 5 км/ч");
}
else if (distance >= 30) {
Serial.println("⚠️ Препятствие обнаружено на средней дистанции.");
Serial.println("🚗 Рекомендуемая скорость: 3 км/ч");
}
else if (distance >= 15) {
Serial.println("⚠️ ВНИМАНИЕ! Препятствие близко!");
Serial.println("🐌 Рекомендуемая скорость: 1 км/ч (медленно)");
}
else {
Serial.println("🛑 СТОП! ОСТАНОВИТЬ МАШИНУ!");
Serial.println("❌ Расстояние менее 15 см - опасность столкновения!");
}
Serial.println("-----------------------------------");
delay(1000); // Обновление каждую секунду
}
Что должно получиться:
Поставьте датчик перед стеной на расстоянии ~70 см и медленно приближайте его к стене. В мониторе порта вы увидите, как система предупреждает о приближении и рекомендует снижать скорость!
Пример вывода:
=== Phobo Parking Radar ===
Система помощи при парковке задним ходом
Расстояние до препятствия: 65 см
✅ Путь свободен! Можно ехать назад.
🚗 Рекомендуемая скорость: 5 км/ч
-----------------------------------
Расстояние до препятствия: 35 см
⚠️ Препятствие обнаружено на средней дистанции.
🚗 Рекомендуемая скорость: 3 км/ч
-----------------------------------
Расстояние до препятствия: 20 см
⚠️ ВНИМАНИЕ! Препятствие близко!
🐌 Рекомендуемая скорость: 1 км/ч (медленно)
-----------------------------------
Расстояние до препятствия: 12 см
🛑 СТОП! ОСТАНОВИТЬ МАШИНУ!
❌ Расстояние менее 15 см - опасность столкновения!
-----------------------------------
Эксперимент 2: Графический индикатор расстояния
Задача: Создать визуальную шкалу расстояния в мониторе порта с помощью символов █. Чем ближе препятствие, тем короче «полоска». Это похоже на индикатор уровня громкости или заряда батареи!
Диапазон: от 2 см (минимум) до 50 см (максимум)
Полный код:
/*
* Эксперимент 2: Графический индикатор расстояния
* Визуализация расстояния в виде полоски из символов
*/
#include <AlashUltrasonic.h>
const uint8_t TRIGGER_PIN = 3;
const uint8_t ECHO_PIN = 7;
AlashUltrasonic sensor(TRIGGER_PIN, ECHO_PIN);
void setup() {
Serial.begin(9600);
sensor.begin();
Serial.println("=== Phobo Distance Indicator ===");
Serial.println("Графический индикатор расстояния (2-50 см)");
Serial.println();
}
void loop() {
float distance = sensor.getDistance();
// Ограничиваем диапазон от 2 до 50 см
if (distance < 2) distance = 2;
if (distance > 50) distance = 50;
// Выводим числовое значение
Serial.print("Расстояние: ");
if (distance < 10) Serial.print(" "); // Выравнивание для красоты
Serial.print(distance, 0); // 0 знаков после запятой
Serial.print(" см |");
// Вычисляем количество блоков (от 0 до 25)
// 2 см = 0 блоков, 50 см = 25 блоков
int blocks = map((int)distance, 2, 50, 0, 25);
// Рисуем полоску из символов █
for (int i = 0; i < blocks; i++) {
Serial.print("█");
}
// Дополняем пустыми пробелами до 25 символов
for (int i = blocks; i < 25; i++) {
Serial.print(" ");
}
Serial.print("| ");
// Текстовое описание
if (distance <= 10) {
Serial.println("Очень близко!");
} else if (distance <= 20) {
Serial.println("Близко");
} else if (distance <= 35) {
Serial.println("Средняя дистанция");
} else {
Serial.println("Далеко");
}
delay(200); // Быстрое обновление для плавной анимации
}
Что должно получиться:
Приближайте и отдаляйте руку от датчика — вы увидите, как «полоска» из символов █ удлиняется и укорачивается в реальном времени!
Пример вывода:
=== Phobo Distance Indicator ===
Графический индикатор расстояния (2-50 см)
Расстояние: 45 см |████████████████████████ | Далеко
Расстояние: 38 см |███████████████████ | Средняя дистанция
Расстояние: 25 см |████████████ | Средняя дистанция
Расстояние: 18 см |████████ | Близко
Расстояние: 8 см |███ | Очень близко!
Расстояние: 3 см | | Очень близко!
Дополнительная задача: Попробуйте изменить максимальную дистанцию на 100 см и количество блоков на 50 — получится более точная шкала!
Эксперимент 3: Детектор движения руки
Задача: Научить Arduino распознавать движение руки перед датчиком (приближение или отдаление). Это пригодится для жестового управления роботом!
Логика работы:
Программа запоминает предыдущее расстояние и сравнивает с текущим. Если расстояние уменьшается — рука приближается, если увеличивается — отдаляется.
Полный код:
/*
* Эксперимент 3: Детектор движения руки
* Определяет направление движения объекта
*/
#include <AlashUltrasonic.h>
const uint8_t TRIGGER_PIN = 3;
const uint8_t ECHO_PIN = 7;
AlashUltrasonic sensor(TRIGGER_PIN, ECHO_PIN);
float previousDistance = 0; // Хранит предыдущее измерение
void setup() {
Serial.begin(9600);
sensor.begin();
Serial.println("=== Phobo Motion Detector ===");
Serial.println("Детектор движения руки");
Serial.println("Поднесите руку к датчику...");
Serial.println();
// Первое измерение для инициализации
previousDistance = sensor.getDistance();
delay(500);
}
void loop() {
float currentDistance = sensor.getDistance();
// Вычисляем разницу между текущим и предыдущим измерением
float difference = currentDistance - previousDistance;
// Выводим данные
Serial.print("Расстояние: ");
Serial.print(currentDistance, 0); // 0 знаков после запятой
Serial.print(" см | ");
// Определяем направление движения
if (abs(difference) < 2) {
// Изменение меньше 2 см — считаем объект неподвижным
Serial.println("⏸️ Объект неподвижен");
}
else if (difference < 0) {
// Расстояние уменьшилось — приближение
Serial.print("👋 Приближается! (");
Serial.print(abs(difference), 0);
Serial.println(" см)");
}
else {
// Расстояние увеличилось — отдаление
Serial.print("👋 Отдаляется! (");
Serial.print(difference, 0);
Serial.println(" см)");
}
// Сохраняем текущее расстояние для следующей итерации
previousDistance = currentDistance;
delay(300); // Обновление 3 раза в секунду
}
Что должно получиться:
Медленно приближайте и отдаляйте руку от датчика — программа будет распознавать направление движения и показывать скорость изменения расстояния!
Пример вывода:
=== Phobo Motion Detector ===
Детектор движения руки
Поднесите руку к датчику...
Расстояние: 45 см | ⏸️ Объект неподвижен
Расстояние: 42 см | 👋 Приближается! (3 см)
Расстояние: 37 см | 👋 Приближается! (5 см)
Расстояние: 31 см | 👋 Приближается! (6 см)
Расстояние: 28 см | 👋 Приближается! (3 см)
Расстояние: 28 см | ⏸️ Объект неподвижен
Расстояние: 32 см | 👋 Отдаляется! (4 см)
Расстояние: 39 см | 👋 Отдаляется! (7 см)
Дополнительная задача: Добавьте счётчик взмахов руки! Если рука резко приблизилась (более 10 см за одно измерение) — это взмах. Считайте количество взмахов и выводите: «Взмах #1», «Взмах #2» и т.д.
Решение проблем
Проблема 1: В мониторе порта только нули (0 см)
Причины:
Неправильное подключение проводов
Перепутаны Trig и Echo
Датчик не получает питание
Решение:
Проверьте все 4 провода — они должны сидеть плотно
Убедитесь: VCC → +5V, GND → GND, Trig → D3, Echo → A5
Убедитесь, что вызвали
sensor.begin()в функцииsetup()Попробуйте поменять местами Trig и Echo:
AlashUltrasonic sensor(A5, 3);вместо(3, A5)
Проблема 2: Расстояние скачет (то 20 см, то 300 см, то 0 см)
Причины:
Плохой контакт в проводах
Помехи от других устройств
Измерение на слишком большом расстоянии (>4 метров)
Решение:
Пошевелите провода — если показания меняются, переподключите провода
Убедитесь, что перед датчиком есть объект в пределах 2-400 см
Добавьте фильтрацию в код:
float distance = sensor.getDistance();
if (distance < 2 || distance > 450) {
Serial.println("Вне диапазона!");
} else {
Serial.print("Расстояние: ");
Serial.print(distance, 1); // 1 знак после запятой
Serial.println(" см");
}
Проблема 3: Ошибка компиляции «AlashUltrasonic.h: No such file»
Причина: Библиотека не установлена
Решение:
Проверьте установку библиотеки через Скетч → Подключить библиотеку — должна быть AlashUltrasonic
Если библиотеки нет — повторите установку (см. раздел «Установка библиотеки»)
Перезапустите Arduino IDE после установки
Проблема 4: Датчик не «видит» некоторые объекты
Причина: RCWL-9610A (как и HC-SR04) лучше всего отражает ультразвук от твёрдых плоских поверхностей
Объекты, которые датчик «видит» плохо:
Мягкие ткани (ковёр, подушка) — поглощают звук
Пушистые предметы (мягкая игрушка) — рассеивают звук
Наклонные поверхности — отражают звук в сторону
Очень тонкие предметы (провод, карандаш) — слишком малы
Решение:
Используйте твёрдые предметы для тестирования (книга, коробка, рука)
Располагайте объект перпендикулярно датчику (под углом 90°)
Углублённая теория
Скорость звука и формула расстояния
RCWL-9610A (как и HC-SR04) использует ультразвук частотой 40 кГц (40000 колебаний в секунду). Человек слышит звуки от 20 Гц до 20 кГц, поэтому ультразвук для нас бесшумный.
Скорость звука в воздухе при 20°C:
v = 343 м/с = 34300 см/с
Звук проходит путь туда и обратно:
Расстояние = (Скорость × Время) / 2
Переведём в удобные единицы:
Arduino измеряет время в микросекундах (мкс). 1 секунда = 1 000 000 мкс.
Расстояние (см) = (34300 см/с × Время (мкс) / 1000000) / 2
= 34300 × Время / 2000000
= Время / 58.2
Вот откуда взялось число 58.2!
Примечание
Интересно: Скорость звука зависит от температуры воздуха! При 0°C звук летит ~331 м/с, при 20°C ~343 м/с. Поэтому в жаркую погоду датчик будет чуть точнее, чем в холодную.
Как библиотека упрощает работу?
Без библиотеки пришлось бы писать так:
// Код БЕЗ библиотеки — сложный!
digitalWrite(trigPin, LOW);
delayMicroseconds(2);
digitalWrite(trigPin, HIGH);
delayMicroseconds(10);
digitalWrite(trigPin, LOW);
long duration = pulseIn(echoPin, HIGH);
long distance = duration / 58.2;
С библиотекой всё проще:
// Код С библиотекой — простой!
float distance = sensor.getDistance();
Библиотека скрывает сложную логику внутри функции getDistance() — вам не нужно помнить все детали!
Что дальше?
Поздравляем! Вы научились работать с ультразвуковым датчиком и устанавливать библиотеки. Теперь робот Phobo может «видеть» препятствия!
Что мы изучили:
✅ Современный датчик RCWL-9610A и его преимущества перед HC-SR04
✅ Режимы работы датчика (GPIO, I2C, UART, 1-Wire) и выбор GPIO
✅ Установка библиотеки AlashUltrasonic двумя способами (Менеджер и GitHub)
✅ Подключение датчика к Sensor Shield V5 в режиме GPIO
✅ Программирование с использованием библиотеки AlashUltrasonic
✅ Вывод данных в монитор порта
✅ Практичные эксперименты: парковочный радар, графический индикатор, детектор движения
Что дальше: Проект 6 (следование за рукой) — робот использует RCWL-9610A и сервопривод для отслеживания движущихся объектов.
Для любознательных:
Попробуйте объединить все 3 эксперимента в одну программу с меню выбора режима через монитор порта
Сохраняйте измерения в массив и выводите среднее значение за последние 10 измерений (фильтрация шума)
Изучите другие режимы работы RCWL-9610A (I2C, UART) — они экономят пины Arduino! Примеры есть в библиотеке AlashUltrasonic
В будущем можно подключить два датчика RCWL-9610A (вперёд и назад) для двустороннего обнаружения препятствий
Примечание
В Проекте 1 датчик установлен на сервопривод (Проект 4) — робот сканирует пространство на 180°. В Проектах 6-7 датчик используется для следования за рукой и объезда препятствий.
Удачи в экспериментах! 🚀