Шаговый не крутится, если в void loop появляются еще строки

vit177
Offline
Зарегистрирован: 08.04.2017

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

#include "DHT.h"
#include <AccelStepper.h>
#include <OLED_I2C.h>
AccelStepper Stepper1(1,3,4); //использует пин 3 и 4 для dir и step, 1 - режим "external driver" 
OLED  myOLED(8, 9, 8); // SDA - 8pin, SCL - 9pin
extern uint8_t RusFont[]; // Русский шрифт
extern uint8_t SmallFont[];
int TempOpen = 29;
int TempClose = 27;
int Rele1 = 7;
int dir = 1; //используется для смены направления
#define DHTPIN 2     // what digital pin we're connected to
#define DHTTYPE DHT22   // DHT 22  (AM2302), AM2321
DHT dht(DHTPIN, DHTTYPE);

void setup() {
  pinMode(Rele1, OUTPUT);
  dht.begin();
  myOLED.begin();
  digitalWrite(Rele1, LOW);
  Stepper1.setMaxSpeed(700); //устанавливаем максимальную скорость вращения ротора двигателя (шагов/секунду)
  Stepper1.setAcceleration(500); //устанавливаем ускорение (шагов/секунду^2)
}

void loop() {
  // Wait a few seconds between measurements.
  delay(2000);
  float h = dht.readHumidity();
  float t = dht.readTemperature();


  // Check if any reads failed and exit early (to try again).
  if (isnan(h) || isnan(t)) {
myOLED.clrScr(); // Стираем все с экрана
myOLED.setFont(RusFont);
myOLED.print("Не удается считать показания", LEFT, 0);
 
    return;
  }
myOLED.clrScr(); // Стираем все с экрана
myOLED.setFont(RusFont);
// Выводим показания влажности и температуры
myOLED.print("Ntvg= ", 0, 6); // Выводим  текст
myOLED.printNumI(t,33,6); // Выводим на экран значение температуры
myOLED.setFont(SmallFont);
myOLED.print("~C", 45, 6);
myOLED.setFont(RusFont);
myOLED.print("Jnrh=", 65, 0); // Выводим  текст
myOLED.printNumI(TempOpen, 97, 0); // Выводим  текст
myOLED.print("Pfrh=", 65, 13); // Выводим  текст
myOLED.printNumI(TempClose, 97, 13); // Выводим  текст
myOLED.print("Dkf;=", 0, 26); // Выводим текст
myOLED.printNumI(h,33,26); // Выводим значение влажности
myOLED.setFont(SmallFont);
myOLED.print("%", 45, 26);
myOLED.update();// Обновляем информацию на дисплее
delay(3000); // Пауза 3 секунды

if(t >= TempOpen){digitalWrite(Rele1, LOW);}
if(t <= TempClose){digitalWrite(Rele1, HIGH);}

if(Stepper1.distanceToGo()==0){ //проверка, отработал ли двигатель предыдущее движение

Stepper1.move(15000*dir); //устанавливает перемещение(если dir равен -1 будет перемещаться в противоположное направление)

dir = dir*(-1); //отрицательное значение dir, благодаря чему реализуется вращение в противоположном направлении

delay(1000); //задержка на 1 секунду
}
Stepper1.run(); //запуск шагового двигателя. Эта строка повторяется вновь и вновь для непрерывного вращения двигателя
}

 НО если закомментить в void loop строки не относящиеся к шаговому, т.е. оставить только: 

if(Stepper1.distanceToGo()==0){ //проверка, отработал ли двигатель предыдущее движение

Stepper1.move(15000*dir); //устанавливает перемещение(если dir равен -1 будет перемещаться в противоположное направление)

dir = dir*(-1); //отрицательное значение dir, благодаря чему реализуется вращение в противоположном направлении

delay(1000); //задержка на 1 секунду
}
Stepper1.run(); //запуск шагового двигателя. Эта строка повторяется вновь и вновь для непрерывного вращения двигателя

то шаговый крутится как надо. Даже если расскомментить чтение температуры   float t = dht.readTemperature();, то   шаговый начинает странно крутится, с паузами. Если у кого есть мысли, подскажите плз, направьте. Сам только начал изучать ардуино

okta
Offline
Зарегистрирован: 10.01.2015

Не работал с библиотекой AccelStepper, но, очевидно, надо как минимум избавляться от всех delay...

vit177
Offline
Зарегистрирован: 08.04.2017

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

vit177
Offline
Зарегистрирован: 08.04.2017

Всем доброго дня. При чтении float t = dht.readTemperature(); шаговый не крутится как надо, может есть у кого мысли как их разнести? Я начал использовать millis, т.е. разнес по времени чтение даных с датчиков, вывод данных на экран и сам шаговый. Все стало норм, шаговый крутится как надо. Но, мне нужно создать условие для старта шаговика в зависимости от темп и если я в этом условии использую переменную t считанную ранее в отдельной ф-ии millis, то такой код даже не компилится, ругается на переменную t. Т.е. мне ее снова нужно читать в ф-ии millis используемого для шаговика, а это снова приводит к странной работе шаговика.В программировании не силен, может есть идеи как применять переменную tсчитанную в одном из millis в разных функциях millis (наверное правильнее это называется так: как сделать t глобальной переменной)

