用esp8266做一个网络时钟

一、产品简介

​ TM1638是深圳市天微电子有限公司设计的一款带键盘扫描接口的LED(发光二极管显示器)驱动控制专用芯片,内部集成有MCU数字接口、数据锁存器、LED高压驱动、键盘扫描等电路。主要应用于冰箱、空调 、家庭影院等产品的高段位显示屏驱动。

​ TM1638按键数码管LED显示模块是用TM1638芯片驱动,集合了单片机常用外围电路,最大特点是只需要占用单片机三个IO口即可驱动,扫描显示和按键扫描不需要单片机干预,只需要读写相关寄存器送显示数据或检测按键,节省MCU资源。

在这里插入图片描述

引脚定义(采用SPI通信协议):

  • VCC:DC-5V
  • GND:GND
  • STB:MOSI
  • CLK:SCLK
  • DIO:MISO

二、技术参数

  • 采用功率CMOS 工艺
  • 显示模式 10 段×8 位
  • 键扫描(8×3bit)
  • 8级辉度可调
  • 串行接口(CLK,STB,DIO)
  • 振荡方式:RC 振荡(450KHz+5%)
  • 内置上电复位电路
  • 采用SOP28封装

三、软件接口

驱动下载地址https://github.com/mcauser/micropython-tm1638

Methods

Power up, power down or check status.

power(val=None)

Get or set brightness.

brightness(val=None)

Write zeros to each address.

clear()

Write to all 16 addresses from a given position. Order is left to right, 1st segment, 1st LED, 2nd segment, 2nd LED etc.

write(data, pos=0)

Set the value of a single LED.

led(pos, val)

Set all LEDs at once. LSB is left most LED. Only writes to the LED positions (every 2nd starting from 1).

leds(val)

Set one or more segments at a relative position. Only writes to the segment positions (every 2nd starting from 0).

segments(segments, pos=0)

Return a byte representing which keys are pressed. LSB is SW1.

keys()

Convert a single hex digit (0x00-0x0f) to a segment.

encode_digit(digit)

Convert a string to a list of segments. Dots are merged with the previous character.

encode_string(string)

Convert a single character to a segment.

encode_char(char)

Display a number in hexadecimal format 00000000 through FFFFFFFF, right aligned, leading zeros.

hex(val)

Display a numeric value -9999999 through 99999999, right aligned.

number(num)

Display a temperature -9 through 99 followed by degrees C.

temperature(num, pos=0)

Displays a relative humidity -9 through 99 followed by RH.

humidity(num, pos=4)

Displays as much of a string as will fit.

show(string, pos=0)

Display a string, scrolling from the right to left, speed adjustable. String starts off-screen right and scrolls until off-screen left at 4 FPS by default.

scroll(string, delay=250)

四、接口案例

利用esp8266显示时钟

在这里插入图片描述

接线:

ESP8266LED&KEY TM1638 Module
3V3 (or 5V)VCC
GGND
D7 (GPIO13)STB
D5 (GPIO14)CLK
D6 (GPIO12)DIO

模块导入:

from package import tm1368 as tm1638
from package import alarm as am
from machine import Pin,RTC
import time
from package import WiFi
import ntptime
import network
import uasyncio as asyncio
#import upip #用于安装asyncio库
#upip.install("_thread")

引脚定义:

rtc = RTC()
'''
D7 (GPIO13)	STB
D5 (GPIO14)	CLK
D6 (GPIO12) DIO
'''
tm=tm1638.TM1638(stb=Pin(13),clk=Pin(14),dio=Pin(12)) ##标号一致 板子有标记

全局变量:

alarm_hour = 12
alarm_minute = 0
alarm_flag = True #闹钟开关
alarm_status = False #闹钟状态

hour = 13
minute = 14
second = 0
year = 2022
month = 5
day = 20

'''
mode = 0 显示时间
mode = 1 显示日期
mode = 2 显示闹钟
'''
mode = 0

联网同步时间:

#联网并同步时间
WiFi.WIFI_Connect()
WiFi.sync_ntp()
last_sync_time = 0
print(rtc.datetime())
print("同步后本地时间:%s" %str(time.localtime()))

显示时间:

def display_time():#时间显示画面
    #tm.clear()
    global hour
    global minute
    global second
    now_time = "{:0>2d}-{:0>2d}-{:0>2d}".format(hour,minute,second)
    # print(now_time)
    tm.show(now_time)

显示日历:

def display_calendar():#日历显示画面
    global month
    global day
    global year
    now_calendar = "{}.{:0>2d}.{:0>2d}".format(year,month,day)
    tm.show(now_calendar)

