Jump to content
Asteriy

Управление светильником на Arduino

Recommended Posts

Добрый день. Пожалуйста помогите решить проблему запоминания текущего уровня в блоке управления светильником.

Питание светодиодов 12 Вольт через драйвер.

Имеется Arduino nano микроконтроллере ATmega328, управление на 2х кнопках: 1а убавить яркость и 2я прибавить яркость. Все работает, но при отключении питания все сбрасывается на минимальные значения установленные программой загруженной в Arduino. Как сделать так что бы при отключения сохранялись настройки яркости установленные в момент работы светильника?

Edited by Asteriy

Share this post


Link to post
Share on other sites

Раз в минуту (к примеру) сверяем текущее значение яркости с записанным в ячейку EEPROM и если оно отличается, записываем туда новое. Либо то же самое проделываем после события регулировки яркости.

Либо посложней - контролировать напряжение питания и как только оно начнёт падать, записываем текущее значение в EEPROM.

При включении программа первым делом пусть считывает эту ячейку и устанавливает значение как текущее..

Edited by Dr. West

Share this post


Link to post
Share on other sites

Сам скетч простой:

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
int brightness =0;    // переменная для задания яркости
int fadeValue = 5;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup()  { 
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход

void loop()  { // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
  }   
  brightness = constrain(brightness, 0, 255); // Эта функция задает крайние точки диапазона для переменной brightness 0 и 255
  analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  delay(50); // Пауза 50 миллисекунд.                            
}

 

Знания в программировании минимальные. Можете помочь написать управление памятью? Раз в минуту это наверное большой интервал, может лучше поменьше временной интервал?

Share this post


Link to post
Share on other sites

Технология Maxim Integrated nanoPower: когда малый IQ имеет преимущества

При разработке устройств с батарейным питанием важно выбирать компоненты не просто с малым потреблением, но и с предельно малым током покоя. При этом следует обратить внимание на линейку nanoPower производства компании Maxim Integrated. В статье рассмотрено их применение на примере системы датчиков беспроводной оконной сигнализации.

Подробнее

Не, я в ардуинах и "сях" не разбираюсь. Интервал вы можете делать какой хотите - это время на осознание пользователем того, что установлена желаемая яркость и больше регулировать не стОит. Можно вообще не ждать, но тогда EEPROM будет перезаписываться слишком часто, а ресурс её не бесконечен.

Share this post


Link to post
Share on other sites

Я так понимаю что нужно что-то типа такого скетча?

/*
 * EEPROM Write
 *
 * Сохраняет в энергонезависимой памяти EEPROM значения,
 * считанные с аналогового входа analog input 0.
 * Данные значения останутся в памяти и после отключения питания 
 * от платы и в будущем могут быть доступны для 
 * другого скетча.
*/

#include <EEPROM.h>

// текущее значение адреса EEPROM
int addr = 0;

void setup()
{
}

void loop()
{
  // деление на 4 необходимо, чтобы перевести значение от
  // 0-1023 к одному байту, т.к. EEPROM может хранить только 
  // значения от 0 до 255.
  int val = analogRead(0) / 4;
  
  // записываем значение в энергонезависимую память
  EEPROM.write(addr, val);
  
  // устанавливаем следующую ячейку памяти. 
  // т.к. EEPROM содержит всего 512 ячеек – при достижении 
  // конца памяти – возвращаемся на начало
  addr = addr + 1;
  if (addr == 512)
    addr = 0;
  
  delay(100);
}

А как теперь объединить управление яркостью и запись в память значения этой яркости?

 

Share this post


Link to post
Share on other sites
                     

Платы Nucleo на базе STM32G0: чего можно добиться с помощью связки Nucleo и Arduino

Платы Nucleo и платы расширения X-NUCLEO от STMicroelectronics можно интегрировать в платформу Arduino с помощью библиотеки STM32duino. Связка плат Nucleo и платформы Arduino, и наличие готовых библиотек – представляет удобный инструмент для создания прототипов и конечных приложений в условиях ограниченного времени. Статья содержит пошаговые инструкции по установке библиотек и запуску примеров для Nucleo.

Подробнее...

Попробуйте в начале скетча дописать

#include <avr/eeprom.h>
  
EEMEM unsigned int e_br;

В setup() добавить

brightness = eeprom_read_word(&e_br);

А в loop() в самом конце дописать

eeprom_update_word(&e_br, &brightness);

 

Share this post


Link to post
Share on other sites

@ARV ,

Посмотрите пожалуйста. Верно ли я вставил строки?

 

#include <avr/eeprom.h>
  
EEMEM unsigned int e_br;

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
int brightness =0;    // переменная для задания яркости
int fadeValue = 5;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup()  { 
brightness = eeprom_read_word(&e_br);
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход

void loop()  { // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
  }   
  brightness = constrain(brightness, 0, 255); // Эта функция задает крайние точки диапазона для переменной brightness 0 и 255
  analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  delay(50); // Пауза 50 миллисекунд.
  eeprom_update_word(&e_br, &brightness);                            
}

 

