Связь Arduino по Bluetooth замедляется из-за цикла for!
Я отправляю данные в Arduino через мобильное приложение. До сих пор весь код работал последовательно.
#include <SoftwareSerial.h>
#define FASTLED_INTERNAL
#include <FastLED.h>
#define NUM_LEDS_PER_STRIP 48
SoftwareSerial bluetooth(53,52); // TX, RX
int bar_analog=0;
int head_analog=0;
int bar_anim=0;
int anim=0;
int motor_speed=1;
int direct=0;
int level=0;
CRGB strip1[NUM_LEDS_PER_STRIP];
CRGB strip2[NUM_LEDS_PER_STRIP];
CRGB strip3[NUM_LEDS_PER_STRIP];
CRGB strip4[NUM_LEDS_PER_STRIP];
boolean debug = true;
int IN1a=49;
int IN2a=48;
int PWM1=3;
int IN1b=22;
int IN2b=23;
int PWM2=4;
int hiz=100;
int PWM_kare=2;
int INA_kare = 51;
int INB_kare = 50; //LED '+'sı OUTPUT B'de olduğu için INB'yi HIGH yapıyoruz.
void m1_cw() {
digitalWrite(IN1a,HIGH);
digitalWrite(IN2a,LOW);
analogWrite(PWM1,hiz);
}
void m1_ccw() {
digitalWrite(IN1a,LOW);
digitalWrite(IN2a,HIGH);
analogWrite(PWM1,hiz);
}
void m2_cw() {
digitalWrite(IN1b,HIGH);
digitalWrite(IN2b,LOW);
analogWrite(PWM2,hiz);
}
void m2_ccw() {
digitalWrite(IN1b,LOW);
digitalWrite(IN2b,HIGH);
analogWrite(PWM2,hiz);
}
void m1_stop() {
digitalWrite(IN1a,LOW);
digitalWrite(IN2a,LOW);
analogWrite(PWM1,0);
}
void m2_stop() {
digitalWrite(IN1b,LOW);
digitalWrite(IN2b,LOW);
analogWrite(PWM2,0);
}
void mast_up() {
digitalWrite(24,HIGH);
digitalWrite(25,LOW);
}
void mast_down() {
digitalWrite(24,LOW);
digitalWrite(25,HIGH);
}
void mast_stop() {
digitalWrite(24,LOW);
digitalWrite(25,LOW);
}
void kare() {
analogWrite(PWM_kare,head_analog);
digitalWrite(INB_kare, HIGH);
digitalWrite(INA_kare, LOW);
}
void strip_dim() {
for(int i=0;i<256;i=i+10) {
for(int j=0;j<NUM_LEDS_PER_STRIP;j++) {
FastLED.setBrightness(i); //Парлаклык
strip1[j] = CRGB( 100, 172, 45); //leds[0] относится к 1-му светодиоду на полосе. (Вот переменная светодиодов.)
strip2[j] = CRGB( 100, 172, 45);
strip3[j] = CRGB( 100, 172, 45);
strip4[j] = CRGB( 100, 172, 45);
FastLED.show();
}}
for(int i=255;i>=0;i=i-10) {
for(int j=0;j<NUM_LEDS_PER_STRIP;j++) {
FastLED.setBrightness(i); //Яркость
strip1[j] = CRGB( 100, 172, 45); //leds[0] относится к 1-му светодиоду на полосе. (Вот переменная светодиодов.)
strip2[j] = CRGB( 100, 172, 45);
strip3[j] = CRGB( 100, 172, 45);
strip4[j] = CRGB( 100, 172, 45);
FastLED.show();
}}
}
void strip_stop() {
for(int j=0;j<NUM_LEDS_PER_STRIP;j++) {
FastLED.setBrightness(0); //Яркость
strip1[j] = CRGB( 100, 172, 45); //leds[0] относится к 1-му светодиоду на полосе. (Вот переменная светодиодов.)
strip2[j] = CRGB( 100, 172, 45);
strip3[j] = CRGB( 100, 172, 45);
strip4[j] = CRGB( 100, 172, 45);
FastLED.show();
}
}
void setup() {
Serial.begin(9600);
bluetooth.begin(9600);
Serial.println("Program is starting...");
Serial.println("by Berke Ogulcan Parlak");
pinMode(IN1a,OUTPUT);
pinMode(IN2a,OUTPUT);
pinMode(IN1b,OUTPUT);
pinMode(IN2b,OUTPUT);
pinMode(PWM1,OUTPUT);
pinMode(PWM2,OUTPUT);
pinMode(24,OUTPUT);
pinMode(25,OUTPUT);
pinMode(INA_kare, OUTPUT);
pinMode(INB_kare, OUTPUT);
pinMode(PWM_kare, OUTPUT);
digitalWrite(IN1a,LOW);
digitalWrite(IN2a,LOW);
digitalWrite(IN1b,LOW);
digitalWrite(IN2b,LOW);
digitalWrite(PWM1,LOW);
digitalWrite(PWM2,LOW);
digitalWrite(24,LOW);
digitalWrite(25,LOW);
digitalWrite(INA_kare, LOW);
digitalWrite(INB_kare, LOW);
digitalWrite(PWM_kare, LOW);
FastLED.addLeds<NEOPIXEL, 26>(strip1, NUM_LEDS_PER_STRIP);
FastLED.addLeds<NEOPIXEL, 28>(strip2, NUM_LEDS_PER_STRIP);
FastLED.addLeds<NEOPIXEL, 30>(strip3, NUM_LEDS_PER_STRIP);
FastLED.addLeds<NEOPIXEL, 32>(strip4, NUM_LEDS_PER_STRIP);
FastLED.setBrightness(0);
}
void loop() {
while (bluetooth.available())
{
bar_analog = bluetooth.parseInt();
head_analog = bluetooth.parseInt();
bar_anim = bluetooth.parseInt();
anim = bluetooth.parseInt();
motor_speed = bluetooth.parseInt();
direct = bluetooth.parseInt();
level = bluetooth.parseInt();
if (debug) {
Serial.print("Bar Brightness: ");
Serial.println(bar_analog);
Serial.print("Bar Animation Type: ");
Serial.println(bar_anim);
Serial.print("Headlight Brightness: ");
Serial.println(head_analog);
Serial.print("Strip Animation Type: ");
Serial.println(anim);
Serial.print("Motor Speed Level: ");
Serial.println(motor_speed);
Serial.print("Direction: ");
Serial.println(direct);
Serial.print("Mast Goes: ");
Serial.println(level);
Serial.println("--------------------------------");
}
if (bluetooth.read() == '\n') {
}}
kare();
if(direct==1) { //илери
m1_ccw();
m2_ccw();
}
else if(direct==2) { //geri
m1_cw();
m2_cw();
}
else if(direct==3) { //соль
m1_ccw();
m2_cw();
}
else if(direct==4) { //sağ
m1_cw();
m2_ccw();
}
else if(direct==0) { // прочно
m1_stop();
m2_stop();
}
if(level==1) { //мачта юкары
mast_up();
}
else if(level==2) { //мачта aşağı
mast_down();
}
else if(level==0) { //долговечность мачты
mast_stop();
}
if(anim==2) {
strip_dim();
}
else if(anim==0) {
strip_stop();
}
}
Но когда я добавил в код цикл for, все данные начали меняться. (Когда я нажимаю кнопку из приложения, происходит «задержка» и данные смешиваются.) Я упомянул эту часть кода ниже. Почему данные смещаются?
void strip_dim() {
for(int i=0;i<256;i=i+10) {
for(int j=0;j<NUM_LEDS_PER_STRIP;j++) {
FastLED.setBrightness(i); //Парлаклык
strip1[j] = CRGB( 100, 172, 45); //leds[0] şeritteki 1.Ledi ifade eder. (Бурадаки ведет переменную дир.)
strip2[j] = CRGB( 100, 172, 45);
strip3[j] = CRGB( 100, 172, 45);
strip4[j] = CRGB( 100, 172, 45);
FastLED.show();
}}
for(int i=255;i>=0;i=i-10) {
for(int j=0;j<NUM_LEDS_PER_STRIP;j++) {
FastLED.setBrightness(i); //Яркость
strip1[j] = CRGB( 100, 172, 45); //leds[0] относится к 1-му светодиоду на полосе. (Вот переменная светодиодов.)
strip2[j] = CRGB( 100, 172, 45);
strip3[j] = CRGB( 100, 172, 45);
strip4[j] = CRGB( 100, 172, 45);
FastLED.show();
}}
}
void strip_stop() {
for(int j=0;j<NUM_LEDS_PER_STRIP;j++) {
FastLED.setBrightness(0); //Яркость
strip1[j] = CRGB( 100, 172, 45); //leds[0] относится к 1-му светодиоду на полосе. (Вот переменная светодиодов.)
strip2[j] = CRGB( 100, 172, 45);
strip3[j] = CRGB( 100, 172, 45);
strip4[j] = CRGB( 100, 172, 45);
FastLED.show();
}
}
@bopele, 👍1
Обсуждение2 ответа
Вы создаете экземпляр класса много раз (25 * 48 * 8 + 255 * 48 * 4 = 58 560 раз), и это дорогостоящая операция.
Вместо этого создайте один экземпляр (перед циклами for) и используйте его для назначения везде, где вам это нужно.
Что-то вроде;
CRGB crgb( 100, 172, 45);
for(int i=0;i<256;i=i+10) {
for(int j=0;j<NUM_LEDS_PER_STRIP;j++) {
FastLED.setBrightness(i);
strip1[j] = crgb;
...
Хорошая точка зрения. Однако, если setBrightness выполняет последовательную связь, > 58 000 итераций цикла по-прежнему будут занимать значительное количество времени., @Duncan C
@DuncanC Верно, но я не хотел менять функциональность., @Michel Keijzers
Спасибо за комментарий, но изменений нет., @bopele
Ваша главная проблема в том, что FastLED отключает прерывания при отправке данных. Это происходит потому, что синхронизация имеет решающее значение, а при включенных прерываниях синхронизация будет полностью нарушена.
Поэтому, когда FastLED постоянно работает в цикле, очень мало времени, когда разрешены прерывания для приема через SoftwareSerial.
В отличие от настоящего UART, который может получать и сохранять байты перед инициированием прерывания, SoftwareSerial инициирует прерывание в начале получения байта, и эта процедура прерывания используется для фактического приема. Таким образом, если прерывания не включены в тот момент, когда байт начинает поступать на вывод GPIO, он не может начать прием, поэтому он пропускает байт, и в итоге получается беспорядок.
Поскольку вы используете Arduino Mega, у вас нет абсолютно никаких причин использовать SoftwareSerial. У вас есть много реальных аппаратных UART, доступных для подключения вашего Bluetooth-устройства, к которому вы сможете получить байт, пока FastLED отправляет данные (пока он не отправляет данные слишком долго...).
Проголосовал за ваш комментарий, и ваш ответ вызвал у меня вопрос, связанный с вашим ответом. Я надеюсь, что вы можете взглянуть на него вкратце. https://arduinoprosto.ru/q/67381/does-dmxserial-stops-interrupts, @Michel Keijzers
Прежде всего, спасибо за ваш ответ, но я мало что знаю об UART. Какие изменения нужно внести в код, чтобы использовать UART вместо SoftwareSerial?, @bopele
- Получение шестнадцатеричных данных с терминала
- Bluetooth-модуль HC-05 не принимает AT-команды
- Я могу отправлять на software serial, но не прочитать?
- Arduino Serial.ReadString() проблема
- Проблемные данные I2C к датчику GY955/BNO055 (Китай)
- Последовательная связь между двумя Arduino не работает при отправке строки в программе с большим количеством функций.
- Серийный монитор, когда порт используется другим приложением
- Отправить пакет данных нескольких датчиков в модуль Bluetooth
Почему вы используете software serial на Меге?!?!, @Majenko