768 views|2 replies

8

Posts

2

Resources
The OP
 

[Digi-Key Follow me Issue 2] + Submit Post: Perpetual Calendar Based on ESP32-S3 [Copy link]

 This post was last edited by liuvx on 2023-11-21 17:04

Recently, we have completed all the contents of this activity. The Adafruit ESP32-S3 TFT Feather development board used in this activity supports WiFi and Bluetooth functions and has a built-in high-definition TFT color display. We have completed tasks such as displaying Chinese on the screen, connecting to WiFi, driving RGB, and making a perpetual calendar.

Content 1: Demonstration Video

This time, we implemented a perpetual calendar based on ESP32-S3, which can connect to the Internet and display the current time, date, weather and temperature on the screen.

Digi-Key Electronics Follow me Second Phase Task - Digi-Key Electronics Follow me Second Phase Task - EEWORLD University
Content 2: Project Summary Report

Task 1: Control the screen to display Chinese

First, the effect diagram is presented here

Figure 1 Effect diagram

initial preparation work :

  1. Get the Adafruit ESP32-S3 TFT Feather development board, power it up, enter UF2 mode, and install the CircuitPython environment.
    CircuitPython firmware U F2 download page:
    Feather ESP32-S3 TFT Download (circuitpython.org)
  2. Drag the downloaded UF2 firmware directly into the disk that comes with the Adafruit ESP32-S3 TFT Feather and wait for it to restart automatically.
  3. When your screen looks like Figure 2, CircuitPython is installed .

figure 2

Officially begin :

Figure 3 CircuitPython

I use V Scode for configuration. You can install this plug-in first and then proceed with the following operations.

This task requires 3 libraries

We can execute this command in vscode

Then enter

After that, you can search and install the libraries you need.

When entering the command execution, enter

You can query the library you downloaded

This section also requires additional fonts

Font library link:

链接已隐藏,如需查看请登录或者注册

What I use is wenquanyi_13px.pcf. After downloading it, just drag it into the disk that comes with the development board.

Then the code part

This part is to import the necessary libraries

import board

import displayio

from adafruit_display_text import label, wrap_text_to_lines

from adafruit_bitmap_font import bitmap_font

Then set the screen parameters

display = board.DISPLAY
board.DISPLAY.brightness = 0.2  # 设置显示屏亮度为0.35
board.DISPLAY.rotation = 0  # 设置显示屏旋转为0度

Then set the characters to be displayed on the screen.

# 加载自定义字体文件
font = bitmap_font.load_font("wenquanyi_13px.pcf")

# 设置文本颜色
color = 0xFF0000  # 这里的颜色为红色

# 初始化文本变量
text_change = 0

# 创建显示组和文本标签
text_group = displayio.Group()
text_area = label.Label(font, text="test", color=color)  # 创建文本标签对象

text_area.x = 0  # 设置文本的X坐标
text_area.y = 55  # 设置文本的Y坐标
text_area.line_spacing = 0.5  # 设置文本行间距
text_area.scale = 2  # 设置文本放大倍数

# 设置文本内容
text_area.text = "WIFI:ESP\n密码:00000000"  # 这里设置文本内容
text_area.ass = "w"
text_group.append(text_area)  # 将文本标签添加到显示组中
display.show(text_group)  # 在显示设备上显示文本

Task 2: Connect to WiFi and create a hotspot

The requirement for this task is to complete the use of network functions, be able to create a hotspot and connect to WiFi.

And the code is relatively simple

Let's talk about connecting to WIFI first:

After we flash the firmware, we can see a settings.toml file in the disk. We only need to modify it to achieve WIFI connection

Then modify the code inside

#配置WIFI的ID
CIRCUITPY_WIFI_SSID = "Liuv"
#配置WiFi密码
CIRCUITPY_WIFI_PASSWORD = "12345678"
#配置网页工作流密码
CIRCUITPY_WEB_API_PASSWORD = "123456"
#配置网页工作流端口
CIRCUITPY_WEB_API_PORT = 80

After we connect to WIFI, the screen will display the IP address

Our WIFI is now connected.

Then turn on the hotspot

Import required libraries

import wifi

Then turn on the hotspot

wifi.radio.start_ap('ESP', '00000000')

Name and password.

mission completed

Task 3: Use of RGB lights

This task will use the RGB lights and buttons on the board.

I plan to use the time library to achieve the effect of switching colors every 0.5 seconds instead of using buttons to switch colors.

The RGB light model on the board is WS2812b, and you can use it using the neopixel library provided by Adafruit .

import neopixel

Import the time library

import time

Modify brightn to change the maximum brightness of the RGB light.

