Сорри, я не программист. Иду по граблям и примерам, котрые нахожу. Примеры блинк находил только для скважности 50%, а чтобы ещё с функцией от температуры, так и близко ничего подобного. Что-то похожее было в библиотеке OneTimer, но там с переменными таймер не хотел работать. Пробовал Ticker для ESP, но там также зависимость от температуры не смог прикрутить.
Сорри, я не программист. Иду по граблям и примерам, котрые нахожу. Примеры блинк находил только для скважности 50%, а чтобы ещё с функцией от температуры, так и близко ничего подобного. Что-то похожее было в библиотеке OneTimer, но там с переменными таймер не хотел работать. Пробовал Ticker для ESP, но там также зависимость от температуры не смог прикрутить.
ну я о том и говорю - дело ведь ни в том, что "блинк не умеет" или в "библиотеке OneTimer этого нельзя" - а в том, что вы "не смогли прикрутить".
Подскажите, где почитать по решению такой нетривиальной задачи? Монка и Соммера штудировал, Виктора Петина также читал. Может коллеги по форуму могут не только мокать носом и отправлять по всем известному адресу (учиться)? Может у кого-то хватит терпения и желания написать пару строк, описывающих принцип?
Подскажите, где почитать по решению такой нетривиальной задачи?
"нетривиальной" ? - издеваетесь?
Вот Вам стандартный блинк:
const int ledPin = 13;
// Variables will change:
int ledState = LOW; // этой переменной устанавливаем состояние светодиода
long previousMillis = 0;
long interval = 1000; // интервал между включение/выключением светодиода (1 секунда)
void setup() {
// задаем режим выхода для порта, подключенного к светодиоду
pinMode(ledPin, OUTPUT);
}
void loop()
{
// здесь будет код, который будет работать постоянно
// и который не должен останавливаться на время между переключениями свето
unsigned long currentMillis = millis();
//проверяем не прошел ли нужный интервал, если прошел то
if(currentMillis - previousMillis > interval) {
// сохраняем время последнего переключения
previousMillis = currentMillis;
// если светодиод не горит, то зажигаем, и наоборот
if (ledState == LOW)
ledState = HIGH;
else
ledState = LOW;
// устанавливаем состояния выхода, чтобы включить или выключить светодиод
digitalWrite(ledPin, ledState);
}
}
Теперь далее. Интервал переключения задан переменной interval - переменной! - запомните это слово
Смотрим на код . В строках 24-27 у нас условный оператор - при включенном светодиоде выполняется одна ветвь, при выключенном другая. И раз мы уже запомнили. что interval - это переменная, то нам ничего не помешает при каждом переключении диода менять значение интервала. чтобы при выключенно оно было одно, а при включенном - другое.
Вот и все. В стандартный пример достаточно добавить две (ВСЕГО!) строчки. "Нетривиальный" код попробуйте написать сами
Интервал - это период. Мне его менять не нужно. Мне нужно менять длительность импульса.
Посмотрите внимательно в код. Попробуйте подумать еще раз, ответ неверный.
Вот вы просите не посылать вас учиться, а дать какой-нибудь пример. А когда вам даешь - я бы даже сказал разжевываешь и кладешь в рот - до вас самое элементарное не доходит. Значит надо еще книжки читать.
Поправлюсь, в данном случае период будет 2*интревал. Мне нужно держать постоянным период, а управлять только скважностью. Для одной переменной будет скважность 50%, чтобы скважность менялась, нужно минимум две переменные, причём в сумме они должны давать период.
В данном случае период будет 2*интревал. Мне нужно держать постоянным период, а управлять только скважностью.
У нас интервал включения и интервал выключения - не равны. Поэтому период будет не 2*интревал, а (интервалON + интервалOFF). Изменяя соотвношение одного интервала к другому, но сохраняя их сумму неизменной - мы можем менять скважность, не меняя периода.
#include <OneWire.h>
#include<DallasTemperature.h>
OneWire oneWire(ONE_WIRE_BUS);
DallasTemperature DS18B20(&oneWire);
const int ledPin = 13;
#define ONE_WIRE_BUS 4 // DS18B20 подключаем на 4-й на плате
// Variables will change:
int ledState = LOW; // этой переменной устанавливаем состояние светодиода
long previousMillis = 0;
long interval = 6000; // начальная длительность импульса для периода 10 с
float temp_0;
void setup() {
DS18B20.begin();
pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду
}
void loop()
{
// здесь будет код, который будет работать постоянно
// и который не должен останавливаться на время между переключениями свето
DS18B20.requestTemperatures();
temp_0 = DS18B20.getTempCByIndex(0); // Sensor 0 показания для датчика 1 в цельсиях
unsigned long currentMillis = millis(); //проверяем не прошел ли нужный интервал, если прошел то
if(currentMillis - previousMillis < interval)
{
ledState = HIGH;
digitalWrite(ledPin, ledState);
}
if(currentMillis - previousMillis > interval && currentMillis - previousMillis < 10000)
{
ledState = LOW;
digitalWrite(ledPin, ledState);
}
previousMillis = currentMillis; // сохраняем время последнего переключения
interval = map (temp_0*10, 840, 930, 6000, 2500);
}
Но меня в первую очередь поражает вот что - нафига вы в код температуру засунули? Я вас просил написать блинк с разными интервалами - но вы, вместо того чтоб разобраться, как это делать - сразу полезли температуру добавлять. В результате - не справились ни с первым, ни со вторым. У вас и работа с интервалами неверная, и код температуры вы пишете на основе библиотеки Даллас, хотя сами же несколько раз писали. что эта библиотека с точными интервалами несовместима.
В общем, если хотите, чтобы я продолжил обьяснять вам эту тему - напишите мне блинк с периодом в 1 сек и скважностью 30%. Без ерунды с температурой - только чистый блинк.
Задача - элементарнейшая, добавить 2 строчки к базовому примеру. Если не справитесь - продолжать нет смысла. В этом случае будет правильнее заказть код стороннему программисту.
const int ledPin = 13;
// Variables will change:
int ledState = LOW; // этой переменной устанавливаем состояние светодиода
long previousMillis = 0;
long interval = 300; // интервал между включение/выключением светодиода (1 секунда)
void setup() {
pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду
}
void loop()
{
// здесь будет код, который будет работать постоянно
// и который не должен останавливаться на время между переключениями свето
unsigned long currentMillis = millis();
if(currentMillis - previousMillis > interval) { //проверяем не прошел ли нужный интервал, если прошел то
previousMillis = currentMillis; // сохраняем время последнего переключения
if (ledState == LOW) // если светодиод не горит, то зажигаем, и наоборот
ledState = HIGH;
else
ledState = LOW;
digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод
interval = 1000 - interval;
}
}
да, хорошо, даже лучше. чем я ожидал. Обошлись всего одной строкой, а не двумя. Надеюсь, не подглядывали?
Единственное "но" - у вас получился ШИМ со скважностью 70%, а не 30, потому что вы перепутали местами периоды. Думаю, Вы ошиблись потому, что считаете интервал снаружи условного оператора if (ledState...) и потому упустили, к какому периоду он относится.. Для наглядности лучше было бы поместить смену интервала в каждую ветку условного оператора - тогда вы могли бы четко устанавливать, какая задержка для включения, а какая для выключения.
Помещение вычисления скважности внутрь оператора if будет удобнее и для дальнейшего добавления расчета скважности от температуры - может попробуете переписать свой пример?
А где можно было такое подлядеть? Разве бы я надоедал здесь, если бы нашёл решение раньше?
const int ledPin = 13;
// Variables will change:
int ledState = LOW; // этой переменной устанавливаем состояние светодиода
unsigned long previousMillis = 0;
unsigned long interval = 300; // интервал между включение/выключением светодиода (1 секунда)
void setup() {
pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду
}
void loop()
{
// здесь будет код, который будет работать постоянно
// и который не должен останавливаться на время между переключениями свето
unsigned long currentMillis = millis();
if(currentMillis - previousMillis > 1000 - interval) { //проверяем не прошел ли нужный интервал, если прошел то
previousMillis = currentMillis; // сохраняем время последнего переключения
if (ledState == LOW) // если светодиод не горит, то зажигаем, и наоборот
ledState = HIGH;
interval = 1000 - interval;
else
ledState = LOW;
interval = 1000 - interval;
}
digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод
}
Всем добрый день.
Коллеги прошу помощи в решении задачи, суть ее такова нужно генерировать ШИМ на двух пинах с зависимой регулируемой скважностью и частотой, частота изменяется от от 20 до 200 Гц скважность как на картинке. суммарно заполнение обоих импульсов всегда 100%
благодаря предыдущему куску кода и пояснений и я свою задачу решил, но пока не полностью
const int ledPin = 11;
const int ledPin2 = 12;
int analogPin_dcy = A0;
int analogPin_frq = A1;
unsigned long val_1 = 0;
unsigned long val_2 = 0;
unsigned long value_1 = 0;
unsigned long value_2 = 0;
// Variables will change:
int ledState = LOW; // этой переменной устанавливаем состояние светодиода
int ledState2 = HIGH;
unsigned long previousMicros = 0;
unsigned long previousMicros_adc = 0;
unsigned long var_period = 0;
unsigned long duty_cycle = 0; // интервал между включение/выключением светодиода (1 секунда)
unsigned long period = 1000000;
void setup() {
pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду
pinMode(ledPin2, OUTPUT);
}
void loop()
{
// здесь будет код, который будет работать постоянно
// и который не должен останавливаться на время между переключениями свето
unsigned long currentMicros = micros();
if(currentMicros - previousMicros_adc > period / 100) { //проверяем не прошел ли нужный интервал, если прошел то
previousMicros_adc = currentMicros;
val_1 = analogRead(analogPin_dcy);
val_2 = analogRead(analogPin_frq);
val_2 = map(val_2, 0, 1023, 4, 50);
value_2 = val_2 * 1000;
val_1 = map(val_1, 0, 1023, 10, 90);
value_1 = val_1 * value_2 / 100;
period = value_2;
}
if(currentMicros - previousMicros > period - duty_cycle) { //проверяем не прошел ли нужный интервал, если прошел то
previousMicros = currentMicros; // сохраняем время последнего переключения
if (ledState == LOW) // если светодиод не горит, то зажигаем, и наоборот
{
ledState = HIGH;
ledState2 = LOW;
duty_cycle = value_1;
duty_cycle = period - duty_cycle;
}
else
{
ledState = LOW;
ledState2 = HIGH;
duty_cycle = period - duty_cycle;
}
}
digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод
digitalWrite(ledPin2, ledState2);
}
const int ledPin = 11;
const int ledPin2 = 12;
int st1 = 1;
int analogPin_dcy = A0;
int analogPin_frq = A1;
unsigned long val_1 = 0;
unsigned long val_2 = 0;
unsigned long value_1 = 0;
unsigned long value_2 = 0;
// Variables will change:
int ledState = LOW; // этой переменной устанавливаем состояние светодиода
int ledState2 = LOW;
unsigned long previousMicros = 0;
unsigned long previousMicros_adc = 0;
unsigned long var_period = 0;
unsigned long duty_cycle = 25000; // интервал между включение/выключением светодиода (1 секунда)
unsigned long period = 500000;
unsigned long dead_time = 100;
void setup() {
pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду
pinMode(ledPin2, OUTPUT);
}
void loop()
{
// здесь будет код, который будет работать постоянно
// и который не должен останавливаться на время между переключениями свето
unsigned long currentMicros = micros();
if(currentMicros - previousMicros_adc > period / 10) { //проверяем не прошел ли нужный интервал, если прошел то
previousMicros_adc = currentMicros; // сохраняем время последнего замера ацп
val_1 = analogRead(analogPin_dcy); // измеряем переменник регулирующий скважность
val_1 = map(val_1, 0, 1023, 10, 90); // масштабируем переменную скважности от 10 до 90%
val_2 = analogRead(analogPin_frq); // измеряем переменник регулирующий частоту
val_2 = map(val_2, 0, 1023, 4, 50); // масштабируем переменную частоты от 4 до 50 мс
period = val_2 * 1000; // присваеваем переменной периода переменную частоты домноженную
value_1 = val_1 * period / 100 - dead_time; // присваеваем переменной
value_2 = period - value_1 - dead_time;
}
if(currentMicros - previousMicros > duty_cycle) { //проверяем не прошел ли нужный интервал, если прошел то
previousMicros = currentMicros; // сохраняем время последнего переключения
switch (st1) {
case 1: //выполняется, когда st1 равно 1
ledState = HIGH;
ledState2 = LOW;
duty_cycle = value_1;
st1 = 2;
break;
case 2: //выполняется когда st1 равно 2
ledState = LOW;
ledState2 = LOW;
duty_cycle = dead_time;
st1 = 3;
break;
case 3: //выполняется когда st1 равно 3
ledState = LOW;
ledState2 = HIGH;
duty_cycle = value_2;
st1 = 4;
break;
case 4: //выполняется когда st1 равно 4
ledState = LOW;
ledState2 = LOW;
duty_cycle = dead_time;
st1 = 1;
break;
}
}
digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод
digitalWrite(ledPin2, ledState2);
}
Напрямую с OneWire работайте, например, а не через DallasTemperature.
без delay? т.к. ds18b20 не дружит с delay. хоть примерно подскажите как
можно с delay. можно и без. Смотрите пример "блинк без delay"
а что это у вас "ds18b20 не дружит с delay" - у всех дружит, у вас нет? :) Как это "не дружит" -не понимаю этой фразы... датчику пофиг
на сколько я помню, блинк никак не может управлять скважностью
Напрямую с OneWire работайте, например, а не через DallasTemperature.
У меня два датчика температуры и дисплей по SPI, плюс несколько релюшек и бузер. Ног в притык хватает.
Может, если своевременно менять...
на сколько я помню, блинк никак не может управлять скважностью
неправильно помните
если написать блинк включенный на 2сек, а выключенный на 8с - будет скважность 20%. А если включен и выключен по 5с - скважность 50%
У меня два датчика температуры и дисплей по SPI, плюс несколько релюшек и бузер. Ног в притык хватает.
сорри, "ИванВасильевич, когда вы говорите - такое впечатление, что вы бредите" (с)
какая связь с количеством ног?
У меня такое впечатление, что вы в своем проекте просто ни в зуб ногой. Может сначала учебники почитать7
Сорри, я не программист. Иду по граблям и примерам, котрые нахожу. Примеры блинк находил только для скважности 50%, а чтобы ещё с функцией от температуры, так и близко ничего подобного. Что-то похожее было в библиотеке OneTimer, но там с переменными таймер не хотел работать. Пробовал Ticker для ESP, но там также зависимость от температуры не смог прикрутить.
Сорри, я не программист. Иду по граблям и примерам, котрые нахожу. Примеры блинк находил только для скважности 50%, а чтобы ещё с функцией от температуры, так и близко ничего подобного. Что-то похожее было в библиотеке OneTimer, но там с переменными таймер не хотел работать. Пробовал Ticker для ESP, но там также зависимость от температуры не смог прикрутить.
ну я о том и говорю - дело ведь ни в том, что "блинк не умеет" или в "библиотеке OneTimer этого нельзя" - а в том, что вы "не смогли прикрутить".
И поэтому самый правильный путь - учиться
для начала возьмите пример "блинк без delay" и попробуйте его изменить, чтобы светодиод был включен на одно время, а выключен на другое.
Будут вопросы по коду - приходите. Только вопросы конкретные, а не просто "у меня не получилось"
Подскажите, где почитать по решению такой нетривиальной задачи? Монка и Соммера штудировал, Виктора Петина также читал. Может коллеги по форуму могут не только мокать носом и отправлять по всем известному адресу (учиться)? Может у кого-то хватит терпения и желания написать пару строк, описывающих принцип?
Хорошо, Вы сумеете на четном проходе blink-а печатать в Serial букву A?
Подскажите, где почитать по решению такой нетривиальной задачи?
"нетривиальной" ? - издеваетесь?
Вот Вам стандартный блинк:
const int ledPin = 13; // Variables will change: int ledState = LOW; // этой переменной устанавливаем состояние светодиода long previousMillis = 0; long interval = 1000; // интервал между включение/выключением светодиода (1 секунда) void setup() { // задаем режим выхода для порта, подключенного к светодиоду pinMode(ledPin, OUTPUT); } void loop() { // здесь будет код, который будет работать постоянно // и который не должен останавливаться на время между переключениями свето unsigned long currentMillis = millis(); //проверяем не прошел ли нужный интервал, если прошел то if(currentMillis - previousMillis > interval) { // сохраняем время последнего переключения previousMillis = currentMillis; // если светодиод не горит, то зажигаем, и наоборот if (ledState == LOW) ledState = HIGH; else ledState = LOW; // устанавливаем состояния выхода, чтобы включить или выключить светодиод digitalWrite(ledPin, ledState); } }Теперь далее. Интервал переключения задан переменной interval - переменной! - запомните это слово
Смотрим на код . В строках 24-27 у нас условный оператор - при включенном светодиоде выполняется одна ветвь, при выключенном другая. И раз мы уже запомнили. что interval - это переменная, то нам ничего не помешает при каждом переключении диода менять значение интервала. чтобы при выключенно оно было одно, а при включенном - другое.
Вот и все. В стандартный пример достаточно добавить две (ВСЕГО!) строчки. "Нетривиальный" код попробуйте написать сами
В данном случае период будет 2*интревал. Мне нужно держать постоянным период, а управлять только скважностью.
Интервал - это период. Мне его менять не нужно. Мне нужно менять длительность импульса.
Посмотрите внимательно в код. Попробуйте подумать еще раз, ответ неверный.
Вот вы просите не посылать вас учиться, а дать какой-нибудь пример. А когда вам даешь - я бы даже сказал разжевываешь и кладешь в рот - до вас самое элементарное не доходит. Значит надо еще книжки читать.
Либо бросать это дело - не дано оно вам.
Поправлюсь, в данном случае период будет 2*интревал. Мне нужно держать постоянным период, а управлять только скважностью. Для одной переменной будет скважность 50%, чтобы скважность менялась, нужно минимум две переменные, причём в сумме они должны давать период.
В данном случае период будет 2*интревал. Мне нужно держать постоянным период, а управлять только скважностью.
У нас интервал включения и интервал выключения - не равны. Поэтому период будет не 2*интревал, а (интервалON + интервалOFF). Изменяя соотвношение одного интервала к другому, но сохраняя их сумму неизменной - мы можем менять скважность, не меняя периода.
Я об этом и говорил - две переменные (интервалON и интервал OFF).
#include <OneWire.h> #include<DallasTemperature.h> OneWire oneWire(ONE_WIRE_BUS); DallasTemperature DS18B20(&oneWire); const int ledPin = 13; #define ONE_WIRE_BUS 4 // DS18B20 подключаем на 4-й на плате // Variables will change: int ledState = LOW; // этой переменной устанавливаем состояние светодиода long previousMillis = 0; long interval = 6000; // начальная длительность импульса для периода 10 с float temp_0; void setup() { DS18B20.begin(); pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду } void loop() { // здесь будет код, который будет работать постоянно // и который не должен останавливаться на время между переключениями свето DS18B20.requestTemperatures(); temp_0 = DS18B20.getTempCByIndex(0); // Sensor 0 показания для датчика 1 в цельсиях unsigned long currentMillis = millis(); //проверяем не прошел ли нужный интервал, если прошел то if(currentMillis - previousMillis < interval) { ledState = HIGH; digitalWrite(ledPin, ledState); } if(currentMillis - previousMillis > interval && currentMillis - previousMillis < 10000) { ledState = LOW; digitalWrite(ledPin, ledState); } previousMillis = currentMillis; // сохраняем время последнего переключения interval = map (temp_0*10, 840, 930, 6000, 2500); }Почти уверен, что не правильно, но тем не менее.
Почти уверен, что не правильно, но тем не менее.
угадали, неправильно.
Но меня в первую очередь поражает вот что - нафига вы в код температуру засунули? Я вас просил написать блинк с разными интервалами - но вы, вместо того чтоб разобраться, как это делать - сразу полезли температуру добавлять. В результате - не справились ни с первым, ни со вторым. У вас и работа с интервалами неверная, и код температуры вы пишете на основе библиотеки Даллас, хотя сами же несколько раз писали. что эта библиотека с точными интервалами несовместима.
В общем, если хотите, чтобы я продолжил обьяснять вам эту тему - напишите мне блинк с периодом в 1 сек и скважностью 30%. Без ерунды с температурой - только чистый блинк.
Задача - элементарнейшая, добавить 2 строчки к базовому примеру. Если не справитесь - продолжать нет смысла. В этом случае будет правильнее заказть код стороннему программисту.
const int ledPin = 13; // Variables will change: int ledState = LOW; // этой переменной устанавливаем состояние светодиода long previousMillis = 0; long interval = 300; // интервал между включение/выключением светодиода (1 секунда) void setup() { pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду } void loop() { // здесь будет код, который будет работать постоянно // и который не должен останавливаться на время между переключениями свето unsigned long currentMillis = millis(); if(currentMillis - previousMillis > interval) { //проверяем не прошел ли нужный интервал, если прошел то previousMillis = currentMillis; // сохраняем время последнего переключения if (ledState == LOW) // если светодиод не горит, то зажигаем, и наоборот ledState = HIGH; else ledState = LOW; digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод interval = 1000 - interval; } }так правильно?
Упрощаем. Безо всяких ledState).
digitalWrite(ledPin, !digitalRead(ledPin));да, хорошо, даже лучше. чем я ожидал. Обошлись всего одной строкой, а не двумя. Надеюсь, не подглядывали?
Единственное "но" - у вас получился ШИМ со скважностью 70%, а не 30, потому что вы перепутали местами периоды. Думаю, Вы ошиблись потому, что считаете интервал снаружи условного оператора if (ledState...) и потому упустили, к какому периоду он относится.. Для наглядности лучше было бы поместить смену интервала в каждую ветку условного оператора - тогда вы могли бы четко устанавливать, какая задержка для включения, а какая для выключения.
Помещение вычисления скважности внутрь оператора if будет удобнее и для дальнейшего добавления расчета скважности от температуры - может попробуете переписать свой пример?
Упрощаем. Безо всяких ledState).
digitalWrite(ledPin, !digitalRead(ledPin));Грин, в данном случае это вредное упрощение. Нам нужны две ветки - одна для ( ledState == HIGH), другая LOW
unsigned long previousMillis, unsigned long interval.
А где можно было такое подлядеть? Разве бы я надоедал здесь, если бы нашёл решение раньше?
const int ledPin = 13; // Variables will change: int ledState = LOW; // этой переменной устанавливаем состояние светодиода unsigned long previousMillis = 0; unsigned long interval = 300; // интервал между включение/выключением светодиода (1 секунда) void setup() { pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду } void loop() { // здесь будет код, который будет работать постоянно // и который не должен останавливаться на время между переключениями свето unsigned long currentMillis = millis(); if(currentMillis - previousMillis > 1000 - interval) { //проверяем не прошел ли нужный интервал, если прошел то previousMillis = currentMillis; // сохраняем время последнего переключения if (ledState == LOW) // если светодиод не горит, то зажигаем, и наоборот ledState = HIGH; interval = 1000 - interval; else ledState = LOW; interval = 1000 - interval; } digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод }Грин, в данном случае это вредное упрощение. Нам нужны две ветки - одна для ( ledState == HIGH), другая LOW
Там смайлик. Но и без ledState делается 2 ветки, если на то пошло.)
А где можно было такое подлядеть? Разве бы я надоедал здесь, если бы нашёл решение раньше?
Вы смеетесь? Думаете вы первый решаете эту простенькую задачку?
Вот, нашел менее чем за минуту:
https://forum.arduino.cc/index.php?topic=463958.0
и таких ссылок, если посикать - думаю не один десяток
К сожалению, я не владею английским на уровне, необходимом для поиска на зарубежных форумах. А на русскоязычных таких примеров не встречал.
Кстати Arduino IDE ругнулась на отсутствие фигурных скобок после условий, т.к. далее исполняется больше одной команды.
В остальном всё правильно?
Кстати Arduino IDE ругнулась на отсутствие фигурных скобок после условий, т.к. далее исполняется больше одной команды.
В остальном всё правильно?
фигурные скобки нужны, иначе будет работать неправильно.
Строчку 34 запишите в явном виде
interval = 300;
это то, что я имел в виду. чтобы снова не перепутать HIGH и LOW
В остальном правильно.
Теперь заменив строку 34 на вычисление интервала как функции от температуры - вы решите свою задачу. Строку в ветке LOW, при этом, трогать не надо.
и да, для периода лучше ввести переменную или дефайн, а не кодировать ее явно в тексе программы
Кстати Arduino IDE ругнулась на отсутствие фигурных скобок после условий, т.к. далее исполняется больше одной команды.
В остальном всё правильно?
фигурные скобки нужны, иначе будет работать неправильно.
Лично я, ставлю фигурные при любом количестве команд, и ТС советую.
Всем добрый день.
Коллеги прошу помощи в решении задачи, суть ее такова нужно генерировать ШИМ на двух пинах с зависимой регулируемой скважностью и частотой, частота изменяется от от 20 до 200 Гц скважность как на картинке. суммарно заполнение обоих импульсов всегда 100%
благодаря предыдущему куску кода и пояснений и я свою задачу решил, но пока не полностью
const int ledPin = 11; const int ledPin2 = 12; int analogPin_dcy = A0; int analogPin_frq = A1; unsigned long val_1 = 0; unsigned long val_2 = 0; unsigned long value_1 = 0; unsigned long value_2 = 0; // Variables will change: int ledState = LOW; // этой переменной устанавливаем состояние светодиода int ledState2 = HIGH; unsigned long previousMicros = 0; unsigned long previousMicros_adc = 0; unsigned long var_period = 0; unsigned long duty_cycle = 0; // интервал между включение/выключением светодиода (1 секунда) unsigned long period = 1000000; void setup() { pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду pinMode(ledPin2, OUTPUT); } void loop() { // здесь будет код, который будет работать постоянно // и который не должен останавливаться на время между переключениями свето unsigned long currentMicros = micros(); if(currentMicros - previousMicros_adc > period / 100) { //проверяем не прошел ли нужный интервал, если прошел то previousMicros_adc = currentMicros; val_1 = analogRead(analogPin_dcy); val_2 = analogRead(analogPin_frq); val_2 = map(val_2, 0, 1023, 4, 50); value_2 = val_2 * 1000; val_1 = map(val_1, 0, 1023, 10, 90); value_1 = val_1 * value_2 / 100; period = value_2; } if(currentMicros - previousMicros > period - duty_cycle) { //проверяем не прошел ли нужный интервал, если прошел то previousMicros = currentMicros; // сохраняем время последнего переключения if (ledState == LOW) // если светодиод не горит, то зажигаем, и наоборот { ledState = HIGH; ledState2 = LOW; duty_cycle = value_1; duty_cycle = period - duty_cycle; } else { ledState = LOW; ledState2 = HIGH; duty_cycle = period - duty_cycle; } } digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод digitalWrite(ledPin2, ledState2); }Вот версия с dead time
const int ledPin = 11; const int ledPin2 = 12; int st1 = 1; int analogPin_dcy = A0; int analogPin_frq = A1; unsigned long val_1 = 0; unsigned long val_2 = 0; unsigned long value_1 = 0; unsigned long value_2 = 0; // Variables will change: int ledState = LOW; // этой переменной устанавливаем состояние светодиода int ledState2 = LOW; unsigned long previousMicros = 0; unsigned long previousMicros_adc = 0; unsigned long var_period = 0; unsigned long duty_cycle = 25000; // интервал между включение/выключением светодиода (1 секунда) unsigned long period = 500000; unsigned long dead_time = 100; void setup() { pinMode(ledPin, OUTPUT); // задаем режим выхода для порта, подключенного к светодиоду pinMode(ledPin2, OUTPUT); } void loop() { // здесь будет код, который будет работать постоянно // и который не должен останавливаться на время между переключениями свето unsigned long currentMicros = micros(); if(currentMicros - previousMicros_adc > period / 10) { //проверяем не прошел ли нужный интервал, если прошел то previousMicros_adc = currentMicros; // сохраняем время последнего замера ацп val_1 = analogRead(analogPin_dcy); // измеряем переменник регулирующий скважность val_1 = map(val_1, 0, 1023, 10, 90); // масштабируем переменную скважности от 10 до 90% val_2 = analogRead(analogPin_frq); // измеряем переменник регулирующий частоту val_2 = map(val_2, 0, 1023, 4, 50); // масштабируем переменную частоты от 4 до 50 мс period = val_2 * 1000; // присваеваем переменной периода переменную частоты домноженную value_1 = val_1 * period / 100 - dead_time; // присваеваем переменной value_2 = period - value_1 - dead_time; } if(currentMicros - previousMicros > duty_cycle) { //проверяем не прошел ли нужный интервал, если прошел то previousMicros = currentMicros; // сохраняем время последнего переключения switch (st1) { case 1: //выполняется, когда st1 равно 1 ledState = HIGH; ledState2 = LOW; duty_cycle = value_1; st1 = 2; break; case 2: //выполняется когда st1 равно 2 ledState = LOW; ledState2 = LOW; duty_cycle = dead_time; st1 = 3; break; case 3: //выполняется когда st1 равно 3 ledState = LOW; ledState2 = HIGH; duty_cycle = value_2; st1 = 4; break; case 4: //выполняется когда st1 равно 4 ledState = LOW; ledState2 = LOW; duty_cycle = dead_time; st1 = 1; break; } } digitalWrite(ledPin, ledState); // устанавливаем состояния выхода, чтобы включить или выключить светодиод digitalWrite(ledPin2, ledState2); }