Еще раз мигаем светодиодом без Delay

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

alexbmd пишет:
искусство а не программирование
Программирование и есть искусство.

DetSimen
DetSimen аватар
Offline
Зарегистрирован: 25.01.2017

qwone пишет:

А если в коде куча ветвлений, то многие ветви будут выполнятся в только в исключительных ситуациях, а нормальной ситуации процессор на них не будет затрачивать ни такта.

Будет, Пух, будет.  Хотя бы на проверку условия. 

Pyotr
Offline
Зарегистрирован: 12.03.2014

Иногда нужно миганием светодиода отображать режим работы простого устройства.
Например: 1 блинк-температура ниже уставки, 2-в пределах нормы, 3-перегрев.

Выложу пример для новичков. Хотя сомневаюсь, что кто-то дочитает до пятой страницы.

word currMillis, prevMillis, intervalMs = 20;
byte countCycle, countTwoSec;
byte needBlink=1;//сколько раз мигнуть 
void setup() {
  digitalWrite(13, LOW);
  pinMode(13, OUTPUT);
}

void loop(){
  currMillis = (word)millis();
  if(currMillis - prevMillis >= intervalMs){//
    prevMillis += intervalMs;
    
    switch (countCycle){
      case 0:  //
        if(needBlink) digitalWrite(13, HIGH); 
        break;
      case 1:
        digitalWrite(13, LOW);     
      break;
      case 16: 
        if(needBlink >= 2) digitalWrite(13, HIGH); 
        break;
      case 17:  
        digitalWrite(13, LOW);     
        break;
      case 32:  
        if(needBlink >= 3) digitalWrite(13, HIGH); 
        break;  
      case 33: 
        digitalWrite(13, LOW);     
        break;
//      case 80: 
//      делаем что-то
//        break;        
    }    
    if(++countCycle >= 100){//прошло  2 сек
      countCycle = 0;
      if(++countTwoSec >= 5){//каждые 10 сек меняем число вспышек
      // от ноля до трех
         countTwoSec = 0;  
         needBlink++;
         needBlink = needBlink % 4;
      }
    }
  }
}//END loop()

 

andycat
andycat аватар
Offline
Зарегистрирован: 07.09.2017

Pyotr пишет:

Иногда нужно миганием светодиода отображать режим работы простого устройства.
Например: 1 блинк-температура ниже уставки, 2-в пределах нормы, 3-перегрев.

я тоже как то сделал такое примитивное устройство, температуру отправляет на MQTT брокер, и по количеству вспышек можно определить ошибку, отвалился интернет или брокер или еще что то, но вот незадача, я тупо забыл какая ошибка на сколько вспышек :(

так что так себе идея.....инструкцию с собой еще таскать

Green
Offline
Зарегистрирован: 01.10.2015

Хе-хе. В ус-ве RTC был на обычном 8-ми ногом МК. А время желательно было, хотя бы изредка, контролировать. Максимум что удалось - светодиод сигнализирующий кодом Морзе.) Инструкция не нужна - всё открытым текстом.)

SLKH
Offline
Зарегистрирован: 17.08.2015

Pyotr пишет:

Иногда нужно миганием светодиода отображать режим работы простого устройства.
Например: 1 блинк-температура ниже уставки, 2-в пределах нормы, 3-перегрев.

Выложу пример для новичков. Хотя сомневаюсь, что кто-то дочитает до пятой страницы.


ещё проще: в "блинк без делэя" в зависимости от температуры изменяется переменная interval. 

Pyotr
Offline
Зарегистрирован: 12.03.2014

Пример с температурой неудачный. Я так не делаю. А вот к примеру у меня драйвер управляет приводами фрамуг на высоте 4,5 метра. Управляется по RS485. Светик мигает-значит не завис. Дисплея нет-снизу не разглядеть.
Один раз - закрыто, три-открыто 100%, 2-промежуточное положение. Зимой может лед намерзнуть и мешать плотному прилеганию. Снизу это не видно, а по блинкам все ясно.

Понравилось - менять частоту мигания в зависимости от температуры. Как только быстро замигал- ложись, а то как долбанет)))

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

andycat пишет:

Pyotr пишет:

Иногда нужно миганием светодиода отображать режим работы простого устройства.
Например: 1 блинк-температура ниже уставки, 2-в пределах нормы, 3-перегрев.