Then enter the loop

while True:
    
    pixel.brightness = 0.6
    pixel.fill((255, 0, 0))
    time.sleep(0.5)
    pixel.brightness = 0.5
    pixel.fill((0, 255, 0))
    time.sleep(0.5)
    pixel.brightness = 0.1
    pixel.fill((0, 0, 255))
    time.sleep(0.5)

middle

pixel.fill((255, 0, 0))

They are Red, Green, and Blue color controls respectively.

time.sleep(0.5)

Indicates a delay of 0.5s

After you burn the code, you can observe that RGB switches back and forth between red, green, and blue, and the brightness of each is different.

The complete code is as follows

import time
import board
import neopixel

pixel = neopixel.NeoPixel(board.NEOPIXEL, 1)#初始化rgb引脚

pixel.brightness = 0.6#更改亮度

while True:
    
    pixel.brightness = 0.6
    pixel.fill((255, 0, 0))
    time.sleep(0.5)
    pixel.brightness = 0.5
    pixel.fill((0, 255, 0))
    time.sleep(0.5)
    pixel.brightness = 0.1
    pixel.fill((0, 0, 255))
    time.sleep(0.5)

Now you have mastered the most basic control of RGB lights. Now let's see how to operate it with buttons.

When you use the buttons, you call the basic digital library

import digitalio

Then initialize the button

button = digitalio.DigitalInOut(board.BUTTON)
button.switch_to_input(pull=digitalio.Pull.UP)

Indicates pull-up input

Then enter the loop

while True:
    if not button.value:
        if n % 3 == 1:
            pixel.brightness = 0.6
            pixel.fill((255, 0, 0))
        elif n % 3 == 2:
            pixel.brightness = 0.5
            pixel.fill((0, 255, 0))
        elif n % 3 == 0:
            pixel.brightness = 0.3
            pixel.fill((0, 0, 255))
        n = n+1

Just writing it like this is effective, but it may not achieve the results we want.

Because the keys will vibrate when pressed, which will affect us.

Therefore, we need to add a delay function to eliminate jitter

while True:
    if not button.value:
         time.sleep(0.1)
         if not button.value:
            if n % 3 == 1:
                pixel.brightness = 0.6
                pixel.fill((255, 0, 0))
            elif n % 3 == 2:
                pixel.brightness = 0.5
                pixel.fill((0, 255, 0))
            elif n % 3 == 0:
                pixel.brightness = 0.3
                pixel.fill((0, 0, 255))
            n = n+1

In this way, we can achieve the desired effect.

The complete code is as follows

import time
import board
import neopixel
import digitalio
n = 0
button = digitalio.DigitalInOut(board.BUTTON)
button.switch_to_input(pull=digitalio.Pull.UP)

pixel = neopixel.NeoPixel(board.NEOPIXEL, 1)#初始化rgb引脚
pixel.brightness = 0.6#更改亮度

while True:
    if not button.value:
         time.sleep(0.1)
         if not button.value:
            if n % 3 == 1:
                pixel.brightness = 0.6
                pixel.fill((255, 0, 0))
            elif n % 3 == 2:
                pixel.brightness = 0.5
                pixel.fill((0, 255, 0))
            elif n % 3 == 0:
                pixel.brightness = 0.3
                pixel.fill((0, 0, 255))
            n = n+1
    else:
        pass
    
        

Task 4: Calendar and Clock

In this task, we need to display time and weather information on our screen.

First put a rendering

Let’s do it step by step

First, complete the text part

Screen display

You can check the previous task for the required library.

First set some basic parameters of the screen

# 设置板子的亮度和是否翻转
board.DISPLAY.brightness = 0.5  #
board.DISPLAY.rotation = 0  #
word_font = bitmap_font.load_font("wenquanyi_13px.pcf")

We can add a picture to this task to make it more beautiful

Need this library

import adafruit_imageload

Then import the picture, note that the picture needs to be in bmp format

# 引入图片
image, palette = adafruit_imageload.load(
    '/images/ysqd.bmp', bitmap=displayio.Bitmap, palette=displayio.Palette)
tile_grid = displayio.TileGrid(image, pixel_shader=palette)
group = displayio.Group()
group.append(tile_grid)

Then display other text, such as time, temperature, etc.

# 日期的设置
date = label.Label(word_font, text="test", color=0x000000)
date.x = 10  #
date.y = 20
date.scale = 2  #
group.append(date)

# 周几的设置
week = label.Label(word_font, text="周五", color=0x000000)
week.x = 120
week.y = 20
week.scale = 2
group.append(week)

# 时间的设置
timer = label.Label(word_font, text='10:17', color=0x779649)
timer.x = 15
timer.y = 65
timer.scale = 2  #
group.append(timer)

