Пакет поддержки Arduino: аналоговый вход - фоторезистор
В предыдущих примерах для пакета поддержки Arduino были широко рассмотрены цифровые выходы/выходы, в этом примере мы перейдём к работе с аналоговым входом. При помощи пакета поддержки Arduino реализуем в модели Engee программу считывания сигнала от фоторезистора и обработки поступающих данных для реализации датчика освещённости.
Введение
Ранее реализация логика работы датчика освещённости была смоделирована в похожем примере для МИК 32 Амур. Здесь мы используем пакет поддержи, чтобы переносить модель на контроллер автоматически.
В примере используются:
- отладочная плата Arduino Mega,
- макетная плата,
- фоторезистор (LDR) GL5516,
- резистор 4.7 кОм (2шт),
- соединительные провода.
Задача модели: по поступающему на аналоговый вход значению падения напряжения на токоограничивающих резисторах в цепи фоторезистора рассчитать освещённость.
Аппаратная часть
Соединим элементы, как показано на схеме ниже:

Величина падения напряжения на токоограничивающих резисторах будет обработана АЦП на аналоговом входе A0 микроконтроллера. Модель Engee для обработки поступающего сигнала представлена ниже.
Модель примера
Настройки блока конфигурации таргета (EDM-Target-Arduino) оставим такими, как в предыдущем примере - светодиодная матрица.
В блоге чтения с аналогового канала (Arduino-analogRead) установим номер пина используемого аналогового канала A0 - 54.

В схеме при помощи простейших математических блоков рассчитывается сопротивление фоторезистора R_LDR исходя из цифрового значения от АЦП канала A0.
Освещённость Lux в свою очередь определяется по значению сопротивления фоторезистора из функции связи переменных .
Определение функции
Связь сопротивления фоторезистора и освещённости может быть определена из его характеристик - например, согласно Fig.1 на стр. 4 из паспортных данных.
Возьмём следующие центральные точки из области характеристики:
x_Ohm = [3e4, 7e3, 2e3];
y_Lux = [1, 10, 100];
Саму же зависимость можно определить как степенную функцию вида
где - сопротивление фоторезистора [Ом], - освещённость [Лк], - коэффициент, - показатель степени.
Для оптимизации функции и нахождения коэффициентов по определённым ранее точкам характеристики добавим следующие пакеты:
]add LsqFit
]add Statistics
Далее перейдём к непосредственному нахождению коэффициентов функции:
using Plots; gr(format=:png)
using LsqFit, Statistics
model(x_Ohm, p) = p[1] .* x_Ohm .^ p[2]
# Начальные параметры
p0 = [1e7, -1.0]
# Подгонка кривой
fit = curve_fit(model, x_Ohm, y_Lux, p0)
# Параметры формулы
a, b = fit.param
println("Формула: y = $a * x ^ ($b)")
# Расчет R²
ss_res = sum((y_Lux .- model(x_Ohm, fit.param)).^2) # сумма квадратов остатков
ss_tot = sum((y_Lux .- mean(y_Lux)).^2) # общая сумма квадратов
r2 = 1 - ss_res/ss_tot
println("R² = $r2")
Конечно, расчёт для двух точек при подгонке функции не является необходимостью. Мы используем данную оценку для того, чтобы удостовериться, что построенная кривая проходит через исходные точки. Построим кривую и точки на плоскости:
plot(x_Ohm, y_Lux)
plot!(collect(1e3:3e4), a.*collect(1e3:3e4).^b)
Полученные коэффициенты:
@show a;
@show b;
также вписаны в обратные вызовы модели.
Подготовка
При помощи этого блока кода автоматизируем запуск серверной программы Engee.Интеграции:
import .engee.package as epkg
const PKGNAME = "Engee-Device-Manager"
function epkg_start(pkg::String)
if !epkg.isinstalled(pkg)
@info "Package not installed. Installing and Starting..."
epkg.install(pkg)
@info "Package is up to date. Starting..."
println("Ссылка для подключения к серверу:\n"*epkg.start(pkg))
else
updates = epkg.checkupdates(pkg)
if isnothing(updates)
@info "Package is up to date. Starting..."
println("Ссылка для подключения к серверу:\n"*epkg.start(pkg))
else
@info "Updates available. Reinstalling and Starting..."
epkg.update(pkg)
@info "Package is up to date. Starting..."
println("Ссылка для подключения к серверу:\n"*epkg.start(pkg))
end
end
end
epkg_start(PKGNAME)
Также за кадром, как обычно, запустим клиентскую программу Engee.Интеграции и подключим наше устройство.
Выполнение модели
Запустим в интерактивном режиме работу модели и будем наблюдать ход расчётов сопротивления фоторезистора и освещённости при изменении яркости света в помещении.
Изменения в яркости окружающей среды приводят, как мы видим, к соответствующим изменениях рассчитанного значения освещённости. Далее, для "боевого" использования разработанного датчика, конечно, следует соотнести рассчитанные значения со значениями освещённости от поверенного измерителя.
Заключение
В примере, как нам и требовалось, мы рассмотрели работу с блоком цифрового входа из пакета поддержки Arduino, начав реализацию датчика освещённости.
