Скетч с форума обещал дисплей с пультом за вечер. Я скопировал его в новую IDE, нажал «Проверить» и получил первую строку, ставшую с тех пор родной: «fatal error: IRremote.h: No such file or directory». Скачал архив по первой ссылке, поставил — появилось предупреждение «Multiple libraries were found for IRremote.h». Убрал дубликат — и упёрся в «'enableIRIn' was not declared in this scope». Три тупика за один вечер, и все три — про одно: библиотеки в Arduino — это не приложения «поставил и забыл», а код, у которого есть версия, копия на диске и характер.
В этом уроке я покажу честный путь: сначала менеджер библиотек, затем ZIP-архив для случаев, когда менеджера не существует, и напоследок — главная тайна форумов, из-за которой рабочий код у одного собирается, а у другого сыплет ошибками. Как обычно, в конце — виртуальная плата: библиотека LiquidCrystal_I2C уже установлена, экран подключён, можно трогать руками.
Менеджер библиотек: ставим одной кнопкой
Меню «Скетч → Подключить библиотеку → Управлять библиотеками…» открывает каталог с тысячами записей (в IDE 2.x — иконка с книгами в левой панели). Поиск по имени, фильтры по типу и теме. В карточке библиотеки — описание, автор и, что важнее всего, две версии: установленная у вас и последняя. Кнопка Install ставит выбранную; рядом с ней выпадающий список версий — запомните это место, оно спасает, когда свежее обновление ломает старый скетч.
У многих библиотек есть зависимости. Типичный пример: «DHT sensor library» от Adafruit требует «Adafruit Unified Sensor» — при установке среда сама спросит «установить также?», и правильный ответ — да, иначе получите пачку ошибок про неизвестный класс Adafruit_Sensor. Не пугайтесь диалога, это нормальная механика.
Физически библиотеки попадают в Документы\Arduino\libraries\ИмяБиблиотеки. Отсюда два практических вывода: переустановка IDE библиотеки не трогает, а когда среда жалуется на библиотеку, чинить её нужно в этой папке, а не где-то в глубинах системы. Внутри каждой — файл library.properties (имя, версия, автор) и папка examples с готовыми скетчами под именно эту версию.
Обновление — отдельная история. В каталоге есть фильтр «Обновляемые»: среда честно перечисляет, где вышла новая версия. Тут я держу паузу: обновлять стоит, когда есть причина — баг в работе, нужная функция, смена платы. Пусть в карточке и горит зелёная метка, а проект собирался вчера: сам факт новой версии причиной не является.
Мой совет с условием: первые месяцы ставьте всё через менеджер и только ZIP оставьте для исключений — заводские библиотеки модулей с маркетплейсов, свежие форки, которых в каталоге ещё нет. Причина проста: менеджер показывает версию и умеет обновляться, ZIP о себе ничего не расскажет.
ZIP-архив: когда библиотеки нет в менеджере
Путь для исключений: «Скетч → Подключить библиотеку → Добавить .ZIP библиотеку…». Выбираете архив — среда сама распакует его в папку libraries. Но перед нажатием проверьте содержимое: внутри ZIP должна лежать папка, в корне которой файлы .h и .cpp. Классическая ловушка — скачивание с GitHub кнопкой Code → Download ZIP: папка получит суффикс -master (например, IRremote-master), а заголовок внутри называется IRremote.h. Среда обычно переваривает это сама, но если после установки «No such file or directory» никуда не делся, переименуйте папку в чистое имя библиотеки. Вторая ловушка — двойная вложенность «IRremote-master\IRremote-master\…»: переупакуйте архив так, чтобы до файлов .h был один уровень.
Библиотеки с завода модуля (страница товара, диск в наборе, ссылка из описания) чаще всего приходят именно ZIP-архивом, и это нормально: автор модуля дал вам свою версию — просто помните, что менеджер о ней знать не будет и обновления не предложит.
Современные библиотеки бывают двух форматов: старого — когда .h и .cpp лежат прямо в корне папки, и нового — с подпапкой src внутри. Среда понимает оба, а правило вложенности при ручной установке одно: от корня папки библиотеки до файлов с кодом — один уровень. Если сомневаетесь — загляните внутрь архива перед установкой, а не после.
Ручная установка тоже законна: распаковать архив в Документы\Arduino\libraries и перезапустить среду — в 1.8.x без перезапуска новая библиотека в списках не появится, в 2.x подхватывается на лету, но я перезапускаю всегда: дешевле, чем искать причину «не видит».
История-тупик с симптомом и лечением, на которой учились все мои знакомые: экран LCD1602, библиотека LiquidCrystal_I2C. Скачал с первой ссылки, поставил. Через неделю поставил ещё одну — с другой страницы, для другого примера. Скетч собирался, но текст на экране вёл себя странно: команды работали не те, что в примере. Симптом был честный: предупреждение «Multiple libraries were found for LiquidCrystal_I2C.h» — в каталоге библиотек оказались две папки с одинаковым заголовком и разными внутренностями. Компилятор молча взял первую по списку. Лечение: открыть Документы\Arduino\libraries, удалить лишнюю копию, перезапустить IDE. Предупреждение в логе — не шум, а указание на дубль.
Версии: почему код с форума не собирается
Библиотеки — это тоже программы, и авторы меняют их интерфейс. Живой пример — IRremote, библиотека ИК-приёмников. В версии 2.x классика выглядела так: IRrecv irrecv(11);, затем irrecv.enableIRIn(); и results.value. С версии 3.x (вышла в 2020-м) всё стало иначе: IrReceiver.begin(11); и IrReceiver.decodedIRData.command. Строка #include <IRremote.h> при этом не изменилась — поэтому скетч 2018 года с современным заголовком собирается наполовину и умирает на «'enableIRIn' was not declared in this scope». Это не ваша ошибка и не битая библиотека — это два разных интерфейса под одним именем.
Лечения три, выбирайте по ситуации. Первое — откатить версию: в менеджере библиотек рядом с Install выберите ту, под которую написан скетч (для старых IRremote-скетчей — 2.x). Второе — переписать скетч под новую версию: откройте examples внутри установленной библиотеки, там рабочие примеры именно вашего API. Третье — не трогать: если проект работает и менять его незачем, зафиксируйте версию и забудьте про обновления до повода.
Правило сверок, которое я вывел за пару таких вечеров: примеры из папки установленной библиотеки всегда соответствуют её версии. Пример с форума — нет. Начинайте с examples, а форумные скетчи адаптируйте, сверяясь с ними. К слову, среда при каждой «Проверить» печатает в логе, из какой папки взята каждая библиотека и какой там номер версии — строка начинается с «Using library»: пользуйтесь ею, когда сомневаетесь, с чем именно собираетесь.
Мой рабочий принцип с оговоркой: переписываю под новые версии только то, что пишу с нуля. Старые работающие проекты живут на своих версиях библиотек — «работает — не трогай» касается и каталога libraries: обновление ради обновления в мире встроенных устройств регулярно ломает собранное.
- В симуляторе выведите на первую строку название своего будущего проекта латиницей, а во второй строке оставьте счётчик секунд — убедитесь, что setCursor(0, 1) затирает старый текст только там, где печатаете.
- Поменяйте интервал обновления с 1000 на 200 мс и посмотрите, как часто перерисовывается строка; на настоящем экране слишком частая перерисовка даёт мерцание — найдите разумный предел сами.
- На настоящей плате: установите библиотеку LiquidCrystal_I2C через менеджер, добавьте в начало скетча строки
#include <Wire.h>и#include <LiquidCrystal_I2C.h>— и этот же код оживит реальный экран. - Откройте Документы\Arduino\libraries, найдите в любой установленной библиотеке файл library.properties и сверьте версию с тем, что показывает менеджер. Теперь вы знаете, где живёт правда о версии.
- Менеджер библиотек — основной путь установки: версии, зависимости, обновления; ZIP — для заводских и редких библиотек
- Библиотеки живут в Документы\Arduino\libraries, внутри каждой — library.properties и examples
- «Multiple libraries were found» — предупреждение о дубликате: удалите лишнюю копию и перезапустите IDE
- Версия библиотеки — часть программы: API меняется между мажорными версиями (IRremote 2.x → 3.x сменил enableIRIn на IrReceiver.begin)
- Примеры в папке установленной библиотеки всегда соответствуют её версии — начинайте сверку с них
- 1. Куда Arduino IDE складывает установленные библиотеки?
- 2. После установки IRremote компилятор пишет «'enableIRIn' was not declared in this scope». Причина?
- 3. Что означает предупреждение «Multiple libraries were found for X.h»?
- 4. Библиотеки нет в менеджере — она пришла с заводской страницей модуля. Как её поставить?
Инструментальная база собрана: среда установлена, драйвер стоит, загрузка отработана, библиотеки под контролем. Заведите себе и папку со скриншотами рабочих версий: снимок карточки библиотеки с номером версии экономит вечер, когда форумная тема разбежалась по эпохам API. Дальше начинается то, ради чего всё затевалось, — настоящая схема на макетке: кнопки, резисторы, провода и первый проект, который нельзя отменить нажатием кнопки. С симулятора перейти на железо проще всего с тем же скетчем в руках: он уже проверен, осталось повторить его на реальной плате.
Частые вопросы по теме урока
- Куда Arduino IDE складывает установленные библиотеки?
- Библиотеки — файлы на компьютере: Документы\Arduino\libraries\ИмяБиблиотеки. Переустановка IDE их не трогает, а дубликаты чистятся вручную в этой папке. В Документы\Arduino\libraries
- После установки IRremote компилятор пишет «'enableIRIn' was not declared in this scope». Причина?
- Строка include у версий одинакова, а вызовы разные: 2.x — enableIRIn(), 3.x+ — IrReceiver.begin(). Лечение: откатить версию в менеджере или переписать скетч по examples. С версии 3.x API сменился: скетч писали под 2.x, а стоит новая версия
- Что означает предупреждение «Multiple libraries were found for X.h»?
- Это предупреждение о дубликате: в libraries лежат две копии одного заголовка. Сборка продолжится, но поведение может отличаться от ожидаемого — лишнюю копию стоит удалить. Найдено несколько копий библиотеки — компилятор возьмёт первую по списку
- Библиотеки нет в менеджере — она пришла с заводской страницей модуля. Как её поставить?
- Пункт «Добавить .ZIP библиотеку» распакует архив в Документы\Arduino\libraries. Следите за вложенностью папки: файлы .h должны быть не глубже одного уровня. «Скетч → Подключить библиотеку → Добавить .ZIP библиотеку…»