# 天气文字的设置
weather = label.Label(word_font, text='阴', color=0x3271ae)
weather.x = 10
weather.y = 110
weather.scale = 2  #
group.append(weather)

# 温度文字的设置
temperature = label.Label(word_font, text='10度-15度', color=0x3271ae)
temperature.x = 60
temperature.y = 110
temperature.scale = 2
group.append(temperature)

# 事实温度文字的设置
tem_now = label.Label(word_font, text='10度', color=0x3271ae)
tem_now.x = 150
tem_now.y = 65
tem_now.scale = 2
group.append(tem_now)

Finally, display it

board.DISPLAY.show(group)

WIFI CONNECTIVITY

Similar to before, configure ssid and password in the SETTING file

# 连接WIFI,若连接失败会报错
print("Connecting to", ssid)
wifi.radio.connect(ssid, password)
time.sleep(1)
print("Connected to", ssid)

The purpose of the 1s delay is to enable the subsequent operations to be performed after connecting to WiFi.

getting information

Related library introduction

adafruit_ntp

adafruit_requests

rtc

To get the weather, you need to return data from other places.

I use the Yike Cloud API here, which is more convenient and stable

Code section

# 周几文字的数据
def get_wday(week_today):
    if week_today == 0:
        return "周一"
    elif week_today == 1:
        return "周二"
    elif week_today == 2:
        return "周三"
    elif week_today == 3:
        return "周四"
    elif week_today == 4:
        return "周五"
    elif week_today == 5:
        return "周六"
    elif week_today == 6:
        return "周日"

Then use RTC to get the time

# 使用rtc
rtc.RTC().datetime = adafruit_ntp.NTP(socketpool.SocketPool(
    wifi.radio), tz_offset=8, server='ntp.aliyun.com').datetime

Get weather conditions from API

def get_weather():
    requests = adafruit_requests.Session(
        socketpool.SocketPool(wifi.radio), ssl.create_default_context())
    appid = os.getenv("appid")
    appsecret = os.getenv("appsecret")
    res = requests.get(
        'https://v0.yiketianqi.com/free/day?appid=%s&appsecret=%s&unescape=1&city=南阳' % (appid, appsecret)).json()
    return res['wea'], res['tem_night'], res['tem_day'], res['tem']

Note that the appid and appsecret here need to be obtained from Yike Cloud and written into the settings file

Otherwise, the temperature will not be obtained normally.

Get the information before looping again

# 获得时间
time_now = time.localtime()
timer.text = '%02d:%02d' % (time_now.tm_hour, time_now.tm_min)
date.text = '%d月%d日' % (time_now.tm_mon, time_now.tm_mday)
week.text = get_wday(time_now.tm_wday)
wea, tem_night, tem_day, tem = get_weather()
weather.text = wea
temperature.text = '%s℃-%s℃' % (tem_night, tem_day)
tem_now.text = '%s度' % (tem)

After entering the loop, the speed of obtaining information needs to be limited

while True:
    time_now = time.localtime()
    timer.text = '%02d:%02d' % (time_now.tm_hour, time_now.tm_min)
    if time_now.tm_min == 0:
        wea, tem_night, tem_day, tem = get_weather()
        weather.text = wea
        temperature.text = '%d℃-%d℃' % (tem_night, tem_day)
        tem_now.text = '%s度' % (tem)
    if time_now.tm_hour == 0:
        date.text = '%d月%d日' % (time_now.tm_mon, time_now.tm_mday)
        week.text = get_wday(time_now.tm_wday)

    pass

That's it.

The complete code is as follows

import board
import displayio
import os
import wifi
import ssl
import socketpool
import adafruit_ntp
import rtc
import time
import ipaddress
import adafruit_requests
import adafruit_imageload
from adafruit_display_text import label, wrap_text_to_lines
from adafruit_bitmap_font import bitmap_font
# 获得WIFI名字和密码
ssid = os.getenv("CIRCUITPY_WIFI_SSID")
password = os.getenv("CIRCUITPY_WIFI_PASSWORD")


# 周几文字的数据
def get_wday(week_today):
    if week_today == 0:
        return "周一"
    elif week_today == 1:
        return "周二"
    elif week_today == 2:
        return "周三"
    elif week_today == 3:
        return "周四"
    elif week_today == 4:
        return "周五"
    elif week_today == 5:
        return "周六"
    elif week_today == 6:
        return "周日"


# 连接WIFI,若连接失败会报错
print("Connecting to", ssid)
wifi.radio.connect(ssid, password)
time.sleep(10)
print("Connected to", ssid)
# 获得天气情况