显示闹钟:

def display_alarm():#闹钟显示画面
    global alarm_hour
    global alarm_minute
    global alarm_flag
    if alarm_flag == 1 :
        status = '-11-'
    else:
        status = 'off-'
        #print(status)
    alarm = "{}{:0>2d}.{:0>2d}".format(status,alarm_hour,alarm_minute)
    tm.show(alarm)

闹钟设置(只设置了led流水灯,没用蜂鸣器):

async def mode1():
    b = 0x80
    t = 0
    for i in range(8):
        b = 0x80
        for j in range(8-i):
            st = b | t
            tm.leds(st)
            time.sleep(0.3)
            await asyncio.sleep(0.3)
            b = cror(b,1)
        b = crol(b,1)
        t = b | t

按键设置:

def set_model():#设置模式,选择显示内容
    k = [0] *9
    k = key_num(k)
    
    n = button(k)
    global alarm_hour
    global alarm_minute
    global mode
    global alarm_flag
    if n == 1:#闹钟小时增加
        if flag[n] == 0:
            alarm_hour +=1
            if alarm_hour > 23:
                alarm_hour = 0
            flag[n] = 1
    elif n == 2:#闹钟小时减少
        if flag[n] == 0:
            flag[n] = 1
            alarm_hour -=1
            if alarm_hour < 0:
                alarm_hour = 23
    elif n == 3:#闹钟分钟增加
        if flag[n] == 0:
            flag[n] = 1
            alarm_minute += 1
            if alarm_minute > 59:
                alarm_minute = 0
    
    elif n == 4:#闹钟分钟减少
        if flag[n] == 0:
            flag[n] = 1
            alarm_minute -= 1
            if alarm_minute < 0:
                alarm_minute = 59
    elif n ==5:#显示输出模式:时间、日历、闹钟
        if flag[n] == 0:
            flag[n] = 1
            mode = (mode+1)%3
    elif n == 6:#设置闹钟开关
        if flag[n] == 0:
            flag[n] = 1
            alarm_flag = ~ alarm_flag
            #print(alarm_flag)
    for i in range(1,len(k)):#按钮标志复位,防止连续按下
        if k[i] == 0 :
            flag[i] = 0

显示模块:

async def display():
  global year
  global month
  global day
  global hour
  global minute
  global second
  global alarm_flag
  global alarm_status
  while 1:
    t = time.localtime(time.time())
    year = t[0]
    month = t[1]
    day = t[2]
    hour = t[3]
    Synchronize_network_time(hour)
    minute = t[4]
    second = t[5]
    tm.brightness(0)
    if mode == 0:
        display_time()
    elif mode == 1:
        display_calendar()
    elif mode == 2:
        display_alarm()
    alarm_status = alarm_hour == hour and alarm_minute == minute
    set_model()
    await asyncio.sleep(0.05)

五、详细代码:

alarm.py

from package import tm1368 as tm1638
from machine import Pin
import time
import uasyncio as asyncio
tm=tm1638.TM1638(stb=Pin(13),clk=Pin(14),dio=Pin(12)) ##标号一致 板子有标记
def crol(d,k):#循环左移
    a = 1
    for i in range(0,k-1):
        a = (a << 1) + 1
    a = a<<(8-k)
    h = (d & a ) >> (8-k)
    d = ((d | a ) << k)%256 + h
    #print("d = {:0>8b},h = {:0>8b},a = {:0>8b}".format(d,h,a))
    return d
def cror(d,k):#循环右移
    a = 1
    for i in range(0,k-1):
        a = (a << 1) + 1
    h = (d & a ) << (8-k)
    d = (d >> k) + h
    print("d = {:0>8b},h = {:0>8b},a = {:0>8b}".format(d,h,a))
    return d
async def mode1():
    b = 0x80
    t = 0
    for i in range(8):
        b = 0x80
        for j in range(8-i):
            st = b | t
            tm.leds(st)
            time.sleep(0.3)
            await asyncio.sleep(0.3)
            b = cror(b,1)
        b = crol(b,1)
        t = b | t
def off():
    b = 0x00
    tm.leds(b)
def led():
    st = 0xaa
    status = []
    mode1()
if __name__ == '__main__':
    while True:
        led()

WIFI.py

import ntptime
import network,time
from machine import RTC,Pin
rtc = RTC()

print("同步前本地时间:%s" %str(time.localtime()))

