Доброго всем дня! Запустил часы! Взял за основу тему на форуме “7- cегментный дисплей для arduino”.Сначала повозился с выводом информации на индикаторы. Привожу тестовый скетч, может кому будет интересно. Случайчый вывод числа в диапазоне от 0 до 9999. Исключил “делеи” как и советовали - задействовав прерывание. Прямоугольный сигнал с частотой 1 Гц на выходе SQW модуля DS3231 организуется (функция в скетче ) настройкой регистра специального назначения по адресу (0Eh) установкой битов выбора частоты 4-ый (RS2), 3-ий (RS1) в логический “0”
Скетч
// вывод D13 синхроимпульсы на регистры LED драйвера
// вывод D11 данные на регистры LED драйвера
#include <SPI.h> // подключаем стандартную библиотеку "SPI"
#include <Wire.h> // подключаем стандартную библиотеку "Wire" для работы с шиной I2C
int LE = 8; // пин ардуинки выход «защёлка» на регистры LED драйвера
#define SQW 2 // пин D2 ардуинки для запуска обработки прерывания от сигнала DS3231
//удобная директива, который позволяет дать имя константе перед тем как программа будет скомпилирована. Обозначаем сегмент"A" семисегментного индикатора.
#define SEG_A 0b10000000
#define SEG_B 0b01000000 // Обозначаем сегмент"B"
#define SEG_C 0b00100000 // Обозначаем сегмент"C"
#define SEG_D 0b00010000 // Обозначаем сегмент"D"
#define SEG_E 0b00001000 // Обозначаем сегмент"E"
#define SEG_F 0b00000100 // Обозначаем сегмент"F"
#define SEG_G 0b00000010 // Обозначаем сегмент"G"
#define SYMBOL_0 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_E | SEG_F) // директива собирающая сегменты индикатора в символ "0"
#define SYMBOL_1 (SEG_B | SEG_C ) // директива собирающая сегменты индикатора в символ "1"
#define SYMBOL_2 (SEG_A | SEG_B | SEG_D | SEG_E | SEG_G) // директива собирающая сегменты индикатора в символ "2"
#define SYMBOL_3 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_G ) // директива собирающая сегменты индикатора в символ "3"
#define SYMBOL_4 (SEG_B | SEG_C | SEG_F | SEG_G ) // директива собирающая сегменты индикатора в символ "4"
#define SYMBOL_5 (SEG_A | SEG_C | SEG_D | SEG_F | SEG_G ) // директива собирающая сегменты индикатора в символ "5"
#define SYMBOL_6 (SEG_A | SEG_C | SEG_D | SEG_E | SEG_F | SEG_G ) // директива собирающая сегменты индикатора в символ "6"
#define SYMBOL_7 (SEG_A | SEG_B | SEG_C ) // директива собирающая сегменты индикатора в символ "7"
#define SYMBOL_8 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_E | SEG_F | SEG_G ) // директива собирающая сегменты индикатора в символ "8"
#define SYMBOL_9 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_F | SEG_G ) // директива собирающая сегменты индикатора в символ "9"
long randNumber; // объявляем переменную "randNumber"
void setup()
{
Serial.begin(9600); // скорость для работы с монитором порта
pinMode(SQW, INPUT); //настройка пина D2 на прием информации
Wire.begin(); // Инициализируем шину I2C
SPI.begin(); // Инициализирует шину SPI
// Функция устанавливает порядок вывода даннах в/из шины SPI, может быть LSBFIRST (наименьший разряд(бит) первый) или MSBFIRST (старший разряд первый).
SPI.setBitOrder(LSBFIRST);
sqw1HzDS3231(); // запуск прямоугольного сигнала с частотой 1 Гц на выходе SQW модуля DS3231
attachInterrupt(0, interrput, FALLING); // запускаем функцию обработки внешнего прерывания
randomSeed(analogRead(0)); // инициализируем генератор псевдослучайных чисел
}
// Функция вывода случайного числа на индикаторы и монитор порта
void showChislo()
{
static const uint8_t Disp[] = {SYMBOL_0,SYMBOL_1,SYMBOL_2,SYMBOL_3,SYMBOL_4,SYMBOL_5,SYMBOL_6,SYMBOL_7,SYMBOL_8,SYMBOL_9}; // массив элиментов вывода на семисегментный светодиодный индикатор
randNumber = random(9999); //возвращаем псевдослучайное число от 0 до 9999
digitalWrite(LE, LOW); // установка низкого уровня на 4 ногу регистров LED драйвера
SPI.transfer( Disp[randNumber%10]); // // работа функции из библиотеки "SPI" передача данных в регистры о единицах
SPI.transfer( Disp[randNumber%100/10]); // работа функции из библиотеки "SPI" передача данных в регистры о десятках
SPI.transfer( Disp[randNumber%1000/100]); // работа функции из библиотеки "SPI" передача данных в регистры о сотнях
SPI.transfer( Disp[randNumber/1000]); // работа функции из библиотеки "SPI" передача данных в регистры о тысячах
Serial.println(randNumber); // вывод в терминал монитор
/ установка высокого уровня на 4 ноге регистров LED драйвера, в этот момент данные из регистров передаются в выходные каскады и происходит смена информации на индикаторах
digitalWrite(LE, HIGH);
}
static void interrput(void) // запуск функции работающей по прерыванию
{
const byte oldSReg = SREG; // переменная где сохраняется текущий статус регистра "SREG"
sei(); //команда устанавливает флаг глобального прерывания в регистре статуса "SREG"
showChislo(); //выполняется функция вывода случайного числа на индикаторы и монитор порта
SREG = oldSReg; // возвращаем статус регистра "SREG" таким же каким он и был
}
void sqw1HzDS3231() // функция запуска прямоугольного сигнала с частотой 1 Гц на выходе SQW модуля DS3231
{
Wire.beginTransmission(0x68); // обращение к шине I2C по адресу 0x68 к модулю DS3231
Wire.write(0x0e); // обращение к регистру 0Eh модуля DS3231
Wire.write(B01100011); // данные записанные в регистр
Wire.endTransmission(); // оканчиваем работу с шиной I2C
}
void loop()
{
}
Прямоугольный сигнал с частотой 1 Гц на выходе SQW модуля DS3231
Вот это очень правильно! Он там появляется как раз в момент смены секунды в часах, так что если им пользоваться, то секунды будут сменяться вовремя, а не когда попало, как делют большинство "ютубсенсэев".
Библиотеку для часов использовал из вышеуказанной темы на форуме № поста #273 и еще одна дублирующая ссылка . Вывод секунд делать не буду, понравилась идея использования точек у индикаторов. Т.е. в диапазоне 0-14 сек горит точка 4-ого индикатора, 15-29 сек точка третьего индикатора, 30-44 сек второго и 45-59 сек первого (при этом индикаторы переворачиваются и точки находятся сверху ). Разделительные точки буду запускать от сигнала с выхода SQW сделаю ключевой каскад (переход с высокого уровня на низкий). Данные о времени в модуль записал отдельным скетчем.
#include "Wire.h"
#define DS3231_ADD 0x68
// Convert normal decimal numbers to binary coded decimal
byte decToBcd(byte val)
{
return( (val/10*16) + (val%10) );
}
// Convert binary coded decimal to normal decimal numbers
byte bcdToDec(byte val)
{
return( (val/16*10) + (val%16) );
}
void setup()
{
Wire.begin();
Serial.begin(9600);
// set the initial time here:
// DS3231 seconds, minutes, hours, day, date, month, year
setDS3231time(00,46,13,6,10,02,18); // вот ввод времени
}
void setDS3231time(byte second, byte minute, byte hour, byte dayOfWeek, byte dayOfMonth, byte month, byte year)
{
// sets time and date data to DS3231
Wire.beginTransmission(DS3231_ADD);
Wire.write(0); // set next input to start at the seconds register
Wire.write(decToBcd(second)); // set seconds
Wire.write(decToBcd(minute)); // set minutes
Wire.write(decToBcd(hour)); // set hours
Wire.write(decToBcd(dayOfWeek)); // set day of week (1=Sunday, 7=Saturday)
Wire.write(decToBcd(dayOfMonth)); // set date (1 to 31)
Wire.write(decToBcd(month)); // set month
Wire.write(decToBcd(year)); // set year (0 to 99)
Wire.endTransmission();
}
void readDS3231time(byte *second,
byte *minute,
byte *hour,
byte *dayOfWeek,
byte *dayOfMonth,
byte *month,
byte *year)
{
Wire.beginTransmission(DS3231_ADD);
Wire.write(0); // set DS3231 register pointer to 00h
Wire.endTransmission();
Wire.requestFrom(DS3231_ADD, 7);
// request seven bytes of data from DS3231 starting from register 00h
*second = bcdToDec(Wire.read() & 0x7f);
*minute = bcdToDec(Wire.read());
*hour = bcdToDec(Wire.read() & 0x3f);
*dayOfWeek = bcdToDec(Wire.read());
*dayOfMonth = bcdToDec(Wire.read());
*month = bcdToDec(Wire.read());
*year = bcdToDec(Wire.read());
}
void displayTime()
{
byte second, minute, hour, dayOfWeek, dayOfMonth, month, year;
// retrieve data from DS3231
readDS3231time(&second, &minute, &hour, &dayOfWeek, &dayOfMonth, &month,
&year);
// send it to the serial monitor
Serial.print(hour, DEC);
// convert the byte variable to a decimal number when displayed
Serial.print(":");
if (minute<10)
{
Serial.print("0");
}
Serial.print(minute, DEC);
Serial.print(":");
if (second<10)
{
Serial.print("0");
}
Serial.print(second, DEC);
Serial.print(" ");
Serial.print(dayOfMonth, DEC);
Serial.print("/");
Serial.print(month, DEC);
Serial.print("/");
Serial.print(year, DEC);
Serial.print(" ");
switch(dayOfWeek){
case 1:
Serial.println("Понедельник");
break;
case 2:
Serial.println("Вторник");
break;
case 3:
Serial.println("Среда");
break;
case 4:
Serial.println("Четверг");
break;
case 5:
Serial.println("Пятница");
break;
case 6:
Serial.println("Суббота");
break;
case 7:
Serial.println("Воскресенье");
break;
}
}
void loop()
{
displayTime(); // display the real-time clock data on the Serial Monitor
delay(1000);
}
Часы работают теперь нужно прикрутить кнопки для установки времени.
// Часы на Arduino Nano, модуль реального времени DS3231, Led драйверы MBI5026 семисегментные идикаторы с общим анодом
// вывод D13 синхроимпульсы на регистры LED драйвера
// вывод D11 данные на регистры LED драйвера
#include <SPI.h> // подключаем стандартную библиотеку "SPI". Информация http://arduino.ru/Reference/Library/SPI
#include <Wire.h> // подключаем стандартную библиотеку "Wire" для работы с шиной I2C. Информация http://arduino.net.ua/file_archive/Arduino%20Library/Arduino%20Wire%20Library/
#include <DS3231.h> // подключаем библиотеку "DS3231" для работы с модулем DS3231. Библиотека https://drive.google.com/open?id=1gLDgEly1GCLp6NTWJxRjWz2vb08AUuoo
int LE = 8; // пин D8 ардуинки выход «защёлка» на регистры LED драйвера
#define SQW 2 // пин D2 ардуинки для запуска обработки прерывания от сигнала DS3231
#define SEG_A 0b10000000 // удобная директива, который позволяет дать имя константе перед тем как программа будет скомпилирована. Обозначаем сегмент"A" семисегментного индикатора.
#define SEG_B 0b01000000 // Обозначаем сегмент"B"
#define SEG_C 0b00100000 // Обозначаем сегмент"C"
#define SEG_D 0b00010000 // Обозначаем сегмент"C"
#define SEG_E 0b00001000 // Обозначаем сегмент"E"
#define SEG_F 0b00000100 // Обозначаем сегмент"F"
#define SEG_G 0b00000010 // Обозначаем сегмент"G"
#define SEG_dp 0b0000001 // Обозначаем сегмент"dp" точка на индикаторе
#define SYMBOL_0 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_E | SEG_F) // директива собирающая сегменты индикатора в символ "0"
#define SYMBOL_1 (SEG_B | SEG_C) // директива собирающая сегменты индикатора в символ "1"
#define SYMBOL_2 (SEG_A | SEG_B | SEG_D | SEG_E | SEG_G) // директива собирающая сегменты индикатора в символ "2"
#define SYMBOL_3 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_G) // директива собирающая сегменты индикатора в символ "3"
#define SYMBOL_4 (SEG_B | SEG_C | SEG_F | SEG_G) // директива собирающая сегменты индикатора в символ "4"
#define SYMBOL_5 (SEG_A | SEG_C | SEG_D | SEG_F | SEG_G) // директива собирающая сегменты индикатора в символ "5
#define SYMBOL_6 (SEG_A | SEG_C | SEG_D | SEG_E | SEG_F | SEG_G) // директива собирающая сегменты индикатора в символ "6"
#define SYMBOL_7 (SEG_A | SEG_B | SEG_C) // директива собирающая сегменты индикатора в символ "7"
#define SYMBOL_8 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_E | SEG_F | SEG_G) // директива собирающая сегменты индикатора в символ "8"
#define SYMBOL_9 (SEG_A | SEG_B | SEG_C | SEG_D | SEG_F | SEG_G) // директива собирающая сегменты индикатора в символ "9"
static DS3231 Clock; // ???????? что-то связанное с библиотекой "DS3231"
int hou,minu,sec; //Тип данных для часов, минут и секунд, смотреть http://arduino.ru/Reference/Int
void setup()
{
Serial.begin(9600); // скорость для работы с монитором порта (нужна для отстройки работы программы)
pinMode(SQW, INPUT); //настройка пина D2 на прием информации
Wire.begin(); // Инициализируем шину I2C
SPI.begin(); // Инициализирует шину SPI, устанавиливая пины SCK, MOSI, и SS как выходы и уровень сигнала на SCK и MOSI — LOW и на SS — HIGH.
SPI.setBitOrder(LSBFIRST); // Функция устанавливает порядок вывода даннах в/из шины SPI, может быть LSBFIRST (наименьший разряд(бит) первый) или MSBFIRST (старший разряд первый).
sqw1HzDS3231(); // запуск прямоугольного сигнала с частотой 1 Гц на выходе SQW модуля DS3231
attachInterrupt(0,interrput, FALLING); // запускаем функцию обработки внешнего прерывания, смотреть http://arduino.ru/Reference/AttachInterrupt
}
void show_Disp() // функция для получения данных о времени с DS3231 и вывод светодиодный индикатор (работа с библиотекой "DS323")
{
hou=Clock.getHour(); // запрос о часах
int h_dec=hou/10; // целое число от деления часов на 10 т.е. десятки часов
int h_ed=hou%10; //остаток от деления часов на 10 т.е. единицы часов
minu=Clock.getMinute(); // запрос о минутах
int m_dec=minu/10; // целое число от деления минут на 10 т.е. десятки минут
int m_ed=minu%10; //остаток от деления минут на 10 т.е. единицы минут
sec=Clock.getSecond(); // запрос о секундах (на дисплей не вывожу)
static const uint8_t Disp[] = {SYMBOL_0,SYMBOL_1,SYMBOL_2,SYMBOL_3,SYMBOL_4,SYMBOL_5,SYMBOL_6,SYMBOL_7,SYMBOL_8,SYMBOL_9}; // массив элиментов вывода на семисегментный светодиодный индикатор
digitalWrite(LE, LOW); // установка низкого уровня на 4 ногу регистров LED драйвера
SPI.transfer( Disp[m_ed]); // работа функции из библиотеки "SPI" передача данных в регистры о единицах минут
SPI.transfer( Disp[m_dec]); // работа функции из библиотеки "SPI" передача данных в регистры о десятках минут
SPI.transfer( Disp[h_ed]); // работа функции из библиотеки "SPI" передача данных в регистры о единицах часов
SPI.transfer( Disp[h_dec]); // работа функции из библиотеки "SPI" передача данных в регистры о десятках часов
digitalWrite(LE, HIGH); // установка высокого уровня на 4 ноге регистров LED драйвера, в этот момент данные из регистров передаются в выходные каскады и происходит смена информации на индикаторах
show_Term_Mon(); //запуск функции вывода на терминал монитор для отладки, закоментировать при реальной работе
}
void show_Term_Mon() //функция вывода на терминал монитор
{
Serial.print(hou);
Serial.print(":");
Serial.print(minu);
Serial.print(":");
Serial.println(sec);
}
static void interrput(void) // запуск функции работающей по прерыванию
{
const byte oldSReg = SREG; // переменная где сохраняется текущий статус регистра "SREG"
sei(); //команда устанавливает флаг глобального прерывания в регистре статуса "SREG"
show_Disp(); //выполняется функция для получения данных о времени с DS3231 и вывод на светодиодный индикатор
SREG = oldSReg; // возвращаем статус регистра "SREG" таким же каким он и был
}
void sqw1HzDS3231() // функция запуска прямоугольного сигнала с частотой 1 Гц на выходе SQW модуля DS3231
{
Wire.beginTransmission(0x68); // обращение к модулю DS3231 по шине I2C по адресу 0x68
Wire.write(0x0e); // обращение к регистру 0Eh модуля DS3231
Wire.write(B01100011); // данные записанные в регистр
Wire.endTransmission(); // оканчиваем работу с шиной I2C
}
void loop()
{
}
Понравилось управление функционалом часов посредством Web-интерфейса.
Ну, я то имел в виду не web-интерфейс, а NTP. У меня вот самоутсанавливаются прикаждом включении питания или раз в неделю (что раньше), так и я забыл про них - всегда точно показывают.
... NTP. У меня вот самоутсанавливаются прикаждом включении питания или раз в неделю (что раньше), так и я забыл про них - всегда точно показывают.
Я забыл чуть раньше - еще до завершения отладки. Поэтому синхронизируются раз в 15 минут. Да и еще пытаются писать протокол отладки на карточку. Чтобы не писали, карточку вынул. А т.к. время показывают нормально, то и возвращаться к ним, убирать протокол и назначить вменяемый интервал синхронизации как-то руки не доходят.
года 3 назад начинал, игрался с часиками. Собрал таки на школьный каток на этой микросхеме точнее на 2х. а вот цифирки я массивом задал несколько проще, код ниже, он тестовый...
byte digits[16]={63, 6, 91, 79, 102, 109, 125, 7, 127, 111, 119, 124, 57, 94, 121, 113};
unsigned char j, k=0;
byte D1, D2, D3, D4;
long previousMillis = 0; // will store last time LED was updated
// the follow variables is a long because the time, measured in miliseconds,
// will quickly become a bigger number than can be stored in an int.
long interval = 200; // interval at which to blink (milliseconds)
int MBI5026_pinOE = 6; // pd6(12) MBIpin21. When (active) low, the output drivers are enabled; when high, all output drivers are turned OFF (blanked).
int MBI5026_pinLE = A1; // pc1(24) MBIpin4. Data strobe. Serial data is transferred to the output latch when LE is high. The data is latched when LE goes low.
int MBI5026_pinCLK = A2; // pc2(25) MBIpin3. Clock input terminal for data shift on rising edge
int MBI5026_pinSDI = A3; // pc3(26) MBIpin2. Serial-data input to the shift register
void Write_MBI5026(byte HD, byte HS, byte MD, byte MS)
{
digitalWrite(MBI5026_pinLE,LOW); // проверить и убрать строку
shiftOut(MBI5026_pinSDI, MBI5026_pinCLK, LSBFIRST, MS);
shiftOut(MBI5026_pinSDI, MBI5026_pinCLK, LSBFIRST, MD);
shiftOut(MBI5026_pinSDI, MBI5026_pinCLK, LSBFIRST, HS);
shiftOut(MBI5026_pinSDI, MBI5026_pinCLK, LSBFIRST, HD);
// shiftOut(MBI5026_pinSDI, MBI5026_pinCLK, MSBFIRST, HD);
digitalWrite(MBI5026_pinLE,HIGH);
digitalWrite(MBI5026_pinLE,LOW);
}
void setup()
{
pinMode(MBI5026_pinOE, OUTPUT);
pinMode(MBI5026_pinCLK, OUTPUT);
pinMode(MBI5026_pinSDI, OUTPUT);
pinMode(MBI5026_pinLE, OUTPUT);
}
void loop()
{
unsigned long currentMillis = millis();
if(currentMillis - previousMillis > interval)
{
// save the last time you blinked the LED
previousMillis = currentMillis;
k=k+1;
}
D1=k /1000%10;
D2=k /100%10;
D3=k /10%10;
D4=k %10;
Write_MBI5026(digits[D2], digits[D1], digits[D4], digits[D3]);
analogWrite(MBI5026_pinOE,128); // стоит 2 микрухи, зажигаем по очереди через инвертер - меньше тока жрет
}
пост 51 строки с 09 по 26 одной строкой 02, да и жрали они много, строка 60
пост 51 строки с 09 по 26 одной строкой 02, да и жрали они много, строка 60
Благодарю за участие в теме.
Согласен строк много, но для начинающих очень даже доходчиво, по-крайней мере для меня все стало на свои места. Все сделано по шагам:
-строки 09-15 сначала определили каждый сегмент индикатора;
-строки 17-26 определили какие сегменты участвуют в индикации той или иной цифры и применив побитовое “ИЛИ” | получили “цифирки данных” которых в скетче совсем не видно;
-строка 46 организовали массив в виде удобно читаемым для таких как я).
Если выполнить вычисления и провести замену элементов “SYMBOL_*” в массиве (строка 46) на числовые значения (от которых у начинающего могут возникнуть вопросы), то строки 09-15 и 17-26 можно убрать.
Вопрос повышенного потребления я не рассматривал. В моем случае контакт "ОЕ" драйверов MBI5026 подключен к “GND” и они как бы всегда в активном состоянии. У Вас задействован ШИМ, надо будет проверить как зависит ток потребления от ширины импульса прямоугольного сигнала.
Вопрос повышенного потребления я не рассматривал. В моем случае контакт "ОЕ" драйверов MBI5026 подключен к “GND” и они как бы всегда в активном состоянии. У Вас задействован ШИМ, надо будет проверить как зависит ток потребления от ширины импульса прямоугольного сигнала.
очень просто, у меня почти 5 метров ленты 12В ушло на часы, а это в пике больше 2А (если все сегменты нули т.к. всех восьмерок в системе нет). провод у меня больше 5 метров от БП и не самый толстый. вот я и "зажигаю" по очереди то одну микросхему, то другую. Задействовал ШИМ т.к. это самое простое для получения меандра, а инвертером меняю фазу сигнала управления. Инвертер самый простой на одном транзисторе и двух сопротивлениях.
AR пишет:
надо будет проверить как зависит ток потребления от ширины импульса прямоугольного сигнала.
а так же яркость свечения сегментов и всякая "гадость" в проводах, которая может повлиять на работу, если не фильтровать большими конденсаторами.
Идея понятна. Времени нет чтобы проверить работу ШИМа с драйверами. И потихоньку перевариваю работу кнопок, вижу основную проблему в "дребезге контактов". На быструю внедрил три кнопки (обнуление секунд, ++ минуты и ++ часы) видна нестабильность работы именно из-за дребезга. Склоняюсь в сторону использования апаратного решения, например: RS-триггер (рассыпуха меня не пугает) и трехконтактные кнопки (из компьютерных мышек).
Склоняюсь в сторону использования апаратного решения, например: RS-триггер (рассыпуха меня не пугает)
Тогда и часы надо было собирать на 155 или 176 серии. А раз взялись за МК, давите дребезг программно. И посмотрите в сторону энкодера с центральной кнопкой.
Тогда и часы надо было собирать на 155 или 176 серии.
Согласен, был не прав, “увиливать” не надо. Исправляюсь.
alex_r61 пишет:
в сторону энкодера с центральной кнопкой
Обязательно поработаю с энкодером. Но в реальной конструкции часов он будет не "комильфо" постоянно его кто-нибудь будет крутить и нажимать, а кнопочки они будут в "потай" и чтобы их нажать надо будет постараться). Вот в следующей конструкции FM приемника энкодер будет в самый раз.
На быструю внедрил три кнопки (обнуление секунд, ++ минуты и ++ часы) видна нестабильность работы именно из-за дребезга.
читайте немного в начале (пару листов), и потом последние 3 листа, всего читать сложно (воды много), главной на последних листах найти ссыль на гитхаб, ну и немного ознакомиться по теме. Добро бы все перечитать, да там 80% мусора, а польза вся размазана.
Как я раньше не сообразил - “титановый велосипед” это именно, тот самый, уже изобретенный “велосипед”. Спасибо за разъяснение. Особенно за отсылку к GITHUB в посте № 712
Как я раньше не сообразил - “титановый велосипед” это именно, тот самый, уже изобретенный “велосипед”. Спасибо за разъяснение. Особенно за отсылку к GITHUB в посте № 712
Доброго всем дня! Запустил часы! Взял за основу тему на форуме “7- cегментный дисплей для arduino”. Сначала повозился с выводом информации на индикаторы. Привожу тестовый скетч, может кому будет интересно. Случайчый вывод числа в диапазоне от 0 до 9999. Исключил “делеи” как и советовали - задействовав прерывание. Прямоугольный сигнал с частотой 1 Гц на выходе SQW модуля DS3231 организуется (функция в скетче ) настройкой регистра специального назначения по адресу (0Eh) установкой битов выбора частоты 4-ый (RS2), 3-ий (RS1) в логический “0”
Скетч
Схема
Индикаторы
Прямоугольный сигнал с частотой 1 Гц на выходе SQW модуля DS3231
Вот это очень правильно! Он там появляется как раз в момент смены секунды в часах, так что если им пользоваться, то секунды будут сменяться вовремя, а не когда попало, как делют большинство "ютубсенсэев".
Библиотеку для часов использовал из вышеуказанной темы на форуме № поста #273 и еще одна дублирующая ссылка . Вывод секунд делать не буду, понравилась идея использования точек у индикаторов. Т.е. в диапазоне 0-14 сек горит точка 4-ого индикатора, 15-29 сек точка третьего индикатора, 30-44 сек второго и 45-59 сек первого (при этом индикаторы переворачиваются и точки находятся сверху ). Разделительные точки буду запускать от сигнала с выхода SQW сделаю ключевой каскад (переход с высокого уровня на низкий). Данные о времени в модуль записал отдельным скетчем.
Часы работают теперь нужно прикрутить кнопки для установки времени.
Благодарствую, Ваша тема очень помогла.
А не лучше ESP-01 присобачить.
Сначала поиграюсь с кнопками, а потом "замахнусь" и на Wi-Fi. Понравилось управление функционалом часов посредством Web-интерфейса.
... NTP. У меня вот самоутсанавливаются прикаждом включении питания или раз в неделю (что раньше), так и я забыл про них - всегда точно показывают.
Я забыл чуть раньше - еще до завершения отладки. Поэтому синхронизируются раз в 15 минут. Да и еще пытаются писать протокол отладки на карточку. Чтобы не писали, карточку вынул. А т.к. время показывают нормально, то и возвращаться к ним, убирать протокол и назначить вменяемый интервал синхронизации как-то руки не доходят.
Я понял, что речь шла о применении сетевого протокола NTP, просто web-интерфейс это продолжение "спортивного интереса".
года 3 назад начинал, игрался с часиками. Собрал таки на школьный каток на этой микросхеме точнее на 2х. а вот цифирки я массивом задал несколько проще, код ниже, он тестовый...
пост 51 строки с 09 по 26 одной строкой 02, да и жрали они много, строка 60
пост 51 строки с 09 по 26 одной строкой 02, да и жрали они много, строка 60
Благодарю за участие в теме.
Согласен строк много, но для начинающих очень даже доходчиво, по-крайней мере для меня все стало на свои места. Все сделано по шагам:
-строки 09-15 сначала определили каждый сегмент индикатора;
-строки 17-26 определили какие сегменты участвуют в индикации той или иной цифры и применив побитовое “ИЛИ” | получили “цифирки данных” которых в скетче совсем не видно;
-строка 46 организовали массив в виде удобно читаемым для таких как я).
Если выполнить вычисления и провести замену элементов “SYMBOL_*” в массиве (строка 46) на числовые значения (от которых у начинающего могут возникнуть вопросы), то строки 09-15 и 17-26 можно убрать.
Вопрос повышенного потребления я не рассматривал. В моем случае контакт "ОЕ" драйверов MBI5026 подключен к “GND” и они как бы всегда в активном состоянии. У Вас задействован ШИМ, надо будет проверить как зависит ток потребления от ширины импульса прямоугольного сигнала.
Вопрос повышенного потребления я не рассматривал. В моем случае контакт "ОЕ" драйверов MBI5026 подключен к “GND” и они как бы всегда в активном состоянии. У Вас задействован ШИМ, надо будет проверить как зависит ток потребления от ширины импульса прямоугольного сигнала.
очень просто, у меня почти 5 метров ленты 12В ушло на часы, а это в пике больше 2А (если все сегменты нули т.к. всех восьмерок в системе нет). провод у меня больше 5 метров от БП и не самый толстый. вот я и "зажигаю" по очереди то одну микросхему, то другую. Задействовал ШИМ т.к. это самое простое для получения меандра, а инвертером меняю фазу сигнала управления. Инвертер самый простой на одном транзисторе и двух сопротивлениях.
надо будет проверить как зависит ток потребления от ширины импульса прямоугольного сигнала.
а так же яркость свечения сегментов и всякая "гадость" в проводах, которая может повлиять на работу, если не фильтровать большими конденсаторами.
Идея понятна. Времени нет чтобы проверить работу ШИМа с драйверами. И потихоньку перевариваю работу кнопок, вижу основную проблему в "дребезге контактов". На быструю внедрил три кнопки (обнуление секунд, ++ минуты и ++ часы) видна нестабильность работы именно из-за дребезга. Склоняюсь в сторону использования апаратного решения, например: RS-триггер (рассыпуха меня не пугает) и трехконтактные кнопки (из компьютерных мышек).
Склоняюсь в сторону использования апаратного решения, например: RS-триггер (рассыпуха меня не пугает)
Тогда и часы надо было собирать на 155 или 176 серии. А раз взялись за МК, давите дребезг программно. И посмотрите в сторону энкодера с центральной кнопкой.
Тогда и часы надо было собирать на 155 или 176 серии.
Согласен, был не прав, “увиливать” не надо. Исправляюсь.
в сторону энкодера с центральной кнопкой
читайте немного в начале (пару листов), и потом последние 3 листа, всего читать сложно (воды много), главной на последних листах найти ссыль на гитхаб, ну и немного ознакомиться по теме. Добро бы все перечитать, да там 80% мусора, а польза вся размазана.
Вот тема которую пытаюсь смотреть Работа с кнопками. В помощь новичку . Тему класс титановый велосипед для тактовой кнопки я видел, но пока еще не пытался "раскурить". Займусь.
"Работа с кнопками...." - базовые подходы изложенные в сумбурной форме, но знать их надо. Лисапед - готовый инструмент для кнопок.