Застрял в цикле While

serial led switch loop led-matrix

Итак, я новичок в Arduino, и мне нужно зажечь светодиодную сетку, чтобы показать цифры от 0 до 9. Я написал немного кода (с помощью некоторых людей), и он выполнен на 90%, но есть одна проблема. Я использовал корпус переключателя, чтобы зажечь светодиоды (поэтому, если пользователь напишет 5, то корпус переключателя заставит светодиоды показывать цифру 5), но он отображается всего на долю секунды.Какие-нибудь исправления для этого?

#define ROW_1 3
#define ROW_2 4
#define ROW_3 5
#define ROW_4 6
#define ROW_5 7

#define COL_1 8
#define COL_2 9
#define COL_3 10
#define COL_4 11
#define COL_5 12
#define COL_6 13

const byte rows[] = {
    ROW_1, ROW_2, ROW_3, ROW_4, ROW_5
};

byte Zero[]  = {B011110, B010010, B010010, B010010, B011110};
byte One[]   = {B001100, B000100, B000100, B000100, B000100};
byte Two[]   = {B011110, B000010, B011110, B010000, B011110};
byte Three[] = {B011110, B000010, B001110, B000010, B011110};
byte Four[]  = {B010010, B010010, B011110, B000010, B000010};
byte Five[]  = {B011110, B010000, B011110, B000010, B011110};
byte Six[]   = {B011110, B010000, B011110, B010010, B011110};
byte Seven[] = {B011100, B000100, B000100, B000100, B000100};
byte Eight[] = {B011110, B010010, B011110, B010010, B011110};
byte Nine[]  = {B011110, B010010, B011110, B000010, B011110};

void setColumns(byte b) {
    digitalWrite(COL_1, (~b >> 0) & 0x01);
    digitalWrite(COL_2, (~b >> 1) & 0x01);
    digitalWrite(COL_3, (~b >> 2) & 0x01);
    digitalWrite(COL_4, (~b >> 3) & 0x01);
    digitalWrite(COL_5, (~b >> 4) & 0x01);
    digitalWrite(COL_6, (~b >> 5) & 0x01);
}

void  drawScreen(byte buffer2[]){
    for (byte i = 0; i < 5; i++) {
        setColumns(buffer2[i]);
        digitalWrite(rows[i], HIGH);
        digitalWrite(rows[i], LOW);
    }
}

void setup() {
    Serial.begin(9600);
    for (byte i = 2; i <= 13; i++)
        pinMode(i, OUTPUT);
}

void loop()
{
    int digit;
    if(Serial.available()) {
        digit = Serial.read();
        Serial.println(digit);
    }
    switch (digit) {
        case 48:
            drawScreen(Zero);
            break;
        case 49:
            drawScreen(One);
            break;
        case 50:
            drawScreen(Two);
            break;
        case 51:
            drawScreen(Three);
            break;
        case 52:
            drawScreen(Four);
            break;
        case 53:
            drawScreen(Five);
            break;
        case 54:
            drawScreen(Six);
            break;
        case 55:
            drawScreen(Seven);
            break;
        case 56:
            drawScreen(Eight);
            break;
        case 57:
            drawScreen(Nine);
            break;
    }
}

, 👍2

Обсуждение

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

48 - это код ASCII для текстового символа " 0`., @jsotola

Мы не можем увидеть ваш код в tinkercad. Он не является общедоступным. Пожалуйста, введите свой код непосредственно в свой вопрос. Тогда мы наверняка сможем дать вам хороший ответ, @chrisl

Спасибо за советы! Я немного отредактировал вопрос, потому что удалил циклы while., @BertjeDP2000


2 ответа


Лучший ответ:

1

Ваша функция drawScreen() выполняется очень быстро, и поэтому светодиоды загораются один раз, очень ненадолго. Есть несколько вариантов; вот пара, чтобы попробовать:

Один из них состоит в том, чтобы написать окружить существующий цикл for{} в drawScreen() другим, чтобы отобразить цифру достаточно раз, чтобы сделать ее видимой. Поэкспериментируйте с количеством внешних петель, начиная, может быть, с 50000 (угадайте здесь...), пока у вас не будет чего-то, что вам нравится.

Другой способ-использовать цикл while( Serial.available() == 0 ){} точно таким же образом, что приведет к сохранению отображаемой цифры до тех пор, пока вы не введете новую.

,

Это последнее звучит действительно хорошо, ооочень, как именно я должен это реализовать? Не могли бы вы написать для меня строки кода? Было бы потрясающе!, @BertjeDP2000

Добрый сэр, вы СПАСЛИ мне ЖИЗНЬ!, @BertjeDP2000


2

Если вы хотите, чтобы отображение сохранялось, вам следует вызывать drawScreen() на каждой итерации цикла. Вам понадобится переменная для “запоминания” того, какой глиф вы должны нарисовать. Затем код последовательной обработки должен обновлять эту переменную только при получении нового символа:

// Запомните, какой глиф мы должны нарисовать.
byte *glyph = Zero;

void loop() {
    if (Serial.available()) {
        char digit = Serial.read();
        Serial.println(digit);
        switch (digit) {
            case '0': glyph = Zero;  break;
            case '1': glyph = One;   break;
            case '2': glyph = Two;   break;
            case '3': glyph = Three; break;
            case '4': glyph = Four;  break;
            case '5': glyph = Five;  break;
            case '6': glyph = Six;   break;
            case '7': glyph = Seven; break;
            case '8': glyph = Eight; break;
            case '9': glyph = Nine;  break;
        }
    }
    drawScreen(glyph);
}

Переменная глифа является “указателем на byte”, потому что на что распадается массив байтов, когда он присваивается переменной.

,