图片
查询原理:象python字典一一对应一样,生成一个与点阵字库存储顺序相对应的ascii字符串数组A。要显示的字符B先遍历数组A,找到此B在A中的下标c,再用c去点阵数组中取下标为c的点阵。
#include "driver/spi_master.h"
#include "driver/gpio.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "string.h"
#include "driver/i2c.h"
#include "esp_rom_sys.h"
#include "sdkconfig.h"
#include <stdio.h>
#include "esp_system.h"
#include "esp_log.h"
//------------------------------------------
#define I2C_MASTER_SCL_IO 14
#define I2C_MASTER_SDA_IO 26
#define I2C_MASTER_NUM I2C_NUM_0
#define I2C_MASTER_FREQ_HZ 100000
#define I2C_MASTER_TX_BUF_DISABLE 0
#define I2C_MASTER_RX_BUF_DISABLE 0
#define DS3231_ADDRESS 0x68 // 68
//--------------------------------------
#define PIN_NUM_MOSI 2
#define PIN_NUM_CLK 15
#define PIN_NUM_CS 5
#define PIN_NUM_DC 19
#define PIN_NUM_RST 18
//--------------------------------------------------------------------------
void i2c_master_init()
{
i2c_config_t conf = {
.mode = I2C_MODE_MASTER,
.sda_io_num = I2C_MASTER_SDA_IO,
.sda_pullup_en = GPIO_PULLUP_ENABLE,
.scl_io_num = I2C_MASTER_SCL_IO,
.scl_pullup_en = GPIO_PULLUP_ENABLE,
.master.clk_speed = I2C_MASTER_FREQ_HZ,
};
ESP_ERROR_CHECK(i2c_param_config(I2C_MASTER_NUM, &conf));
ESP_ERROR_CHECK(i2c_driver_install(I2C_MASTER_NUM, conf.mode, 0, 0, 0));
}
uint8_t dec_to_bcd(uint8_t val)
{
return ((val / 10 * 16) + (val % 10));
}
uint8_t bcd_to_dec(uint8_t val)
{
return ((val / 16 * 10) + (val % 16));
}
esp_err_t ds3231_set_time(uint8_t sec, uint8_t min, uint8_t hour, uint8_t day, uint8_t date, uint8_t month, uint8_t year)
{
uint8_t time_data[7] = {dec_to_bcd(sec), dec_to_bcd(min), dec_to_bcd(hour), dec_to_bcd(day), dec_to_bcd(date), dec_to_bcd(month), dec_to_bcd(year)};
i2c_cmd_handle_t cmd = i2c_cmd_link_create();
i2c_master_start(cmd);
i2c_master_write_byte(cmd, (DS3231_ADDRESS << 1) | I2C_MASTER_WRITE, true);
i2c_master_write_byte(cmd, 0x00, true);
i2c_master_write(cmd, time_data, sizeof(time_data), true);
i2c_master_stop(cmd);
esp_err_t ret = i2c_master_cmd_begin(I2C_MASTER_NUM, cmd, 1000 / portTICK_PERIOD_MS);
i2c_cmd_link_delete(cmd);
return ret;
}
//---------------------------------------------------------------------------------
//-----------------------------------------------------------
spi_device_handle_t spi;
void spi_init() {
spi_bus_config_t buscfg = {
.mosi_io_num = PIN_NUM_MOSI,
.miso_io_num = -1,
.sclk_io_num = PIN_NUM_CLK,
.quadwp_io_num = -1,
.quadhd_io_num = -1,
.max_transfer_sz = 4096,
};
spi_bus_initialize(HSPI_HOST, &buscfg, 1);
spi_device_interface_config_t devcfg = {
.clock_speed_hz = 25 * 1000 * 1000, // 10 MHz
.mode = 0, // SPI mode 0
.spics_io_num = PIN_NUM_CS, // CS pin
.queue_size = 7,
};
spi_bus_add_device(HSPI_HOST, &devcfg, &spi);
}
void st7735_send_cmd(uint8_t cmd) {
gpio_set_level(PIN_NUM_DC, 0); // Command mode
spi_transaction_t t;
memset(&t, 0, sizeof(t));
t.length = 8;
t.tx_buffer = &cmd;
spi_device_transmit(spi, &t);
}
void st7735_send_data(uint8_t data) {
gpio_set_level(PIN_NUM_DC, 1); // Data mode
spi_transaction_t t;
memset(&t, 0, sizeof(t));
t.length = 8;
t.tx_buffer = &data;
spi_device_transmit(spi, &t);
}
void st7735_reset() {
gpio_set_level(PIN_NUM_RST, 0);
vTaskDelay(1 / portTICK_PERIOD_MS);
gpio_set_level(PIN_NUM_RST, 1);
vTaskDelay(200 / portTICK_PERIOD_MS);
}
void st7735_init() {
// Reset the display
st7735_reset();
// Initialization commands for ST7735S
st7735_send_cmd(0x01); // Software reset
vTaskDelay(150 / portTICK_PERIOD_MS);
st7735_send_cmd(0x11); // Sleep out
vTaskDelay(120 / portTICK_PERIOD_MS);
st7735_send_cmd(0xB1);
st7735_send_data(0x01);
st7735_send_data(0x2c);
st7735_send_data(0x2D);
st7735_send_cmd(0xB2);
st7735_send_data(0x01);
st7735_send_data(0x2c);
st7735_send_data(0x2D);
st7735_send_cmd(0xB3);
st7735_send_data(0x01);
st7735_send_data(0x2c);
st7735_send_data(0x2D);
st7735_send_data(0x01);
st7735_send_data(0x2c);
st7735_send_data(0x2D);
st7735_send_cmd(0xB4);
st7735_send_data(0x00);
st7735_send_cmd(0xc0);
st7735_send_data(0xa2);
st7735_send_data(0x02);
st7735_send_data(0x84);
st7735_send_cmd(0xc1);
st7735_send_data(0xc5);
st7735_send_cmd(0xc2);
st7735_send_data(0x0d);
st7735_send_cmd(0xc3);
st7735_send_data(0x8d);
st7735_send_data(0x2a);
st7735_send_cmd(0xc4);
st7735_send_data(0x8d);
st7735_send_data(0xee);
st7735_send_cmd(0xc5);
st7735_send_data(0x0e);
st7735_send_cmd(0x36);
st7735_send_data(0b01000000); //40
st7735_send_cmd(0xe0);
st7735_send_data(0x0f);
st7735_send_data(0x1a);
st7735_send_data(0x0f);
st7735_send_data(0x18);
st7735_send_data(0x2f);
st7735_send_data(0x28);
st7735_send_data(0x20);
st7735_send_data(0x22);
st7735_send_data(0x1f);
st7735_send_data(0x1b);
st7735_send_data(0x23);
st7735_send_data(0x37);
st7735_send_data(0x00);
st7735_send_data(0x07);
st7735_send_data(0x02);
st7735_send_data(0x10);
st7735_send_cmd(0xe1);
st7735_send_data(0x0f);
st7735_send_data(0x1b);
st7735_send_data(0x0f);
st7735_send_data(0x17);
st7735_send_data(0x33);
st7735_send_data(0x2c);
st7735_send_data(0x29);
st7735_send_data(0x2e);
st7735_send_data(0x30);
st7735_send_data(0x30);
st7735_send_data(0x39);
st7735_send_data(0x3f);
st7735_send_data(0x00);
st7735_send_data(0x07);
st7735_send_data(0x03);
st7735_send_data(0x10);
st7735_send_cmd(0x2a);
st7735_send_data(0x00);
st7735_send_data(0x00);
st7735_send_data(0x00);
st7735_send_data(127);
st7735_send_cmd(0x2b);
st7735_send_data(0x00);
st7735_send_data(0x00);
st7735_send_data(0x00);
st7735_send_data(160);
st7735_send_cmd(0xf0);
st7735_send_data(0x01);
st7735_send_cmd(0xf6);
st7735_send_data(0x00);
st7735_send_cmd(0x3a);
st7735_send_data(0x05);
st7735_send_cmd(0x29); // Display on
vTaskDelay(100 / portTICK_PERIOD_MS);
}
void qp(uint8_t xs, uint8_t xe,uint8_t ys,uint8_t ye) {
// Set 列
st7735_send_cmd(0x2A);
st7735_send_data(0x00);
st7735_send_data(xs);
st7735_send_data(0x00);
st7735_send_data(xe);
// Set 行
st7735_send_cmd(0x2B);
st7735_send_data(0x00);
st7735_send_data(ys);
st7735_send_data(0x00);
st7735_send_data(ye);
// Write memory
st7735_send_cmd(0x2C);
}
void cls(){
qp(0,127,0,159); // lcd 全屏刷成白屏
for (uint16_t a = 0; a < 159; a++) {
for(uint8_t b=0;b<127;b++){
st7735_send_data(0xff);
st7735_send_data(0xff);
}
}
}
uint8_t font[][8] ={
{0x1C, 0x22, 0x26, 0x2A, 0x32, 0x22, 0x1C, 0x00}, // '0'
{0x04, 0x0C, 0x04, 0x04, 0x04, 0x04, 0x0E, 0x00}, // 数字 '1'
{0x0E, 0x11, 0x01, 0x06, 0x08, 0x10, 0x1F, 0x00 }, // 2
{0x1C, 0x22, 0x02, 0x1C, 0x02, 0x22, 0x1C, 0x00}, // '3'
{0x08, 0x18, 0x28, 0x48, 0x7E, 0x08, 0x08, 0x00}, // '4'
{0x3E, 0x20, 0x3E, 0x02, 0x02, 0x22, 0x1C, 0x00}, // '5'
{0x1C, 0x22, 0x20, 0x3C, 0x22, 0x22, 0x1C, 0x00}, // '6'
{0x3E, 0x02, 0x04, 0x08, 0x10, 0x20, 0x20, 0x00}, // '7'
{0x1C, 0x22, 0x22, 0x1C, 0x22, 0x22, 0x1C, 0x00}, // '8'
{0x1C, 0x22, 0x22, 0x1E, 0x02, 0x22, 0x1C, 0x00}, // '9'
{0x00, 0x18, 0x18, 0x00, 0x00, 0x18, 0x18, 0x00}, // :
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, //空格
//--------------
{0x00,0x00,0x00,0xff,0x00,0x00,0x00,0x00}, //中间短横线-
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xff}, //下横线_
{ 0x00,0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x30}, //逗号
{ 0x3C, 0x42, 0x02, 0x0C, 0x10, 0x10, 0x00,0x10},//问号
{ 0x10, 0x10, 0x10, 0x10, 0x10,0x00,0x10, 0x00},//感叹号
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18,0x18},//句号
{ 0x00, 0x00, 0x18, 0x18, 0x00, 0x18, 0x18, 0x30},// 分号
//-------------------
{0x00,0x00, 0x3C, 0x02, 0x3E, 0x42, 0x3E, 0x00 }, //a
{ 0x40, 0x40, 0x7C, 0x42, 0x42, 0x42, 0x7C, 0x00},//
{0x00, 0x00, 0x3E, 0x40, 0x40, 0x40, 0x3E, 0x00},//
{0x02, 0x02, 0x3E, 0x42, 0x42, 0x42, 0x3E, 0x00},//
{0x00, 0x00, 0x3C, 0x42, 0x7E, 0x40, 0x3C, 0x00},//
{0x1C, 0x22, 0x20, 0x7C, 0x20, 0x20, 0x20, 0x00},//
{0x00, 0x00, 0x3E, 0x42, 0x3E, 0x02, 0x3C, 0x00},//
{0x40, 0x40, 0x7C, 0x42, 0x42, 0x42, 0x42, 0x00},//
{0x00, 0x10, 0x00, 0x30, 0x10, 0x10,0x10, 0x00},//
{0x00, 0x08, 0x00, 0x08, 0x08, 0x48, 0x30, 0x00},//
{0x40, 0x44, 0x48,0x70, 0x48, 0x44, 0x42, 0x00},
{0x30, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x00},//
{0x00, 0x00, 0x66, 0x5A, 0x42, 0x42, 0x42, 0x00},//
{ 0x00,0x00, 0x7C, 0x42, 0x42, 0x42, 0x42, 0x00},//
{0x00, 0x00, 0x3C, 0x42, 0x42, 0x42, 0x3C, 0x00},//
{0x00, 0x00, 0x7C, 0x42, 0x42, 0x7C, 0x40, 0x40},// *
{0x00, 0x00, 0x3E, 0x42, 0x42, 0x3E, 0x02, 0x02},// *
{0x00, 0x00, 0x7C, 0x42, 0x40, 0x40, 0x40, 0x00},//
{0x00, 0x00, 0x3C, 0x40, 0x3C,0x02, 0x7C, 0x00},//
{0x00, 0x10,0x7C, 0x10, 0x10, 0x12, 0x0C, 0x00},//
{0x00, 0x00, 0x42, 0x42, 0x42, 0x42, 0x3E, 0x00},//
{ 0x00, 0x00,0x42, 0x42, 0x24, 0x24, 0x18, 0x00},//
{0x00, 0x00, 0x42, 0x42, 0x5A, 0x5A, 0x24, 0x00},//
{0x00, 0x00, 0x42, 0x24, 0x18, 0x24, 0x42, 0x00},//
{0x00, 0x00, 0x42, 0x42, 0x3E, 0x02, 0x3C, 0x00},//
{0x00, 0x00, 0x7E, 0x04, 0x18, 0x20, 0x7E, 0x00},// z
};
char asc[]={0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,':',0x20,
'-','_',',','?','!','.',';',
'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z',
};
void xs(uint8_t ls,uint8_t le,uint8_t hs,uint8_t he,uint8_t *ci,uint8_t ys){
qp(127-le,127-ls,hs,he);
for (uint16_t a = 0; a < 8; a++) {
for(uint8_t b=0;b<8;b++){
if((int)(((ci[a]>>b)&0b00000001))==1){ //如果像素点为1
st7735_send_data(ys);
st7735_send_data(0x00);
}else{
st7735_send_data(0xff);
st7735_send_data(0xff);
}
}
}
}
void hxs(uint8_t lc,uint8_t hc,char *i,size_t cd,uint8_t ys){ //在一行中显示字符
uint16_t len=(int)cd;
for(uint8_t a=0;a<len;a++){
uint8_t ls=lc;
uint8_t le=ls+7;
uint8_t hs=hc;
uint8_t he=hs+7;
int asc_len=(int)sizeof(asc);
for(int n=0;n<asc_len;n++){
if(memcmp(&i[a],&asc[n],1)==0){ //查表
xs(ls,le,hs,he,&font[n][0],ys);
lc=le; //列自动加7,相当于光标后移一个字符
break;
}
}
}
}
//=========================================================================================================
void app_main() {
i2c_master_init();
gpio_set_direction(PIN_NUM_DC, GPIO_MODE_OUTPUT);
gpio_set_direction(PIN_NUM_RST, GPIO_MODE_OUTPUT);
spi_init();
st7735_init(); //lcd 初始化后是花屏
cls();
uint8_t data[7]; // 0-255 无符号数组
char i[8]; //字符串数组
for(;;){
// uint8_t i[]={6,1,8,3,7,3,6,7,8,7,1,7};
i2c_cmd_handle_t cmd = i2c_cmd_link_create();
i2c_master_start(cmd);
i2c_master_write_byte(cmd, (DS3231_ADDRESS << 1) | I2C_MASTER_WRITE, true);
i2c_master_write_byte(cmd, 0x00, true);
i2c_master_start(cmd);
i2c_master_write_byte(cmd, (DS3231_ADDRESS << 1) | I2C_MASTER_READ, true);
i2c_master_read(cmd,data, sizeof(data), I2C_MASTER_LAST_NACK);
i2c_master_stop(cmd);
esp_err_t ret = i2c_master_cmd_begin(I2C_MASTER_NUM, cmd, 1000 / portTICK_PERIOD_MS);
i2c_cmd_link_delete(cmd);
if (ret == ESP_OK) {
uint8_t so=data[2]; //时
uint8_t soh=(so>>4)&0b00001111;
i[0]=soh+0x30; //转为ascii 字符
uint8_t sol=so&0b00001111;
i[1]=sol+0x30; //转为ascii 字符
i[2]=':';
uint8_t fo=data[1]; //分
uint8_t foh=(fo>>4)&0b00001111;
i[3]=foh+0x30;
uint8_t fol=fo&0b00001111;
i[4]=fol+0x30;
i[5]=':';
uint8_t mo=data[0]; //秒
uint8_t moh=(mo>>4)&0b00001111;
i[6]=moh+0x30;
uint8_t mol=mo&0b00001111;
i[7]=mol+0x30;
hxs(65,2,i,sizeof(i),0xf8);
char i2[]="1;42,5:7_8.?!7a bcde";
hxs(0,50,i2,sizeof(i2),0xf8);
vTaskDelay(pdMS_TO_TICKS(100));
}
}
}