# 联WIFI
def WIFI_Connect():

    wlan = network.WLAN(network.STA_IF) #STA模式
    wlan.active(True)                   #激活接口
    start_time=time.time()              #记录时间做超时判断
    if not wlan.isconnected():
        print('connecting to network...')
        wlan.connect('ssid', 'password') #输入WIFI账号密码
        while not wlan.isconnected():
            if time.time()-start_time > 15 :
                print('WIFI Connected Timeout!')
                break
    if wlan.isconnected():
        print('connected!')
        print('network information:', wlan.ifconfig())

# 同步时间
def sync_ntp():
     ntptime.NTP_DELTA = 3155644800   # 可选 UTC+8偏移时间(秒),不设置就是UTC0
     ntptime.host = 'ntp1.aliyun.com'  # 可选,ntp服务器,默认是"pool.ntp.org"
     try:
         ntptime.settime()   # 修改设备时间,到这就已经设置好了
     except:
         #for i in range(6):
         #   led.value(1)              #turn off 0是亮
          #  time.sleep(0.1)
          #  led.value(0)             
           # time.sleep(0.1)
         print('同步失败')

if __name__ == '__main__':
    WIFI_Connect()
    sync_ntp()
    print(rtc.datetime())
    print("同步后本地时间:%s" %str(time.localtime()))



main.py

from package import tm1368 as tm1638
from package import alarm as am
from machine import Pin,RTC
import time
from package import WiFi
import ntptime
import network
import uasyncio as asyncio
rtc = RTC()
'''
D7 (GPIO13)	STB
D5 (GPIO14)	CLK
D6 (GPIO12) DIO
'''
tm=tm1638.TM1638(stb=Pin(13),clk=Pin(14),dio=Pin(12)) ##标号一致 板子有标记

alarm_hour = 12
alarm_minute = 0
alarm_flag = True #闹钟开关
alarm_status = False #闹钟状态

hour = 13
minute = 14
second = 0
year = 2022
month = 5
day = 20

#k = [0]*9
'''
mode = 0 显示时间
mode = 1 显示日期
mode = 2 显示闹钟
'''
mode = 0
#联网并同步时间
WiFi.WIFI_Connect()
WiFi.sync_ntp()
last_sync_time = 0
print(rtc.datetime())
print("同步后本地时间:%s" %str(time.localtime()))

def key_num(k):#这个类是按钮用的,凑合用用
  if tm.keys()==1:
    k[1]=1
  elif tm.keys()==2:
    k[2]=1
  elif tm.keys()==4:
    k[3]=1
  elif tm.keys()==8:
    k[4]=1
  elif tm.keys()==16:
    k[5]=1
  elif tm.keys()==32:
    k[6]=1
  elif tm.keys()==64:
    k[7]=1
  elif tm.keys()==128:
    k[8]=1
  return k
        
def display_time():#时间显示画面
    #tm.clear()
    global hour
    global minute
    global second
    now_time = "{:0>2d}-{:0>2d}-{:0>2d}".format(hour,minute,second)
    # print(now_time)
    tm.show(now_time)
    
def display_calendar():#日历显示画面
    global month
    global day
    global year
    now_calendar = "{}.{:0>2d}.{:0>2d}".format(year,month,day)
    tm.show(now_calendar)

def display_alarm():#闹钟显示画面
    global alarm_hour
    global alarm_minute
    global alarm_flag
    if alarm_flag == 1 :
        status = '-11-'
    else:
        status = 'off-'
        #print(status)
    alarm = "{}{:0>2d}.{:0>2d}".format(status,alarm_hour,alarm_minute)
    tm.show(alarm)
    
flag = [0]*9 #按键标志
def button(k):
    for i in range(len(k)):
        if k[i]==1:
            return i
    return 0

def set_model():#设置模式,选择显示内容
    k = [0] *9
    k = key_num(k)
    
    n = button(k)
    global alarm_hour
    global alarm_minute
    global mode
    global alarm_flag
    if n == 1:#闹钟小时增加
        #print(n,flag[n],flag[2])
        if flag[n] == 0:
            alarm_hour +=1
            if alarm_hour > 23:
                alarm_hour = 0
            flag[n] = 1
    elif n == 2:#闹钟小时减少
        #print(n,flag[n],flag[1])
        if flag[n] == 0:
            flag[n] = 1
            alarm_hour -=1
            if alarm_hour < 0:
                alarm_hour = 23
    elif n == 3:#闹钟分钟增加
        if flag[n] == 0:
            flag[n] = 1
            alarm_minute += 1
            if alarm_minute > 59:
                alarm_minute = 0
    
    elif n == 4:#闹钟分钟减少
        if flag[n] == 0:
            flag[n] = 1
            alarm_minute -= 1
            if alarm_minute < 0:
                alarm_minute = 59
    elif n ==5:#显示输出模式:时间、日历、闹钟
        if flag[n] == 0:
            flag[n] = 1
            mode = (mode+1)%3
    elif n == 6:#设置闹钟开关
        if flag[n] == 0:
            flag[n] = 1
            alarm_flag = ~ alarm_flag
            #print(alarm_flag)
    for i in range(1,len(k)):#按钮标志复位,防止连续按下
        if k[i] == 0 :
            flag[i] = 0
            
