Общие сведения
Датчик влажности почвы с нержавеющими щупами — две иглы в литой пластиковой головке на проводе длиной 3 метра. Пригодится для автополива: следить за влажностью в горшке, на грядке или в теплице и вовремя узнать, что земля пересохла. Иглы уходят в землю, а плата с электроникой остаётся в сухом месте — на то и три метра провода.
Устроен датчик предельно просто: своей платы, микросхем и светодиодов внутри нет, это честно два электрода на проводе. В землю уходят стальные иглы, а не дорожки на плате. От головки идёт двужильный чёрный провод, на конце — двухконтактный разъём с защёлкой. Схема, которая превращает землю в число, собирается уже на вашей стороне.
И сразу про главное, чтобы потом не было обид: датчик показывает не «влажность в процентах», а проводимость почвенного раствора между иглами. Для полива этого хватает: вы снимаете на своей земле две отметки, «сухо» и «полито», и дальше живёте по ним.
Датчик пассивный. У него нет вывода Signal (S), нет цифрового выхода, нет подстроечника и порога срабатывания. Сам по себе он ничего не показывает: число появляется только в вашей схеме — делитель напряжения плюс аналоговый вход. Как это собрать — в разделе «Подключение».
Характеристики
- Тип датчика: кондуктометрический (резистивный), два электрода
- Материал щупов: нержавеющая сталь
- Провод: двужильный, длина 3 м
- Разъём на конце провода: двухконтактный, с защёлкой
- Выход датчика: пассивный, сопротивление между щупами
Напряжение и ток задаёт ваша схема — у самого датчика их нет.
Подключение
Внутри датчика нет ни платы, ни микросхем, ни усилителя — это две стальные иглы на проводе, то есть переменный резистор, который сам по себе ничего не выдаёт. Наружу к нему нужно добавить ровно одну деталь: постоянный резистор. Вместе они дают делитель напряжения, и уже с середины этого делителя аналоговый вход Arduino снимает число. Операционный усилитель, компаратор, транзистор и подтягивающие резисторы тут не нужны — напряжение на входе получается сразу в вольтах, а не в милливольтах, усиливать нечего.
И ещё одна причина, по которой встроенного АЦП хватает без всякой обвязки: вход «видит» не сопротивление земли, а сопротивление земли параллельно вашему резистору, то есть величину, которая никогда не больше самого резистора. Даташит ATmega328P (это мозг Uno и Nano) просит источник сопротивлением примерно до 10 кОм — значит, поставив резистор не больше 10 кОм, вы укладываетесь в это требование при любой влажности: и в мокрой земле, и в пересохшей, где между иглами сотни килоом.
Что приготовить
- Плату. Для начала удобнее всего Arduino Uno R3, а если коробочку с электроникой прячут у самой грядки — Arduino Nano.
- Постоянный резистор 4,7 кОм. Он есть в наборе резисторов, там же рядом 2,2 и 1 кОм — пригодятся, если захотите подобрать номинал под свою землю.
- Керамический конденсатор 0,1 мкФ. Не обязателен, но с ним замер чище: он снимает высокочастотный мусор от насоса и отдаёт заряд входу АЦП вместо трёхметрового провода.
- Место, где всё это соединить: макетная плата и провода «мама-мама» — паять не нужно ничего. На постоянную установку жилы лучше посадить на винтовой клеммник.
Шилды Trema Shield, Trema Power Shield, Motor Shield и Trema Set Shield самому датчику не помогут: у него двухконтактный разъём и нет вывода сигнала, а делитель всё равно собирается отдельно. Зато они пригодятся для остального хозяйства — насоса, реле, экрана.
Собираем делитель, по шагам
- Жилы у датчика равноправные, полярности нет — втыкайте любой стороной. Запомните только, что игла со стороны питания работает анодом и съедается быстрее: раз в сезон жилы полезно поменять местами, тогда износ пойдёт на вторую иглу.
- Первую жилу — на цифровой вывод платы, в примерах это вывод 7. Он подаёт питание на щуп только на момент замера. Годится любой цифровой вывод, кроме 0 и 1 (заняты монитором порта) и 13 (на нём светодиод платы с резистором).
- Вторую жилу — в свободный ряд макетной платы. Этот ряд и есть средняя точка делителя, весь смысл схемы в нём.
- Из того же ряда — резистор 4,7 кОм на вывод GND.
- Из того же ряда — провод на аналоговый вход A0. На Uno и Nano годятся A0–A3: A4 и A5 отданы шине I2C, и если на ней что-то висит, аналоговыми они уже не будут.
- Туда же, между A0 и GND, — конденсатор 0,1 мкФ, обязательно у самой платы. Только керамику: электролит на 1 мкФ и больше не успеет зарядиться за паузу в скетче, и показания уедут в «сухо».
- Резистор и конденсатор ставьте у платы, а не у щупа — тогда длинный провод остаётся в «сильной» части цепи.
- На GND у этого датчика не сажают ни одну жилу: у него всего два провода, и оба сигнальные. Третьего провода искать не надо.
- Опорное напряжение АЦП не трогайте, пусть остаётся по умолчанию — питание платы. Тогда делитель и АЦП питаются от одного источника, показание получается отношением, и просадка питания при пуске насоса на него почти не влияет. Внутреннюю подтяжку на A0 тоже не включайте: она 20–50 кОм и просто подмешается в ваш делитель, а отдельная подтяжка и не нужна — нижний резистор и есть подтяжка вниз.
Получается цепочка: вывод 7 → иглы в земле → средняя точка → резистор 4,7 кОм → GND, а с середины снимается напряжение на A0.
Куда смотрит число
Показание считается так: N = 1023 × R / (R + сопротивление земли). Земля мокрее — сопротивление между иглами меньше — число больше. С резистором 4,7 кОм выходит примерно такая картина:
- иглы замкнуты накоротко (уронили щуп в воду) — 1023;
- между иглами 2,2 кОм, земля мокрая — 697;
- 4,7 кОм — 512, ровно половина шкалы;
- 22 кОм, подсохла — 180;
- 100 кОм, сухая — 46;
- обрыв провода или выдернутый разъём — 0.
Свои числа у вас будут другими — они зависят от земли, удобрений и глубины игл, на то и калибровка. Важно направление: мокрее = больше. Оба скетча в разделе «Примеры» написаны именно под эту схему. Если соберёте зеркально (резистор к выводу питания, щуп на GND), число перевернётся, и в скетче придётся развернуть знаки сравнения, поменять местами отметки levelDry и levelWet и переписать проверку на обрыв: в зеркальной схеме обрыв выглядит не как 0, а как 1023. Выигрыша у зеркального варианта никакого, так что лучше собирайте как на картинке.
Почему 4,7 кОм и когда его менять
Рабочий коридор — от 1 до 10 кОм, и обе границы взяты не с потолка.
- Снизу ограничивает вывод контроллера. Худший случай — иглы замкнула вода: тогда через вывод течёт питание, делённое на резистор. При 4,7 кОм это 1,1 мА, при 1 кОм — 5 мА, а даташит ATmega328P даёт на вывод 40 мА как абсолютный максимум, за которым за вывод уже никто не отвечает. То есть запас почти в сорок раз, и никаких ключей и транзисторов щупу не нужно. А вот на 100 Ом вывод упрётся в свой предел, на 10 Ом уйдёт за него в разы — такие номиналы из набора сюда не ставьте.
- Сверху ограничивает АЦП: он рассчитан на источник примерно до 10 кОм. В наборе резисторов ближайший к этому потолку номинал как раз 4,7 кОм — следующий там уже 22 кОм.
Подбор внутри коридора простой. На политой земле число упёрлось в 1023 — поставьте резистор поменьше, 2,2 или 1 кОм. На сухой лежит у самого нуля — побольше. Если и на 4,7 кОм разброс между сухой и политой землёй маленький, можно попробовать 22 кОм, но тогда конденсатор 0,1 мкФ обязателен, а паузу delay(10) в скетче поднимите до delay(25): с 22 кОм напряжение устаивается около 15 мс, в десять миллисекунд оно не укладывается и показания занизятся.
Питание на щуп берите только с цифрового вывода самой платы. Отдельный источник сюда ставить нельзя: напряжение со средней точки делителя приходит прямо на аналоговый вход, а даташит ATmega328P разрешает на любом выводе не больше, чем питание платы плюс 0,5 В. Подадите на щуп 12 В от насоса — вход выгорит. Силовой ключ для щупа тоже не годится: он нижний, коммутирует минус нагрузки, плюс им не подашь — да и незачем, речь про один миллиампер. Ключ оставьте насосу. И если плата у вас 3,3-вольтовая, щуп питается её же 3,3 В.
Если датчиков несколько
- У каждого свой цифровой вывод питания, свой резистор и свой аналоговый вход. Один вывод питания на два щупа не вешают никогда.
- Мерить строго по очереди. Выводы питания неработающих датчиков держите отключёнными (INPUT), а не в LOW: заземлённая игла соседа уводит часть тока мимо вашего делителя, и работающий датчик покажет суше, чем есть на самом деле.
- Щупы разносите по горшку или грядке, а не втыкайте рядом — иначе меряете один и тот же пятачок.
- Не хватает аналоговых входов — поставьте внешний 16-битный АЦП ADS1115: у него 4 входа и 4 адреса, до 16 точек на одной шине I2C. Питайте его тем же напряжением, что и щуп: по его карточке напряжение на входах не должно превышать питание модуля больше чем на 0,3 В, так что связка «ADS1115 от 3,3 В плюс щуп от пятивольтового вывода» не годится.
Провода и трасса
- Обе жилы датчика ведите до платы парой и подальше от силовых проводов насоса: три метра исправно ловят наводки.
- Разъём не подошёл к вашей плате — посадите жилы на винтовой клеммник.
- Не хватило длины — нарастите силиконовым проводом: он не дубеет на улице и не ломается на изгибах. Наращивайте обе жилы и делайте скрутку герметичной — мокрая скрутка подмешивается в делитель и сдвигает обе отметки.
Бережём электроды: замер с переполюсовкой
Под напряжением в мокрой земле идёт электролиз, и металл с иглы понемногу уходит в почву. Первое средство уже в скетчах: питание подаётся только на момент замера, щуп под напряжением около 30 мс, а в скетче полива замер идёт раз в минуту — это сотые доли процента времени. Кому хочется аккуратнее — меняйте полярность от замера к замеру: тогда каждая игла одинаково долго бывает и плюсом, и минусом, а средний постоянный ток близок к нулю.
Схема почти та же, переезжает только нижний конец резистора:
- первая жила датчика — на вывод 7, как и раньше;
- вторая жила — в среднюю точку, и на ней же по-прежнему сидит A0;
- резистор 4,7 кОм идёт из средней точки не на GND, а на второй цифровой вывод, например 8;
- первый замер: вывод 7 в HIGH, вывод 8 в LOW — число читается как обычно;
- второй замер: наоборот, 7 в LOW, 8 в HIGH. Плечи делителя поменялись местами, поэтому второе число надо пересчитать как 1023 минус показание. Среднее двух и есть результат;
- между замерами оба вывода сначала переводят в LOW и только потом в INPUT. Переведёте во вход, не погасив единицу, — включится внутренняя подтяжка, и щуп останется под напряжением, ровно то, от чего уходили.
Предельный ток тут задаёт тот же резистор, что и в обычной схеме, так что по части вывода платы ничего не меняется. А вот отметки «сухо» и «полито» для этого варианта снимайте заново — с прежними они не совпадут. И не вешайте щуп прямо между двумя выводами без резистора: мерить будет нечем (делителя нет), а на мокрой земле два вывода окажутся соединены почти накоротко.
Насос или клапан: силовой ключ
Насос, клапан или лампу на выводы платы напрямую не вешают: вывод отдаёт миллиамперы, а насосу нужны амперы. Между платой и насосом ставят силовой ключ N-канал — это наш Trema-модуль на полевом транзисторе, и для полива он подходит лучше всего: по его карточке он коммутирует постоянное напряжение до 30 В и ток до 10 А (от 6 А производитель советует радиатор), сам питается от 3 до 5,5 В, а джамперами на плате выбирается, откуда брать питание нагрузки — от Arduino или от отдельного источника. В комплекте трёхпроводной шлейф, так что паять ничего не нужно.
- Ключ нижний: он размыкает минус нагрузки. Плюс насоса идёт прямо от блока питания, а минус — через ключ. Поэтому минус блока питания и GND платы обязательно соединяют вместе: без общей земли ключ просто не откроется.
- Управляется ключ с любого цифрового вывода, в примерах это вывод 8. Транзистор N-канальный, открывается логической единицей, поэтому digitalWrite(pinPump, HIGH) в скетче означает «включить».
- Повесьте резистор 10 кОм с управляющего вывода на GND. От включения питания до первой строки скетча проходит около секунды — сброс и загрузчик, — и всё это время вывод висит в воздухе. Удержать насос выключенным может только этот резистор, перестановка строк в скетче тут не поможет.
- Нагрузка индуктивная — мотор насоса, катушка клапана — поэтому поставьте параллельно ей защитный диод, катодом к плюсу.
- Питание у насоса своё, отдельное. С 5 В платы и тем более от USB насос не питают.
- реле нужно в двух случаях: если нагрузка переменного тока (ключ умеет только постоянное) или если нужна развязка между платой и силовой частью. Тогда насос сажают на нормально разомкнутую пару контактов, чтобы и ноль на входе «S», и перезагрузка платы оставляли полив выключенным; наше реле срабатывает от логической единицы, так что скетч менять не придётся. Ставите чужой релейный модуль — сверьтесь с его описанием: у многих активный уровень обратный, и тогда HIGH и LOW в скетче надо поменять местами.
- Прежде чем шланг окажется в горшке, проверьте всё на столе: подайте питание, нажмите RESET несколько раз и убедитесь, что насос не дёргается.
Поливать удобно мембранным насосом из бочки или канистры, а если вода уже под давлением — поставьте нормально закрытый соленоидный клапан: при пропаже питания полив перекроется сам. И про гидравлику, она отвечает за самый дорогой отказ: бак ставьте ниже горшка или хотя бы поднимите петлю шланга выше уровня воды в баке. Если бак стоит выше, вода пойдёт в горшок самотёком через остановленный насос, и никакая программа этого не увидит. Поплавковый датчик уровня воды в баке — защита не от залива, а от сухого хода насоса: это разные беды и разные средства.
У пассивного датчика обрыв провода выглядит как очень сухая земля: на входе почти ноль, и автоматика честно включит насос. Поэтому в скетче полива стоит нижний порог — число ниже 20 скетч считает обрывом, зажигает светодиод платы и не поливает. По той же причине вынимать щуп из земли (на зиму, на промывку, на пересадку) можно только после того, как снято питание с насоса. А если хотите отличать обрыв наверняка — припаяйте прямо на контакты разъёма датчика, параллельно жилам, резистор 100 кОм и закройте термоусадкой: целый датчик тогда даже в воздухе не покажет меньше 46, а ноль на входе будет означать только одно — цепь до щупа порвана.
Подробнее о датчике
Ток между иглами несут не «вода» и не «почва» сами по себе, а ионы, растворённые в почвенной влаге: соли, остатки удобрений, минералы из самой земли. Чем больше в порах воды, тем больше сплошных плёнок-мостиков между частицами грунта и тем ниже сопротивление. Земля сохнет — плёнки рвутся, между частицами остаётся воздух, и сопротивление растёт резко. Поэтому весь полезный ход показаний приходится на средний и влажный диапазон.
Отсюда понятно, чего от такого датчика ждать не стоит:
- Влажности в процентах. Меряется проводимость, перевод в проценты возможен только своей калибровкой и остаётся оценкой.
- Одинаковых чисел в разных горшках. Песок, суглинок, торф и покупная смесь при одинаковом поливе дадут разные числа, а воздушный зазор у иглы читается как «сухо».
- Независимости от удобрений. После подкормки показания уходят в «влажнее», после промывки грунта чистой водой — в «суше», хотя воды столько же.
- Чувствительности в пересушенной земле. Там сопротивление огромное, и «сухо» от «совсем сухо» датчик почти не отличает.
- Картины по всему горшку. Меряется пятачок между иглами: рядом с поливочной струёй и в углу вазона будет разное, на грядке ставят несколько точек.
Электроды в земле изнашиваются. Под напряжением идёт электролиз: металл понемногу уходит в почву, на иглах копится налёт, показания дрейфуют. У стальной иглы нет тонкого покрытия, которое можно протереть насквозь, как у щупа, вырезанного из печатной платы (такой у нас тоже есть — датчик влажности почвы, резистивный), но и она не вечная. Если мешают именно открытые электроды в земле, посмотрите емкостной датчик влажности почвы: у него электроды закрыты, и, по его карточке, он не подвержен коррозии.
И раз удобрения влияют на показания напрямую, в теплице и на гидропонике подкормку лучше дозировать отдельно — например, блоком перистальтических насосов, а не ловить их этим щупом.
Калибровка и уход
- Обе отметки снимайте на той земле, в которой датчик будет жить: сухая земля комнатной температуры — первое число, она же после нормального полива, когда вода разойдётся, — второе.
- Снимайте отметки заново после смены грунта, пересадки, подкормки и промывки земли чистой водой.
- Иглы должны быть в земле по всей рабочей длине, грунт вокруг обожмите, а головку, место входа провода и разъём не заглубляйте и держите выше уровня полива.
- Появился налёт — достаньте щуп, промойте, при необходимости пройдитесь мягкой щёткой, и снимите обе отметки заново: после чистки они сдвинутся.
- На зиму и на время простоя системы датчик из земли доставайте — но сначала обесточьте полив: вынутый из земли щуп читается как «очень сухо». Тянуть его из грунта нужно за головку, а не за провод.
Примеры
Вывод показаний датчика в монитор порта.
Залейте этот скетч, откройте монитор порта и запишите два числа: на сухой земле и после нормального полива, когда вода разойдётся. Это и есть ваши отметки «сухо» и «полито», дальше всё считается от них. Число обновляется раз в две секунды, так что видно, как оно растёт при поливе и когда перестаёт.
const uint8_t pinPower = 7; // Создаём константу с номером вывода, которым подаём питание на щуп
const uint8_t pinSensor = A0; // Создаём константу с номером входа, к которому подключена средняя точка делителя
int readSoil(){ // Функция замера: подаём питание, читаем, снимаем питание
uint32_t sum = 0, cnt = 0; // Создаём переменные для суммы замеров и для их количества
pinMode(pinPower, OUTPUT); // Делаем вывод выходом ...
digitalWrite(pinPower, HIGH); // ... и подаём питание на щуп
delay(10); // Даём напряжению на делителе устояться
uint32_t t = millis(); // Запоминаем время начала серии замеров
while(millis() - t < 20){ // Меряем ровно 20 мс - это период сетевой наводки 50 Гц ...
sum += analogRead(pinSensor); // ... складываем все замеры, и наводка в сумме гасит сама себя
cnt++; // ... и считаем, сколько замеров успело набежать
}
digitalWrite(pinPower, LOW); // Снимаем питание со щупа ...
pinMode(pinPower, INPUT); // ... и отключаем вывод совсем: цепь через электроды разорвана
return sum / cnt; // Возвращаем среднее по всей серии
}
void setup(){
Serial.begin(9600); // Инициируем передачу данных по последовательному порту на скорости 9600 бит/сек
pinMode(pinPower, INPUT); // Пока замера нет, вывод отключён совсем - через электроды ничего не течёт
}
void loop(){
Serial.println(readSoil()); // Выводим показание датчика: чем земля мокрее, тем число больше
delay(2000); // Ждём 2 секунды - так видно, как число растёт при поливе и когда перестаёт
}
Полив по своим отметкам.
Тот же замер, но с насосом. Числа levelDry и levelWet поставьте свои, из первого скетча; насос включается через реле или силовой ключ, а не с вывода платы напрямую. В скетче две защиты, без которых полив однажды закончится лужей. Первая: у пассивного датчика обрыв провода выглядит как очень сухая земля, поэтому число ниже levelBreak скетч считает неисправностью и насос не включает. Вторая: если после всех разрешённых порций земля так и не дошла до отметки «полито», значит воды нет или слетел шланг — скетч взводит аварию, зажигает светодиод платы и больше не поливает, пока вы не разберётесь и не перезапустите плату.
const uint8_t pinPower = 7; // Вывод, которым подаём питание на щуп
const uint8_t pinSensor = A0; // Вход, к которому подключена средняя точка делителя
const uint8_t pinPump = 8; // Вход реле или силового ключа, через который включается насос
const int levelDry = 300; // ВАШЕ число «сухо», снятое на своей земле (у каждого грунта оно своё)
const int levelWet = 600; // ВАШЕ число «полито», снятое на своей земле
const uint32_t timePump = 5000; // Сколько миллисекунд льём за один раз (подберите под свой горшок)
const uint8_t maxTry = 4; // Сколько порций подряд разрешаем долить за один полив
const int levelBreak= 20; // Ниже этого числа живой земли не бывает: так выглядит обрыв провода
bool fault = false; // Взводится при аварии: пока он поднят, насос не включаем
int readSoil(){ // Замер такой же, как в примере выше
uint32_t sum = 0, cnt = 0; // Создаём переменные для суммы замеров и для их количества
pinMode(pinPower, OUTPUT); // Делаем вывод выходом ...
digitalWrite(pinPower, HIGH); // ... и подаём питание на щуп
delay(10); // Даём напряжению на делителе устояться
uint32_t t = millis(); // Запоминаем время начала серии замеров
while(millis() - t < 20){ // Меряем ровно 20 мс - это период сетевой наводки 50 Гц ...
sum += analogRead(pinSensor); // ... складываем все замеры
cnt++; // ... и считаем, сколько их набежало
}
digitalWrite(pinPower, LOW); // Снимаем питание со щупа ...
pinMode(pinPower, INPUT); // ... и отключаем вывод совсем: цепь через электроды разорвана
return sum / cnt; // Возвращаем среднее по всей серии
}
void setup(){
Serial.begin(9600); // Инициируем передачу данных по последовательному порту на скорости 9600 бит/сек
pinMode(pinPower, INPUT); // Щуп обесточен, вывод отключён совсем
pinMode(pinPump, OUTPUT); // Конфигурируем вывод управления насосом как выход
digitalWrite(pinPump, LOW); // Насос при старте выключен
pinMode(LED_BUILTIN, OUTPUT); // Светодиод платы будет гореть при аварии
}
void loop(){
int soil = readSoil(); // Смотрим, что в горшке
Serial.println(soil); // Заодно пишем число в монитор порта, чтобы видеть картину
if(soil < levelBreak){ // Такого низкого числа живая земля не даёт ...
fault = true; // ... значит оборван провод или выскочил разъём, поливать нельзя
Serial.println(F("Датчик не отвечает: обрыв провода или разъём"));
}
if(soil > 1013){ // Почти максимум - щупы замкнуты или залит разъём ...
Serial.println(F("Щупы замкнуты или залит разъём: полива не будет"));
}
if(!fault && soil < levelDry){ // Если аварии нет и земля суше вашей отметки «сухо», то ...
uint8_t i = 0; // ... считаем вылитые порции
while(i != maxTry && readSoil() < levelWet){ // ... льём порциями, пока земля не дойдёт до отметки «полито»
digitalWrite(pinPump, HIGH); // Включаем насос
delay(timePump); // Льём заданное время
digitalWrite(pinPump, LOW); // Выключаем насос
delay(120000); // Ждём 2 минуты, чтобы вода дошла до щупа
i++; // Порция израсходована
}
if(readSoil() < levelWet){ // Вылили всё, что разрешено, а земля так и не намокла ...
fault = true; // ... значит воды нет или слетел шланг, больше не поливаем
Serial.println(F("Полив не помог: проверьте воду, насос и шланг"));
}
}
digitalWrite(LED_BUILTIN, fault); // Горит светодиод платы - система в аварии, полива не будет
delay(60000); // Пока полива нет, проверяем землю раз в минуту
}
Комплектация
- 1x Датчик влажности почвы с нержавеющими щупами (провод 3 м);

