Share this post


Link to post
Share on other sites

Вроде да, хотя я с ардуино дел никогда не имел - мои рекомендации касаются исключительно подходов AVR-GCC, т.е. компилятора, встроенного в том числе и в среду ардуино.

Share this post


Link to post
Share on other sites

Выдает ошибку при проверке:

 

  This report would have more information with
  "Show verbose output during compilation"
  enabled in File > Preferences.
Arduino: 1.0.6 (Windows 7), Board: "Arduino Nano w/ ATmega328"
sketch_jul04a.ino: In function 'void loop()':
sketch_jul04a:24: error: 'eeprom_update_word' was not declared in this scope

Share this post


Link to post
Share on other sites

В Ардуино есть класс EEPROM поэтому замените:

#include <avr/eeprom.h>  на #include <EEPROM.h>

EEMEM unsigned int e_br  на unsigned int e_br

brightness = eeprom_read_word(&e_br)  на brightness = EEPROM.get(0, e_br)

eeprom_update_word(&e_br, &brightness)  на EEPROM.update(0, brightness )

Share this post


Link to post
Share on other sites

@snn_krs , в строке brightness = EEPROM.get(0, e_br); выдает ошибку:

  This report would have more information with
  "Show verbose output during compilation"
  enabled in File > Preferences.
Arduino: 1.0.6 (Windows 7), Board: "Arduino Nano w/ ATmega328"
sketch_jul04a.ino: In function 'void setup()':
sketch_jul04a:12: error: 'class EEPROMClass' has no member named 'get'
sketch_jul04a.ino: In function 'void loop()':
sketch_jul04a:25: error: 'class EEPROMClass' has no member named 'update'

Сам скетч:

 

#include <EEPROM.h>;
  
unsigned int e_br;

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
int brightness =0;    // переменная для задания яркости
int fadeValue = 5;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup()  { 
brightness = EEPROM.get(0, e_br);
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход

void loop()  { // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
  }   
  brightness = constrain(brightness, 0, 255); // Эта функция задает крайние точки диапазона для переменной brightness 0 и 255
  analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  delay(50); // Пауза 50 миллисекунд.
  EEPROM.update(0, brightness );                            
}

Share this post


Link to post
Share on other sites

дайте угадаю, размерность адреса не совпадает

Share this post


Link to post
Share on other sites

В версии 1.05 было только два метода read и write. Скачайте новее версию.

Share this post


Link to post
Share on other sites
Цитата

Попробуй это


  
  #include <EEPROM.h>
  
int adress;
unsigned long zaderzka=30000;
byte brightness_old;
unsigned long time;

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
byte brightness =0;    // переменная для задания яркости
byte fadeValue = 5;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup() 
{ 
brightness = EEPROM.read(adress);
brightness_old=brightness;
time=millis();
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход
} 

void loop() 
{ // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
  }   
  brightness = constrain(brightness, 0, 255); // Эта функция задает крайние точки диапазона для переменной brightness 0 и 255
  analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  delay(50); // Пауза 50 миллисекунд.
   if((millis()-time)>zaderzka)
   {
   if(brightness!=brightness_old)
     {
       EEPROM.write(adress,brightness);  
       brightness_old=brightness;
     }
       time=millis();
   }
} 

 

 

Edited by skripach

Share this post


Link to post
Share on other sites

@skripach , спасибо!

Запоминает позицию.

Два вопроса.

1) Можно ли заменить бесконечный цикл, т.е. при что бы при нажатии на кнопку убавить в минимум потом не зажигалось в полный накал и тоже самое с кнопкой прибавить - не перескакивал на минимальный уровень? Собственно так было и задумано что при убавлении не включался максимум и наоборот.

2) При включении питания на 1 секунду зажигается светильник на максимум, а потом на уровень сохранившийся в памяти. Можно ли что бы при включении не зажигалось на момент на максимум, а сразу с сохраненного уровня?

Share this post


Link to post
Share on other sites
#include <EEPROM.h>
  
int adress;
unsigned long zaderzka=300000;
int brightness_old;
unsigned long time;

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
int brightness =0;    // переменная для задания яркости
byte fadeValue = 5;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup() 
{ 
brightness = EEPROM.read(adress);
brightness_old=brightness;
time=millis();
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход
analogWrite(ledPin, brightness);
} 

void loop() 
{ // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
    if(brightness>255) brightness=255;
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
    if(brightness<=0)brightness=5;
  }   
  brightness = constrain(brightness, 0, 255); // Эта функция задает крайние точки диапазона для переменной brightness 0 и 255
  analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  delay(50); // Пауза 50 миллисекунд.
   if((millis()-time)>zaderzka)
   {
   if(brightness!=brightness_old)
     {
       EEPROM.write(adress,(byte)brightness);  
       brightness_old=brightness;
     }
     time=millis();
   }
} 

 