def Synchronize_network_time(hour):#每六个小时同步时间
    global last_sync_time
    if hour %6 == 0 and hour!= last_sync_time:
        wlan = network.WLAN(network.STA_IF) #STA模式
        if not wlan.isconnected():
            #print("正在连接网络")
            WiFi.WIFI_Connect()
        WiFi.sync_ntp()
        print('{hour}同步成功')
        last_sync_time == hour
''' 按下第 n 个按钮 k[n] = 1'''
async def alarm():
    global alarm_flag
    global alarm_status
    if alarm_flag == 1 and alarm_status == 1:
        
        await am.mode1()
    else:
        am.off()
        
async def alarm_test():
    while True:
        await alarm()
        
        await asyncio.sleep(1)
        
        
async def display():
  global year
  global month
  global day
  global hour
  global minute
  global second
  global alarm_flag
  global alarm_status
  while 1:
    t = time.localtime(time.time())
    year = t[0]
    month = t[1]
    day = t[2]
    hour = t[3]
    Synchronize_network_time(hour)
    minute = t[4]
    second = t[5]
    tm.brightness(0)
    if mode == 0:
        display_time()
    elif mode == 1:
        display_calendar()
    elif mode == 2:
        display_alarm()
    alarm_status = alarm_hour == hour and alarm_minute == minute
    set_model()
    await asyncio.sleep(0.05)
        
loop = asyncio.get_event_loop()
loop.create_task(alarm_test())
loop.create_task(display())
loop.run_forever()
  • 0
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
使用ESP8266和OLED 1306显示屏制作网络时钟一个很有趣的项目。下面是一些步骤来帮助你实现它: 1. 硬件准备: - ESP8266开发板:你可以选择NodeMCU或者Wemos D1 mini等。 - OLED 1306显示屏:确保你有一个兼容I2C接口的OLED 1306显示屏。 - 杜邦线:用于连接ESP8266和OLED显示屏。 2. 软件准备: - Arduino IDE:确保你已经安装了Arduino IDE,并正确设置了ESP8266开发板的支持。 - Adafruit SSD1306库:在Arduino IDE中安装Adafruit SSD1306库,用于控制OLED显示屏。 3. 连接: - 连接ESP8266和OLED显示屏。将ESP8266的SDA引脚连接到OLED显示屏的SDA引脚,将ESP8266的SCL引脚连接到OLED显示屏的SCL引脚。 4. 编程: - 打开Arduino IDE,创建一个新的Arduino项目。 - 导入Adafruit SSD1306库:在Arduino IDE中选择“工具”->“库管理器”,搜索并安装“Adafruit SSD1306”库。 - 编写代码:使用以下代码作为起点,你可以自定义它来满足你的需求。 ```cpp #include <Wire.h> #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> #define OLED_RESET 0 // OLED显示屏复位引脚 Adafruit_SSD1306 display(OLED_RESET); void setup() { // 初始化OLED显示屏 display.begin(SSD1306_SWITCHCAPVCC, 0x3C); // 传入OLED地址 display.clearDisplay(); display.setTextColor(WHITE); } void loop() { display.clearDisplay(); // 获取当前时间 int hours = hour(); int minutes = minute(); int seconds = second(); // 在OLED上显示时间 display.setTextSize(2); display.setCursor(0, 0); display.print(hours); display.print(":"); if (minutes < 10) display.print("0"); display.print(minutes); display.print(":"); if (seconds < 10) display.print("0"); display.println(seconds); display.display(); delay(1000); // 更新时间间隔 } ``` 5. 上传代码: - 连接ESP8266到电脑,并确保选择了正确的开发板和端口。 - 编译并上传代码到ESP8266开发板。 这样,你的ESP8266和OLED 1306显示屏网络时钟就完成了。它会通过无线网络连接获取当前时间,并在OLED显示屏上实时显示。你还可以根据需要进行更多的定制和功能扩展。祝你成功!

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值