def get_weather():
    requests = adafruit_requests.Session(
        socketpool.SocketPool(wifi.radio), ssl.create_default_context())
    appid = os.getenv("appid")
    appsecret = os.getenv("appsecret")
    res = requests.get(
        'https://v0.yiketianqi.com/free/day?appid=%s&appsecret=%s&unescape=1&city=南阳' % (appid, appsecret)).json()
    return res['wea'], res['tem_night'], res['tem_day'], res['tem']


# 使用rtc
rtc.RTC().datetime = adafruit_ntp.NTP(socketpool.SocketPool(
    wifi.radio), tz_offset=8, server='ntp.aliyun.com').datetime
# 引入图片
image, palette = adafruit_imageload.load(
    '/images/ysqd.bmp', bitmap=displayio.Bitmap, palette=displayio.Palette)
tile_grid = displayio.TileGrid(image, pixel_shader=palette)
group = displayio.Group()
group.append(tile_grid)
# 设置板子的亮度和是否翻转
board.DISPLAY.brightness = 0.5  #
board.DISPLAY.rotation = 0  #
word_font = bitmap_font.load_font("wenquanyi_13px.pcf")

# 日期的设置
date = label.Label(word_font, text="test", color=0x000000)
date.x = 10  #
date.y = 20
date.scale = 2  #
group.append(date)

# 周几的设置
week = label.Label(word_font, text="周五", color=0x000000)
week.x = 120
week.y = 20
week.scale = 2
group.append(week)

# 时间的设置
timer = label.Label(word_font, text='10:17', color=0x779649)
timer.x = 15
timer.y = 65
timer.scale = 2  #
group.append(timer)

# 天气文字的设置
weather = label.Label(word_font, text='阴', color=0x3271ae)
weather.x = 10
weather.y = 110
weather.scale = 2  #
group.append(weather)

# 温度文字的设置
temperature = label.Label(word_font, text='10度-15度', color=0x3271ae)
temperature.x = 60
temperature.y = 110
temperature.scale = 2
group.append(temperature)

# 事实温度文字的设置
tem_now = label.Label(word_font, text='10度', color=0x3271ae)
tem_now.x = 150
tem_now.y = 65
tem_now.scale = 2
group.append(tem_now)
# 获得时间
time_now = time.localtime()
timer.text = '%02d:%02d' % (time_now.tm_hour, time_now.tm_min)
date.text = '%d月%d日' % (time_now.tm_mon, time_now.tm_mday)
week.text = get_wday(time_now.tm_wday)
wea, tem_night, tem_day, tem = get_weather()
weather.text = wea
temperature.text = '%s℃-%s℃' % (tem_night, tem_day)
tem_now.text = '%s度' % (tem)
board.DISPLAY.show(group)


while True:
    time_now = time.localtime()
    timer.text = '%02d:%02d' % (time_now.tm_hour, time_now.tm_min)
    if time_now.tm_min == 0:
        wea, tem_night, tem_day, tem = get_weather()
        weather.text = wea
        temperature.text = '%d℃-%d℃' % (tem_night, tem_day)
        tem_now.text = '%s度' % (tem)
    if time_now.tm_hour == 0:
        date.text = '%d月%d日' % (time_now.tm_mon, time_now.tm_mday)
        week.text = get_wday(time_now.tm_wday)

    pass

Content 3: Task Summary

This activity was my real contact with ESP32. Before that, I had only been exposed to MCUs such as STM32 and 51. Through this activity, I learned a lot about how to use ESP32 and how to operate CircuitPython. I realized that ESP32 is indeed simpler to use than 32 in some places. This mission brought me into a new field of embedded systems, trained my skills, and supplemented my previous half-knowledge. I gained a lot. I am very grateful to Digi-Key and EE for their support for this activity.

Code resource link

follow me The second full set of code - Embedded development related materials download - EEWORLD Download Center

This post is from DigiKey Technology Zone

Latest reply

Thanks for the technical sharing provided by the host. I will collect and study it first and then express my personal opinion.   Details Published on 2023-11-23 18:12
 
 

6593

Posts

0

Resources
2
 

Tested and organized very well, learned a lot

This post is from DigiKey Technology Zone
 
 
 

731

Posts

4

Resources
3
 

Thanks for the technical sharing provided by the host. I will collect and study it first and then express my personal opinion.


This post is from DigiKey Technology Zone
 
 
 

Guess Your Favourite
Just looking around
Find a datasheet?

EEWorld Datasheet Technical Support

EEWorld
subscription
account

EEWorld
service
account

Automotive
development
circle

Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号
快速回复 返回顶部 Return list