В этой вводной статье мы узнаем о технологии сверхширокополосной связи с использованием модуля ESP32 DW1000 UWB. Технология UWB (Ultra Wideband Technology) — это технология беспроводной связи с несущей частотой, которая использует полосу пропускания выше 1 ГГц. Она не использует синусоидальную несущую, а использует несинусоидальные узкие импульсы наносекундной длительности для передачи данных.

BU01 разработан компанией Ai-Thinker на основе чипа DecaWave DW1000, который объединяет антенну, все радиочастотные схемы, управление питанием и модули синхронизации. Модуль ESP32 UWB на основе DW1000 и ESP32 похож на непрерывно сканирующий радар, который может точно захватить другое устройство, определить его местоположение и связаться с ним.
В этом уроке мы рассмотрим конструкцию платы ESP32 DW1000, ее технические характеристики и приложения. Затем мы узнаем как использовать плату ESP32 DW1000 для обнаружения объектов и измерения дальности. Во время обнаружения дальности могут возникнуть проблемы с задержкой антенны, приводящие к неправильному измерению расстояния. Поэтому мы изучим метод устранения проблемы с расстоянием с помощью метода калибровки задержки антенны.
Что такое сверхширокополосная связь?
UWB — это протокол беспроводной связи ближнего действия, похожий на Bluetooth или Wi-Fi. Он также использует радиоволны для связи и работает на очень высокой частоте. Как следует из его названия, он также использует широкий спектр в несколько ГГц. Один из способов представить его как радар, который может непрерывно сканировать всю комнату и точно захватить объект, как лазерный луч, чтобы обнаружить его местоположение и передать данные.

Основная цель Ultra Wideband — обнаружение местоположения и определение дальности действия устройства. В то время как Wi-Fi и Bluetooth были модифицированы для обеспечения большей точности в определении местоположения других устройств и подключении к ним, UWB изначально более точен и потребляет меньше энергии.
Как работает UWB?
Передатчик UWB работает, отправляя миллиарды импульсов по широкому спектру частот. Соответствующий приемник получает сигнал, который преобразует импульсы в данные, прослушивая знакомую последовательность импульсов, отправленную передатчиком. Импульсы отправляются примерно один раз в две наносекунды, что помогает UWB достичь точности в реальном времени.

UWB потребляет крайне мало энергии. Его высокая пропускная способность (обусловленная широкой полосой 500 МГц) идеально подходит для передачи большого количества данных с хост-устройства на другие устройства на расстоянии до 30 футов. В отличие от Wi-Fi, он не особенно хорош для передачи через стены.
Когда смартфон с чипом UWB приближается к другому устройству UWB, они начинают определять расстояние или измерять точное расстояние между ними. Определение расстояния осуществляется с помощью измерений "времени полета" (Time of Flight, ToF) между устройствами. Они используются для расчета времени прохождения пакетов вызова/ответа в обоих направлениях.

Понятия “anchor” («якорь») и “tag” («тег») важны для понимания измерения расстояния и местоположения с помощью UWB. Якорь — это, как правило, фиксированное устройство UWB с известным местоположением. Тег — это, как правило, мобильное устройство UWB. Якорь и тег обмениваются информацией для установления расстояния между ними. Точное местоположение тега можно определить, связавшись с несколькими якорями. Некоторые устройства могут действовать как якорь или тег.
Модуль UWB на базе DW1000 BU01

Модуль BU01 разработан Ai-Thinker на основе чипа DW1000 от DecaWave. Он объединяет антенну, все радиочастотные схемы, управление питанием и модули синхронизации. Модуль может использовать двустороннюю систему определения дальности или позиционирования TDOA с точностью позиционирования 10 см. Скорость передачи данных до 6,8 Мбит/с.
Функции
-
Простая интеграция, не требуется проектирование радиочастот.
-
Использование инфраструктуры RTLS для расширения диапазона связи.
-
Поддержка высокой плотности этикеток.
-
Соответствует стандарту IEEE 802.15.4-2011 UWB.
-
Поддержка 4 каналов от 3,5 ГГц до 6,5 ГГц.
-
Программируемая мощность передачи.
-
Напряжение питания 2,8 В - 3,6 В.
-
Потребляемая мощность в спящем режиме <1мА.
-
Поддержка двухстороннего измерения дальности и TDOA.
-
Поддержка интерфейса SPI.
-
Скорость передачи данных 110 кбит/с, 850 кбит/с, 6,8 Мбит/с.
Плата ESP32 UWB (Ultra Wideband)
Модуль ESP32 UWB Ultra Wideband основан на DW1000 и ESP32. Эта плата произведена компанией Makerfabs. Модуль BU01 на основе чипа DW1000 сопряжен с модулем ESP32 WiFi с расширением ввода/вывода. Плата действует как непрерывно сканирующий радар, который точно фиксируется на другом устройстве (называемым Anchor) и связывается с ним, таким образом вычисляя свое собственное местоположение.