Edited by skripach

Share this post


Link to post
Share on other sites

@skripach ,

 

#include <EEPROM.h>
  
int adress;
unsigned long zaderzka=300000;
int brightness_old;
unsigned long time;

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
int brightness =0;    // переменная для задания яркости
byte fadeValue = 3;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup() 

brightness = EEPROM.read(adress);
brightness_old=brightness;
time=millis();
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход
analogWrite(ledPin, brightness);

void loop() 
{ // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
    if(brightness>255) brightness==255;
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
    if(brightness<=0)brightness=0;
  }   
  brightness = constrain(brightness, 0, 255); // Эта функция задает крайние точки диапазона для переменной brightness 0 и 255
  analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  delay(50); // Пауза 50 миллисекунд.
   if((millis()-time)>zaderzka)
   {
   if(brightness!=brightness_old)
     {
       EEPROM.write(adress,(byte)brightness);  
       brightness_old=brightness;
     }
     time=millis();
   }

 

Не убавлялось до полного отключения.  В строке if(brightness<=0)brightness=5; поменял 5 на 0 - if(brightness<=0)brightness=0; Верно ли я понял?

Не запоминает теперь позицию. Все время включается из одной позиции.

Share this post


Link to post
Share on other sites
#include <EEPROM.h>
  
int adress;
unsigned long zaderzka=300000;
byte brightness_old;
unsigned long time;

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
int brightness =0;    // переменная для задания яркости
byte fadeValue = 5;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup() 
{ 
brightness = EEPROM.read(adress);
brightness_old=brightness;
time=millis();
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход
analogWrite(ledPin, brightness);
} 

void loop() 
{ // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
    if(brightness>255) brightness==255;
    analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
    if(brightness<0)brightness=0;
    analogWrite(ledPin, brightness);    // устанавливаем на выводе ledPin значение яркости яркость brightness
  }   
 
  delay(50); // Пауза 50 миллисекунд.
  
   if((millis()-time)>zaderzka)
   {
   if(brightness!=brightness_old)
     {
       EEPROM.write(adress,byte(brightness));  
       brightness_old=brightness;
     }
     time=millis();
   }
} 

 

Share this post


Link to post
Share on other sites

@skripach . право мне не удобно уже)

Но снова запустился бесконечный цикл. Но позицию запоминает.

Share this post


Link to post
Share on other sites

Там была ошибка. Пробуй эту!

#include <EEPROM.h>
  
int adress;
unsigned long zaderzka=300000;
byte brightness_old;
unsigned long time;

int ledPin = 11;      // Присваиваем имя ledPin цифровому выводу 11, к которому подключен светодиод
int brightness =0;    // переменная для задания яркости
byte fadeValue = 5;    // шаг изменения яркости
int buttonPlus=2;     //  Номер Pin к которому подключена кнопка "+" 
int buttonMinus=3;    //  Номер Pin к которому подключена кнопка "-"
 
void setup() 
{ 
brightness = EEPROM.read(adress);
brightness_old=brightness;
time=millis();
pinMode(ledPin, OUTPUT); // Инициализируем цифровой вывод ledPin (pin 11) как выход
analogWrite(ledPin,byte(brightness));
} 

void loop() 
{ // Этот цикл будет выполняться бесконечное количество раз.
  if (digitalRead(buttonPlus) == HIGH) { //если на выводе 2 (кнопка "+") высокий уровень (нажата), то
    brightness +=  fadeValue; // прибавляем значение яркости с шагом fadeValue
    if(brightness>255) brightness=255;
    analogWrite(ledPin,byte(brightness));    // устанавливаем на выводе ledPin значение яркости яркость brightness
    time=millis();
  }   
  if (digitalRead(buttonMinus) == HIGH) { //если на выводе 3 (кнопка "-") высокий уровень (нажата), то
    brightness -=  fadeValue; // уменьшаем значение яркости с шагом fadeValue
    if(brightness<0)brightness=0;
    analogWrite(ledPin,byte(brightness));    // устанавливаем на выводе ledPin значение яркости яркость brightness
    time=millis();
  }   
 
  delay(50); // Пауза 50 миллисекунд.
  
   if((millis()-time)>zaderzka)
   {
   if(brightness!=brightness_old)
     {
       EEPROM.write(adress,byte(brightness));  
       brightness_old=brightness;
     }
     time=millis();
   }
} 

 

поменяй

unsigned long zaderzka=300000;

на

unsigned long zaderzka=30000;

(30000 миллисекунд время через которое будет запоминать значение)

Edited by skripach

Share this post


Link to post
Share on other sites

@skripach , класс! Здорово!

unsigned long zaderzka=300000 - это время обновления записи позиции кнопки в память?

 

Допустим мне понадобится подключить еще один канал с аналогичным управлением и записью позиции кнопки в память, то что нужно продублировать в скетче?

Share this post


Link to post
Share on other sites

Join the conversation

You are posting as a guest. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...

×
×
  • Create New...