я тоже как то сделал такое примитивное устройство, температуру отправляет на MQTT брокер, и по количеству вспышек можно определить ошибку, отвалился интернет или брокер или еще что то, но вот незадача, я тупо забыл какая ошибка на сколько вспышек :(

так что так себе идея.....инструкцию с собой еще таскать

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

Taxom
Offline
Зарегистрирован: 12.08.2020

Прошу в помощи, не могу понять как сделать отдельную функцию  для "мигания" которая может работать с несколькими светодиодами одновременно

как оптимизировать этот код убрав эти повторения?

//номера выводов и глобальные переменные
const uint8_t greenled = 2;
const uint8_t yellowled = 3;
const uint8_t redled = 4;
const uint8_t button = 8;

//настраиваем порты
void setup() {
  pinMode(greenled, OUTPUT);
  pinMode(yellowled, OUTPUT);
  pinMode(redled, OUTPUT);
  pinMode(button, INPUT_PULLUP); 
  Serial.begin(9600);
}

void GreenLedBlink(uint8_t period){ //функция мигания зеленым(принемаем с каким периодом)
  static uint32_t timer; // локальная переменная с сохранением между вызовами
  if((millis() - timer) >= period) {  //проверяем прошедшее время
  digitalWrite(greenled, !digitalRead (greenled)); //по прошествии инвертируем
  timer = millis();
  }
}

void RedLedBlink(uint8_t period){ //функция мигания красным(принемаем с каким периодом)
  static uint32_t timer; // локальная переменная с сохранением между вызовами
  if((millis() - timer) >= period) {  //проверяем прошедшее время
  digitalWrite(redled, !digitalRead (redled)); //по прошествии инвертируем
  timer = millis();
  }
}

void YellowLedBlink(uint8_t period){ //функция мигания красным(принемаем с каким периодом)
  static uint32_t timer; // локальная переменная с сохранением между вызовами
  if((millis() - timer) >= period) {  //проверяем прошедшее время
  digitalWrite(yellowled, !digitalRead (yellowled)); //по прошествии инвертируем
  timer = millis();
  }
}

void loop() {  
  //чтото делаем 
  if (!digitalRead (button)){ 
    RedLedBlink(1000); 
    GreenLedBlink(200);
    YellowLedBlink(300); 
        
  }
  else {
  digitalWrite (greenled, LOW);  
  digitalWrite (redled, LOW);
  digitalWrite (yellowled, LOW);

  }
Serial.println(millis());

/*
  if (что-то происходит){ 
    RedLedBlink(300); 
    GreenLedBlink(2000);
        
  }
  else {
  digitalWrite (greenled, LOW);  
  digitalWrite (redled, LOW);

  }
 */

  
  //продолжаем делать 
}

Эта функция прекрасно работает с отдельными светодиодами, но по понятным причинам не работает с несколькими одновременно

//номера выводов и глобальные переменные
const uint8_t greenled = 2;
const uint8_t yellowled = 3;
const uint8_t redled = 4;
const uint8_t button = 8;

//настраиваем порты
void setup() {
  pinMode(greenled, OUTPUT);
  pinMode(yellowled, OUTPUT);
  pinMode(redled, OUTPUT);
  pinMode(button, INPUT_PULLUP); 
  Serial.begin(9600);
}

void LedBlink(uint8_t portLed,uint8_t period){ //принимаем чем мигать и с каким периодом
  static uint32_t timer; // локальная переменная с сохранением между вызовами
  if((millis() - timer) >= period) {  //проверяем прошедшее время
  digitalWrite(portLed, !digitalRead (portLed)); //по прошествии инвертируем
  timer = millis();
  }
}

void loop() {  
  //чтото делаем 
  if (!digitalRead (button)){ 
    LedBlink(greenled, 500);
    LedBlink(redled, 300);
    LedBlink(yellowled, 1000);
         
  }
  else {
  digitalWrite (greenled, LOW);
  digitalWrite (redled, LOW);
  digitalWrite (yellowled, LOW);


  }

  
  //продолжаем делать 
}

 

sadman41
Offline
Зарегистрирован: 19.10.2016

Оптимизировать в каком ключе?

rkit
Offline
Зарегистрирован: 23.11.2016

  static uint32_t timer; // локальная переменная с сохранением между вызовами

Taxom
Offline
Зарегистрирован: 12.08.2020

Это я понимаю, но как это обойти не знаю.

 

Taxom
Offline
Зарегистрирован: 12.08.2020

Оптимизировать в плане использовать одну функцию, а не по функции для каждого LED.

это всего лишь часть кода, у меня нужно "мигать" 6 разными портами в разной последовательности (по очереди и вместе) с разными интервалами. соответственно нужно написать для каждого порта отдельно функцию, а хотелось бы одну универсальную. Которая принимает номер порта и период.

sadman41
Offline
Зарегистрирован: 19.10.2016

Вариант #1: завернуть функционал в class.

Taxom
Offline
Зарегистрирован: 12.08.2020

Можно ли немного по подробнее, я новичок. Где есть справка по class ?

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Собственно, варианта 2:

1. Хранить снаружи и передавать по ссылке в функцию третий параметр - timer.

2. Как уже было сказано, использовать класс.

Опять же, чудес не бывает: в тексте оно, может, и будет короче, а в коде - вряд ли: все равно на каждый светодиод необходим свой собственный набор параметров: номер порта, период мигания и время последнего переключения. 

Taxom
Offline
Зарегистрирован: 12.08.2020

"1. Хранить снаружи и передавать по ссылке в функцию третий параметр - timer."

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

где можно более-менее понятно для новичка почитать про классы на русском.

rkit
Offline
Зарегистрирован: 23.11.2016

Taxom пишет:

 чтобы не было при каждом вызове функции мигания 100500 строк кода, что убьет весь смысл отдельной функции.

Ты уже в этом форум написал в несколько раз больше. чем нужно для задачи.

Taxom
Offline
Зарегистрирован: 12.08.2020

rkit пишет:

Ты уже в этом форум написал в несколько раз больше. чем нужно для задачи.

ваш комментарий очень помог, спасибо!

rkit
Offline
Зарегистрирован: 23.11.2016

Пинки под зад по интернету не передаются, извиняй уж. А кроме этого тебе вряд ли что-то поможет.

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Taxom пишет:

 

где можно более-менее понятно для новичка почитать про классы на русском.

https://www.bsuir.by/m/12_100229_1_98220.pdf