Верхняя сторона платы имеет встроенный модуль ESP32 WROOM/Wrover с модулем BU01 и другими пассивными электронными компонентами. Есть две кнопки, одна для вспышки, другая для отдыха. Плата имеет порт micro-USB для загрузки прошивки и последовательной связи.

На задней стороне платы находится чип CP2102 для связи UART. Названия портов ввода/вывода также указаны на плате. Штекерные или гнездовые разъемы могут быть припаяны с обеих сторон платы. Плата дружелюбна к макетной плате. Поэтому вы можете разместить ее на макетной плате вместе с другими компонентами во время практических применений.
Функции
- Decawave DWM1000 для точного отслеживания.
- ESP32 для быстрых и мощных приложений.
- Поддержка Wi-Fi, Bluetooth.
- Совместимость с Arduino.
- Разъем Micro-USB.
- Диапазон напряжения питания USB-платы: 4,8~5,5 В, типичное значение 5,0 В.
Начало работы с модулем ESP32 DW1000 UWB (Ultra Wideband)
Давайте узнаем, как использовать плату ESP32 DW1000 UWB (Ultra Wideband) с Arduino IDE и измерить расстояние между платами. Для этого проекта вам понадобится пара плат. Затем нам нужно будет выполнить ряд шагов, чтобы использовать этот модуль.
Установка библиотеки DW1000
Сначала нам нужно установить библиотеку Arduino-DW1000 от thotro. Эта библиотека предлагает функционал для использования чипов/модулей DW1000 от Decawave с Arduino.
Вы также можете установить эту библиотеку через менеджер библиотек. Просто найдите DW1000 и нажмите install («Установить»), чтобы установить библиотеку.
Изменение библиотеки
Библиотека DW1000 UWB не компилируется для плат ESP32 напрямую. Поэтому нам нужно внести некоторые изменения в библиотечную часть.
Перейдите в папку Arduino Library и найдите DW1000. Затем откройте папку Library и найдите исходную папку (src).
Откройте папку src и найдите файл DW1000.cpp. Откройте файл с помощью текстового редактора, например Notepad++.
Теперь найдите следующие строки (строка № 172) и закомментируйте все эти 3 строки.
|
1 2 3 |
//#ifndef ESP8266 // SPI.usingInterrupt(digitalPinToInterrupt(irq)); // not every board support this, e.g. ESP8266 //#endif |
После того, как эти строки будут закомментированы, код библиотеки будет успешно скомпилирован.
Выбор платы
Подключите пару плат ESP32 Wrover к двум разным USB-портам вашего компьютера с помощью кабеля micro-USB.
В Arduino IDE выберите плату разработки «ESP32 Dev Module», если вы используете плату ESP32 UWB с чипом ESP32 WROOM. В противном случае выберите «ESP32 WROVER Module», если вы используете плату ESP32 UWB с чипом ESP32 WROVER.

