7-сегментный многоэкранный дисплей, отображает только 1 цифру
Я пытаюсь создать отображение так, чтобы при нажатии кнопки счетчик увеличивался на единицу. Проблема в том, что загорается только один из них, и он не показывает правильный результат, он показывает комбинацию обеих цифр (например, 01 показывает 0, 02 показывает 8). Вот мой полный код.
const int a = 8; //Для отображения сегмента "а"
const int b = 9; //Для отображения сегмента "b"
const int c = 4; //Для отображения сегмента "c"
const int d = 5; //Для отображения сегмента "d"
const int e = 6; //Для отображения сегмента "e"
const int f = 2; //Для отображения сегмента "f"
const int g = 3; //Для отображения сегмента "g"
const int D1 = 7;
const int D2 = 13;
bool bPress = false;
const int IncbuttonPin = 10;
// Переменные изменятся:
int buttonPushCounter = 0; // счетчик количества нажатий кнопок
int buttonPushCounterD1 = 0;
int buttonPushCounterD2 = 0;
int IncbuttonState = 0;
int lastIncbuttonState = 0;
void setup() {
// поместите сюда свой код установки для однократного запуска:
pinMode(a, OUTPUT); //А
pinMode(b, OUTPUT); //Б
pinMode(c, OUTPUT); //С
pinMode(d, OUTPUT); //Д
pinMode(e, OUTPUT); //Э
pinMode(f, OUTPUT); //Ф
pinMode(g, OUTPUT); //Г
pinMode(D1, OUTPUT);
pinMode(D2, OUTPUT);
pinMode( IncbuttonPin , INPUT_PULLUP );
Serial.begin(9600);
}
void loop() {
IncbuttonState = digitalRead(IncbuttonPin);
checkIncButtonPress();
if( bPress ){
bPress = false;
turnOff();
lightDigit1(buttonPushCounterD1);
delay(5);
lightDigit2(buttonPushCounterD2);
delay(5);
}
}
void checkIncButtonPress()
{
// сравниваем IncbuttonState с его предыдущим состоянием
if (IncbuttonState != lastIncbuttonState) {
// если состояние изменилось, увеличиваем счетчик
if (IncbuttonState == LOW) {
// если текущее состояние ВЫСОКОЕ, то кнопка переключилась из выключенного состояния во включенное:
bPress = true;
buttonPushCounter++;
buttonPushCounterD1 = buttonPushCounter / 10;
buttonPushCounterD2 = buttonPushCounter % 10;
Serial.println("on");
Serial.println(buttonPushCounterD1);
Serial.println(buttonPushCounterD2);
} else {
// если текущее состояние НИЗКОЕ, то кнопка переключилась из включенного состояния в выключенное:
Serial.println("off");
}
// Небольшая задержка, чтобы избежать подпрыгивания
delay(50);
}
// сохраняем текущее состояние как последнее для следующего прохода цикла
lastIncbuttonState = IncbuttonState;
}
void lightDigit1(byte digit) {
digitalWrite(D1, LOW);
digitalWrite(D2, HIGH);
displayDigit1(digit);
}
void lightDigit2(byte digit) {
digitalWrite(D1, HIGH);
digitalWrite(D2, LOW);
displayDigit2(digit);
}
void displayDigit1(byte digit)
{
//Условия отображения сегмента a
if(digit!=1 && digit != 4)
digitalWrite(a,HIGH);
//Условия отображения сегмента b
if(digit != 5 && digit != 6)
digitalWrite(b,HIGH);
//Условия отображения сегмента c
if(digit !=2)
digitalWrite(c,HIGH);
//Условия отображения сегмента d
if(digit != 1 && digit !=4 && digit !=7)
digitalWrite(d,HIGH);
//Условия отображения сегмента e
if(digit == 2 || digit ==6 || digit == 8 || digit==0)
digitalWrite(e,HIGH);
//Условия отображения сегмента f
if(digit != 1 && digit !=2 && digit!=3 && digit !=7)
digitalWrite(f,HIGH);
if (digit!=0 && digit!=1 && digit !=7)
digitalWrite(g,HIGH);
}
void displayDigit2(byte digit)
{
// digitalWrite(D1, HIGH);
// digitalWrite(D2, LOW);
//Условия отображения сегмента a
if(digit!=1 && digit != 4)
digitalWrite(a,HIGH);
//Условия отображения сегмента b
if(digit != 5 && digit != 6)
digitalWrite(b,HIGH);
//Условия отображения сегмента c
if(digit !=2)
digitalWrite(c,HIGH);
//Условия отображения сегмента d
if(digit != 1 && digit !=4 && digit !=7)
digitalWrite(d,HIGH);
//Условия отображения сегмента e
if(digit == 2 || digit ==6 || digit == 8 || digit==0)
digitalWrite(e,HIGH);
//Условия отображения сегмента f
if(digit != 1 && digit !=2 && digit!=3 && digit !=7)
digitalWrite(f,HIGH);
if (digit!=0 && digit!=1 && digit !=7)
digitalWrite(g,HIGH);
}
void turnOff()
{
digitalWrite(a,LOW);
digitalWrite(b,LOW);
digitalWrite(c,LOW);
digitalWrite(d,LOW);
digitalWrite(e,LOW);
digitalWrite(f,LOW);
digitalWrite(g,LOW);
}
когда я удаляю код
lightDigit1(buttonPushCounterD1);
delay(5);
Он показывает правильный вывод, но только для 1 цифры. Кто-нибудь может мне помочь в этом? Спасибо.
@user50125, 👍1
1 ответ
Вы неправильно мультиплексируете дисплеи.
В данный момент вы делаете:
- Ничего не делайте, пока кнопка не будет нажата
- Включить дисплей 1
- Включить сегменты для цифры 1.
- Подождите 5 мс.
- Выключить дисплей 1
- Включить дисплей 2
- Включить сегменты для цифры 2.
- Подождите 5 мс.
- Перейти к 1
Приблизительно в течение 5 мс одна цифра будет кратковременно мигать, но поскольку вы не выключаете сегменты, включенные для этой цифры, они просто добавляются к второй цифре, которую вы отображаете в течение длительного периода времени.
Для правильного мультиплексирования необходимо:
- Отключить сегменты, которые больше не используются для текущего отображения (лучше всего отключить их все)
- Неоднократно отображать обе цифры все время.
В идеале ваш метод должен быть следующим:
- Отключить все сегменты
- Включить сегменты для цифры 1.
- Включить цифру 1.
- Задержка 5 мс
- Отключить цифру 1
- Отключить все сегменты
- Включить сегменты для цифры 2.
- Включить цифру 2
- Задержка 5 мс
- Отключить цифру 2
- Перейдите к 1 (обычно это делает
loop()
).
И отдельно от того, что вы обрабатываете нажатие кнопки и меняете отображаемое значение.
Также обратите внимание на отключение цифры перед расстановкой сегментов для следующей цифры. Это предотвращает двоение, когда вы получаете слабое впечатление от предыдущей цифры, наложенной на текущую.
- 74HC595 к 4 значному 7 сегменту с использованием библиотеки SevSegShift
- Запуск двух циклов одновременно на Arduino
- Как записать и прочитать из файла SPIFFS как данные объекта на ESP8266
- Почему у меня 7 сегмент не обновляется каждую секунду как в программе?
- 7-сегментный дисплей с потенциометром
- Как прочитать выходные данные с разъема SPI с помощью Arduino Uno?
- отображение 3-значного времени часов на 4-значном 7-сегментном дисплее
- 4-значный 7-сегментный дисплей неправильно отображает значение