OlegK
OlegK аватар
Offline
Зарегистрирован: 26.11.2014

vit177 пишет:
как сделать t глобальной переменной

Объявить её вверху, до setup(), где уже есть объявленные переменные float t;.
А в коде уже используете t = dht.readTemperature();
Ну и тут , наверное, почитать будет полезно.

vit177
Offline
Зарегистрирован: 08.04.2017

Ну при использовании t = dht.readTemperature(); это же опять обращение к датчику и чтение его данных, поэтому двигатель опять будет заикаться на этом моменте. 

OlegK
OlegK аватар
Offline
Зарегистрирован: 26.11.2014

Вы ж спросили - "как сделать t глобальной" ))
Выше же Вам посоветовали - избавляйтесь от дилэев, их в коде аж на 6 секунд, убирать нужно ВСЕ.
Делайте всё через millis() - с одной периодичностью читайте датчик, с другой управляйте моторами, с третьей обновляйте экран.

OlegK
OlegK аватар
Offline
Зарегистрирован: 26.11.2014

Примерно так -

void loop() {
    static uint32_t prevDmillis = millis();
    static uint32_t prevTmillis = millis();
    static uint32_t prevDispMillis = millis();

        if (millis() - prevDmillis > 200) {
            prevDmillis = millis();
           //Тут раз в 0,2 сек. рулим движками
        }

        if (millis() - prevTmillis > 3000) {
            prevTmillis = millis();
           //Тут раз в 3 сек. читаем температуру
        }

        if (millis() - prevDispMillis > 500) {
           prevDispMillis = millis();
           //Тут раз в 0.5 сек. обновляем дисплей
        }
}

 

vit177
Offline
Зарегистрирован: 08.04.2017

Я так и сделал, но в той периодичности, что управляем двигателями, мне снова приходится читать значение t, т.к. оно почему-то не подтягивается из той периодичности, где уже прочитали датчик (даже не компилится, пока в периодичности с двигателями снова не прочитаю датчик). 

OlegK
OlegK аватар
Offline
Зарегистрирован: 26.11.2014

Вот нифига не понятно. Покажите код, как сделали, что ли...

vit177
Offline
Зарегистрирован: 08.04.2017

OlegK, большое спасибо за ваши комментарии. У меня сейчас нет под рукой своего кода, давайте на вашем покажу:

void loop() {

    static uint32_t prevDmillis = millis();
    static uint32_t prevTmillis = millis();
    static uint32_t prevDispMillis = millis();

        if (millis() - prevDmillis > 200) {
            prevDmillis = millis();
           //Тут раз в 0,2 сек. рулим движками
	if (t>25) {          // если значение переменной больше t, то крутим двигатель
	Stepper1.move(4000); //крутим двигатель
	}
        }

        if (millis() - prevTmillis > 3000) {
            prevTmillis = millis();
           //Тут раз в 3 сек. читаем температуру
	   float t = dht.readTemperature(); // читаем значение температуры и присваиваем его переменной t
        }

        if (millis() - prevDispMillis > 500) {
           prevDispMillis = millis();
           //Тут раз в 0.5 сек. обновляем дисплей
        }
}

и вот на условие на переменную t в условии if (t>25) ругается при компиляции. Т.к. как я понял, значение этой переменной актуально для данного millis:  if (millis() - prevTmillis > 3000) и ее можно использовать только в этой периодичности millis

Как только установить в millis периодичности 200 новое чтение температуры float t = dht.readTemperature();, то компиляция пройдет, но шаговик заикается на время чтения датчика. 

OlegK
OlegK аватар
Offline
Зарегистрирован: 26.11.2014

Ну и правильно ругается... Вы всё же по ссылке почитайте, что я привёл ))
Выше Вы спросили про "как сделать глобальную t".
Так и сделайте её глобальную, как я писал в сообщении 4.
Вверху, где у Вас переменные TempOpen и прочие описаны - они же глобальные, т.е. имеют область видимости везде, в коде.
Там и объявите  свою t, а в лупе просто в неё читайте температуру.
И ещё учтите, что двигатель начнёт реагировать на температуру лишь спустя 3 секунды, когда обновится значение температуры.
Можете первый раз её в setup() прочитать, если это критично.

OlegK
OlegK аватар
Offline
Зарегистрирован: 26.11.2014

vit177 пишет:
шаговик заикается на время чтения датчика.

Заикается, потому, что в библиотеке DHT тоже дилэи понапиханы...
Тут придётся избавляться от этой библиотеки и считывать температуру с реализацией задержек на millis.

vit177
Offline
Зарегистрирован: 08.04.2017

Понял свою ошибку, я просто почему то думал, что при объявлении глобальной переменной я ей там и значение сразу должен присвоить, т.е. там же и прочитать датчик и у меня в голове не укладывается как же оно будет меняться. А нужно просто объявить t например с нулевым значением, она станет доступна всему коду, а при старте, через 3 сек этой переменной присвоится значение датчика. Сегодня опробуют, спасибо огромное за разъяснения.