Также выберите COM-порт. Номер COM-порта, который был назначен плате при ее подключении к компьютеру, можно найти в диспетчере устройств. Теперь плата ESP32 Ultra Wideband готова к последовательной связи.
Как использовать модуль ESP32 UWB для измерения расстояния?
Чтобы измерить расстояние между платами, нам необходимо загрузить код «Anchor» на одну плату ESP32, а код «Tag» на другую плату ESP32.
Одна из плат будет действовать как Якорь (Отправитель), а другая плата будет действовать как Тег (Приемник). Согласно стандартам UWB, Якорь должен быть неподвижным, а тег должен быть подвижным. Для целей тестирования мы держим платы на расстоянии 1 метра друг от друга.
Код Якоря (Anchor)
Скопируйте следующий код и загрузите его на первую плату UWB (Ultra Wideband).
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 |
#include <SPI.h> #include "DW1000Ranging.h" //https://github.com/thotro/arduino-dw1000 #define ANCHOR_ADD "83:17:5B:D5:A9:9A:E2:9C" #define SPI_SCK 18 #define SPI_MISO 19 #define SPI_MOSI 23 #define DW_CS 4 // connection pins const uint8_t PIN_RST = 27; // reset pin const uint8_t PIN_IRQ = 34; // irq pin const uint8_t PIN_SS = 4; // spi select pin void setup() { Serial.begin(115200); delay(1000); //init the configuration SPI.begin(SPI_SCK, SPI_MISO, SPI_MOSI); DW1000Ranging.initCommunication(PIN_RST, PIN_SS, PIN_IRQ); //Reset, CS, IRQ pin //define the sketch as anchor. It will be great to dynamically change the type of module DW1000Ranging.attachNewRange(newRange); DW1000Ranging.attachBlinkDevice(newBlink); DW1000Ranging.attachInactiveDevice(inactiveDevice); //Enable the filter to smooth the distance //DW1000Ranging.useRangeFilter(true); //we start the module as an anchor // DW1000Ranging.startAsAnchor("82:17:5B:D5:A9:9A:E2:9C", DW1000.MODE_LONGDATA_RANGE_ACCURACY); DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_LONGDATA_RANGE_LOWPOWER, false); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_SHORTDATA_FAST_LOWPOWER); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_LONGDATA_FAST_LOWPOWER); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_SHORTDATA_FAST_ACCURACY); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_LONGDATA_FAST_ACCURACY); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_LONGDATA_RANGE_ACCURACY); } void loop() { DW1000Ranging.loop(); } void newRange() { Serial.print("from: "); Serial.print(DW1000Ranging.getDistantDevice()->getShortAddress(), HEX); Serial.print("\t Range: "); Serial.print(DW1000Ranging.getDistantDevice()->getRange()); Serial.print(" m"); Serial.print("\t RX power: "); Serial.print(DW1000Ranging.getDistantDevice()->getRXPower()); Serial.println(" dBm"); } void newBlink(DW1000Device *device) { Serial.print("blink; 1 device added ! -> "); Serial.print(" short:"); Serial.println(device->getShortAddress(), HEX); } void inactiveDevice(DW1000Device *device) { Serial.print("delete inactive device: "); Serial.println(device->getShortAddress(), HEX); } |
Код тега (Tag)
Скопируйте следующий код и загрузите его на вторую плату UWB (сверхширокополосную).
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 |
#include <SPI.h> #include "DW1000Ranging.h" #define SPI_SCK 18 #define SPI_MISO 19 #define SPI_MOSI 23 #define DW_CS 4 // connection pins const uint8_t PIN_RST = 27; // reset pin const uint8_t PIN_IRQ = 34; // irq pin const uint8_t PIN_SS = 4; // spi select pin void setup() { Serial.begin(115200); delay(1000); //init the configuration SPI.begin(SPI_SCK, SPI_MISO, SPI_MOSI); DW1000Ranging.initCommunication(PIN_RST, PIN_SS, PIN_IRQ); //Reset, CS, IRQ pin //define the sketch as anchor. It will be great to dynamically change the type of module DW1000Ranging.attachNewRange(newRange); DW1000Ranging.attachNewDevice(newDevice); DW1000Ranging.attachInactiveDevice(inactiveDevice); //Enable the filter to smooth the distance //DW1000Ranging.useRangeFilter(true); //we start the module as a tag DW1000Ranging.startAsTag("7D:00:22:EA:82:60:3B:9C", DW1000.MODE_LONGDATA_RANGE_LOWPOWER); } void loop() { DW1000Ranging.loop(); } void newRange() { Serial.print("from: "); Serial.print(DW1000Ranging.getDistantDevice()->getShortAddress(), HEX); Serial.print("\t Range: "); Serial.print(DW1000Ranging.getDistantDevice()->getRange()); Serial.print(" m"); Serial.print("\t RX power: "); Serial.print(DW1000Ranging.getDistantDevice()->getRXPower()); Serial.println(" dBm"); } void newDevice(DW1000Device *device) { Serial.print("ranging init; 1 device added ! -> "); Serial.print(" short:"); Serial.println(device->getShortAddress(), HEX); } void inactiveDevice(DW1000Device *device) { Serial.print("delete inactive device: "); Serial.println(device->getShortAddress(), HEX); } |
Диапазон тестирования между платами
После загрузки кода на платы Anchor и tag вы можете открыть Serial Monitor (окно монитора последовательной связи). Он покажет идентификаторы anchor и tag. Он также покажет диапазон в метрах и мощность приемника в dBm.
Согласно нашей настройке, мы разместили якорь и метку на расстоянии 1 метра друг от друга, но последовательный монитор показывает расстояние более 2 метров.
Отсюда мы можем сказать, что измеренное расстояние неверно. Это из-за проблемы задержки антенны. Задержка антенны DW1000 является внутренней для чипа и не включена в расчет времени пролета (TOF). Таким образом, нам необходимо откалибровать задержку антенны чтобы устранить эту проблему.
Какова задержка антенны DW1000?
Многоканальный приемопередатчик DecaWave DW1000, работающий на основе сверхширокополосной (UWB) радиосвязи, позволяет с высокой точностью маркировать сообщения по мере их отправки и прибытия на приемопередатчик.
Задержки, которые измеряются в этих временных метках, включают задержку распространения через устройства DW1000 от точек, в которых применяются временные метки передатчика, до точек, в которых фиксируются временные метки приемника. Эти задержки называются задержками передающей/приемной антенны.
Эти задержки антенн являются внутренними для чипа и не включены во время пролета (ToF), но включены в задержку распространения от временной метки передачи до временной метки приема сообщения.

![]()
где:
ToF = Время пролета
tMeasured = Измеренное время от временной метки передачи до временной метки приема
tADTX = Задержка передающей антенны
tADRX = Задержка приемной антенны
Внутренние задержки распространения в устройствах DW1000 немного различаются от чипа к чипу. Также могут быть различия из-за компонентов между DW1000 и антенной. Поскольку мы измеряем радиочастотные сигналы, движущиеся со скоростью света, эти изменения могут привести к различиям в измерениях дальности в десятки сантиметров. Калибровка задержки антенны используется для устранения этих изменений.
Калибровка задержки антенны DW1000
Для устранения проблемы задержки антенны Джим Ремингтон модифицировал указанную выше библиотеку DW1000 Томаса Тройера.
Обновленную библиотеку DW1000 от Джима можно загрузить из репозитория jremington Github. С калибровкой антенны измерение расстояния кажется более точным.
Удалите старую библиотеку DW1000 из папки библиотеки Arduino и добавьте последний загруженный файл библиотеки jremington DW1000 в папку библиотеки Arduino.
Код автокалибровки якоря ESP32
Скопируйте следующий код и загрузите его на первую плату ESP32 UWB.
В следующем коде внесите изменения в следующую строку:
|
1 |
float this_anchor_target_distance = 1; //measured distance to anchor in m |
Измените расстояние, на котором выполняется калибровка.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 |
#include <SPI.h> #include "DW1000Ranging.h" #include "DW1000.h" // ESP32_UWB pin definitions #define SPI_SCK 18 #define SPI_MISO 19 #define SPI_MOSI 23 #define DW_CS 4 // connection pins const uint8_t PIN_RST = 27; // reset pin const uint8_t PIN_IRQ = 34; // irq pin const uint8_t PIN_SS = 4; // spi select pin char this_anchor_addr[] = "84:00:22:EA:82:60:3B:9C"; float this_anchor_target_distance = 1; //measured distance to anchor in m uint16_t this_anchor_Adelay = 16600; //starting value uint16_t Adelay_delta = 100; //initial binary search step size void setup() { Serial.begin(115200); while (!Serial); //init the configuration SPI.begin(SPI_SCK, SPI_MISO, SPI_MOSI); DW1000Ranging.initCommunication(PIN_RST, PIN_SS, PIN_IRQ); //Reset, CS, IRQ pin Serial.print("Starting Adelay "); Serial.println(this_anchor_Adelay); Serial.print("Measured distance "); Serial.println(this_anchor_target_distance); DW1000.setAntennaDelay(this_anchor_Adelay); DW1000Ranging.attachNewRange(newRange); DW1000Ranging.attachNewDevice(newDevice); DW1000Ranging.attachInactiveDevice(inactiveDevice); //Enable the filter to smooth the distance //DW1000Ranging.useRangeFilter(true); //start the module as anchor, don't assign random short address DW1000Ranging.startAsAnchor(this_anchor_addr, DW1000.MODE_LONGDATA_RANGE_LOWPOWER, false); } void loop() { DW1000Ranging.loop(); } void newRange() { static float last_delta = 0.0; Serial.print(DW1000Ranging.getDistantDevice()->getShortAddress(), DEC); float dist = 0; for (int i = 0; i < 100; i++) { // get and average 100 measurements dist += DW1000Ranging.getDistantDevice()->getRange(); } dist /= 100.0; Serial.print(","); Serial.print(dist); if (Adelay_delta < 3) { Serial.print(", final Adelay "); Serial.println(this_anchor_Adelay); // Serial.print("Check: stored Adelay = "); // Serial.println(DW1000.getAntennaDelay()); while(1); //done calibrating } float this_delta = dist - this_anchor_target_distance; //error in measured distance if ( this_delta * last_delta < 0.0) Adelay_delta = Adelay_delta / 2; //sign changed, reduce step size last_delta = this_delta; if (this_delta > 0.0 ) this_anchor_Adelay += Adelay_delta; //new trial Adelay else this_anchor_Adelay -= Adelay_delta; Serial.print(", Adelay = "); Serial.println (this_anchor_Adelay); // DW1000Ranging.initCommunication(PIN_RST, PIN_SS, PIN_IRQ); //Reset, CS, IRQ pin DW1000.setAntennaDelay(this_anchor_Adelay); } void newDevice(DW1000Device *device) { Serial.print("Device added: "); Serial.println(device->getShortAddress(), HEX); } void inactiveDevice(DW1000Device *device) { Serial.print("delete inactive device: "); Serial.println(device->getShortAddress(), HEX); } |
Код тега (настройка ESP32 UWB)
Скопируйте следующий код и загрузите его на вторую плату ESP32 UWB.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 |
#include <SPI.h> #include "DW1000Ranging.h" #include "DW1000.h" #define SPI_SCK 18 #define SPI_MISO 19 #define SPI_MOSI 23 #define DW_CS 4 // connection pins const uint8_t PIN_RST = 27; // reset pin const uint8_t PIN_IRQ = 34; // irq pin const uint8_t PIN_SS = 4; // spi select pin // TAG antenna delay defaults to 16384 // leftmost two bytes below will become the "short address" char tag_addr[] = "7D:00:22:EA:82:60:3B:9C"; void setup() { Serial.begin(115200); delay(1000); //init the configuration SPI.begin(SPI_SCK, SPI_MISO, SPI_MOSI); DW1000Ranging.initCommunication(PIN_RST, PIN_SS, PIN_IRQ); //Reset, CS, IRQ pin DW1000Ranging.attachNewRange(newRange); DW1000Ranging.attachNewDevice(newDevice); DW1000Ranging.attachInactiveDevice(inactiveDevice); // start as tag, do not assign random short address DW1000Ranging.startAsTag(tag_addr, DW1000.MODE_LONGDATA_RANGE_LOWPOWER, false); } void loop() { DW1000Ranging.loop(); } void newRange() { Serial.print(DW1000Ranging.getDistantDevice()->getShortAddress(), HEX); Serial.print(","); Serial.println(DW1000Ranging.getDistantDevice()->getRange()); } void newDevice(DW1000Device *device) { Serial.print("Device added: "); Serial.println(device->getShortAddress(), HEX); } void inactiveDevice(DW1000Device *device) { Serial.print("delete inactive device: "); Serial.println(device->getShortAddress(), HEX); } |
Расчет параметра Аделая (Adelay Parameter)
После загрузки кода откройте оба Serial Monitor. Разместите модули на фиксированном расстоянии 1 метр. Затем нажмите кнопку сброса.
Коэффициент калибровки задержки антенны DW1000, называемый Adelay, можно определить из кода. В последовательном мониторе коэффициент Adelay равен примерно 16586. Скопируйте это число, так как оно потребуется в окончательном коде программы.
Точное измерение расстояния с включением параметра Аделая
Теперь определен коэффициент калибровки задержки антенны DW1000, называемый Adelay. Поэтому нам нужно загрузить окончательный код на плату якоря (Anchor). Код для тега остается прежним.
Код якоря ESP32 UWB
Необходимо изменить код в этих двух строках.
|
1 2 |
uint16_t Adelay = 16611; float dist_m = 1; //meters |
Замените параметр Аделая в коде, а также укажите расстояние, на котором вы его определили.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 |
#include <SPI.h> #include "DW1000Ranging.h" #include "DW1000.h" // leftmost two bytes below will become the "short address" char anchor_addr[] = "84:00:5B:D5:A9:9A:E2:9C"; //#4 //calibrated Antenna Delay setting for this anchor uint16_t Adelay = 16611; // previously determined calibration results for antenna delay // #1 16630 // #2 16610 // #3 16607 // #4 16580 // calibration distance float dist_m = 1; //meters #define SPI_SCK 18 #define SPI_MISO 19 #define SPI_MOSI 23 #define DW_CS 4 // connection pins const uint8_t PIN_RST = 27; // reset pin const uint8_t PIN_IRQ = 34; // irq pin const uint8_t PIN_SS = 4; // spi select pin void setup() { Serial.begin(115200); delay(1000); //wait for serial monitor to connect Serial.println("Anchor config and start"); Serial.print("Antenna delay "); Serial.println(Adelay); Serial.print("Calibration distance "); Serial.println(dist_m); //init the configuration SPI.begin(SPI_SCK, SPI_MISO, SPI_MOSI); DW1000Ranging.initCommunication(PIN_RST, PIN_SS, PIN_IRQ); //Reset, CS, IRQ pin // set antenna delay for anchors only. Tag is default (16384) DW1000.setAntennaDelay(Adelay); DW1000Ranging.attachNewRange(newRange); DW1000Ranging.attachNewDevice(newDevice); DW1000Ranging.attachInactiveDevice(inactiveDevice); //start the module as an anchor, do not assign random short address DW1000Ranging.startAsAnchor(anchor_addr, DW1000.MODE_LONGDATA_RANGE_LOWPOWER, false); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_SHORTDATA_FAST_LOWPOWER); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_LONGDATA_FAST_LOWPOWER); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_SHORTDATA_FAST_ACCURACY); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_LONGDATA_FAST_ACCURACY); // DW1000Ranging.startAsAnchor(ANCHOR_ADD, DW1000.MODE_LONGDATA_RANGE_ACCURACY); } void loop() { DW1000Ranging.loop(); } void newRange() { // Serial.print("from: "); Serial.print(DW1000Ranging.getDistantDevice()->getShortAddress(), HEX); Serial.print(", "); #define NUMBER_OF_DISTANCES 1 float dist = 0.0; for (int i = 0; i < NUMBER_OF_DISTANCES; i++) { dist += DW1000Ranging.getDistantDevice()->getRange(); } dist = dist/NUMBER_OF_DISTANCES; Serial.println(dist); } void newDevice(DW1000Device *device) { Serial.print("Device added: "); Serial.println(device->getShortAddress(), HEX); } void inactiveDevice(DW1000Device *device) { Serial.print("Delete inactive device: "); Serial.println(device->getShortAddress(), HEX); } |
Тестирование финального кода
После загрузки нового кода в плату якоря (Anchor) откройте Serial Monitor. Поскольку якорь и тег находятся на расстоянии 1 метра друг от друга, Serial Monitor должен показывать расстояние в 1 метр.

Теперь давайте проведем еще один тест, переместив метку на расстояние полуметра от якоря.
В этом случае последовательный монитор покажет расстояние около 0,5 метра, что кажется почти точным.

При правильной настройке задержки точность измерения может быть значительно улучшена. Итак, вот как вы можете начать работу с платой ESP32 UWB (Ultra Wideband) и измерить расстояние между двумя подобными платами.












