【AT-START-F425测评】No.07 8x8双色点阵屏走马灯
## 前言
自从上次折腾了SLCD之后,发现折腾硬件也并不是那么复杂,最关键的是竟然可以免费打板(真是发现了新大陆)。
这次折腾下一块双色8X8点阵屏,这个屏是eeworld的网友打包便宜转给我的。
在网上找了一个图,大概是这样子的:
!(https://s2.loli.net/2022/06/05/n6EdpiLr81hSmjq.jpg)
## 关于双色点阵
规格书(供参考):
!(https://s2.loli.net/2022/06/05/hev3VszFItEfopX.jpg)
它对应的原理图如下:
!(https://s2.loli.net/2022/06/05/SDY7zfrNPVvpiaj.jpg)
原理图说明:
- 1,2,3,4,21,22,23,24这8个管脚控制行。
- 5,6,7,8,9,10,11,12这8个管脚控制列的绿灯。
- 13,14,15,16,17,18,19,20这8个管脚控制列的红灯。
## 原理图设计
一般驱动这种段码LED需要用到74HC595,我花了几块钱买了20片TM74HC595,是天微出品的。
!(https://s2.loli.net/2022/06/05/sPJQi3rA97qnL4u.jpg)
这个片子的具体可以去参考芯片手册,它的基本功能就是串转并。
具体到我们的需求,由于双色点阵共用24个数据,那么需要3片TM74HC595。
至于是如何连法,当我们理解了串转并的原理后,那么,三并,两并一串,两串一并或者三串都是可以的,其差异就是对外接口和程序处理上的差异。
我们这里采用常规的两串一并,两串对应的列数据,一并对应的行数据。
其原理图如下所示:
![双色点阵驱动原理图](https://s2.loli.net/2022/06/05/hBRNXEpSMADbyVq.jpg)
![双色点阵驱动原理图](https://s2.loli.net/2022/06/05/7AojmEMVFK4S6qW.png)
对应的打板如下:
![双色点阵驱动板](https://s2.loli.net/2022/06/05/cXVNGtya8nKhkjD.png)
## 程序设计
## 74HC595的驱动
```
//#define LED_USING_SPI
#if defined(SPI1_FOR_LED)
/* SPI1:PB13-SCK-SPI_SCK PB14-CE-SPI_MISO PB15-DATA-SPI_MOSI */
#define CURRENT_SPI SPI1
#define CURRENT_SPI_RCU RCU_SPI1
#define LED_RCU CRM_GPIOB_PERIPH_CLOCK
#define LED_GPIO GPIOB
#define LED_CTRL_SCK GPIO_PINS_3
#define LED_CTRL_RCK GPIO_PINS_4
#define LED_CTRL_SI GPIO_PINS_5
#define LED_DATA_SCK GPIO_PINS_13
#define LED_DATA_RCK GPIO_PINS_14
#define LED_DATA_SI GPIO_PINS_15
#define ROW_OFF_ALL 0x00
#define ROW_ON(row) (0x80>>row)
#ifdef LED_USING_SPI
#else
#define LED_CTRL_SCK_HIGH gpio_bits_set(LED_GPIO, LED_CTRL_SCK);
#define LED_CTRL_SCK_LOW gpio_bits_reset(LED_GPIO, LED_CTRL_SCK);
#define LED_CTRL_RCK_HIGH gpio_bits_set(LED_GPIO, LED_CTRL_RCK);
#define LED_CTRL_RCK_LOW gpio_bits_reset(LED_GPIO, LED_CTRL_RCK);
#define LED_CTRL_SI_HIGH gpio_bits_set(LED_GPIO, LED_CTRL_SI);
#define LED_CTRL_SI_LOW gpio_bits_reset(LED_GPIO, LED_CTRL_SI);
#define LED_DATA_SCK_HIGH gpio_bits_set(LED_GPIO, LED_DATA_SCK);
#define LED_DATA_SCK_LOW gpio_bits_reset(LED_GPIO, LED_DATA_SCK);
#define LED_DATA_RCK_HIGH gpio_bits_set(LED_GPIO, LED_DATA_RCK);
#define LED_DATA_RCK_LOW gpio_bits_reset(LED_GPIO, LED_DATA_RCK);
#define LED_DATA_SI_HIGH gpio_bits_set(LED_GPIO, LED_DATA_SI);
#define LED_DATA_SI_LOW gpio_bits_reset(LED_GPIO, LED_DATA_SI);
#endif
void spi5_init(){}
#ifdef LED_USING_SPI
void spi1_init()
{
}
#else
void spi1_init() {
gpio_init_output_mode(LED_RCU, LED_GPIO, LED_CTRL_SCK,GPIO_DRIVE_STRENGTH_MODERATE, 0);
gpio_init_output_mode(LED_RCU, LED_GPIO, LED_CTRL_RCK,GPIO_DRIVE_STRENGTH_MODERATE, 0);
gpio_init_output_mode(LED_RCU, LED_GPIO, LED_CTRL_SI,GPIO_DRIVE_STRENGTH_STRONGER, 0);
gpio_init_output_mode(LED_RCU, LED_GPIO, LED_DATA_SCK,GPIO_DRIVE_STRENGTH_MODERATE, 0);
gpio_init_output_mode(LED_RCU, LED_GPIO, LED_DATA_RCK,GPIO_DRIVE_STRENGTH_MODERATE, 0);
gpio_init_output_mode(LED_RCU, LED_GPIO, LED_DATA_SI,GPIO_DRIVE_STRENGTH_STRONGER, 0);
}
void led_74hc595_ctrl_send_byte(uint8_t data)
{
uint8_t i = 0;
LED_CTRL_RCK_LOW;
for(i = 0; i < 8; i++)
{
if(data & 0x80)
{
LED_CTRL_SI_HIGH;
}
else
{
LED_CTRL_SI_LOW;
}
data<<=1;
LED_CTRL_SCK_LOW;
LED_CTRL_SCK_HIGH;
}
LED_CTRL_RCK_HIGH;
delay_us(10);
LED_CTRL_RCK_LOW;
}
void led_74hc595_data_send_word(uint16_t data)
{
uint8_t i = 0;
LED_DATA_RCK_LOW;
for(i = 0; i < 16; i++)
{
LED_DATA_SCK_LOW;
if(data & 0x8000)
{
LED_DATA_SI_HIGH;
}
else
{
LED_DATA_SI_LOW;
}
data<<=1;
LED_DATA_SCK_HIGH;
}
LED_DATA_RCK_HIGH;
delay_us(10);
LED_DATA_RCK_LOW;
}
```
## 灯的控制
先把基本原理说一下。
参考上面的原理图,假设我们需要把标号为1脚的红灯和绿灯点亮,那么:
控制脚:1脚=1,其他脚=0(对应QCON7=1,QCON6-0=0,D1=0x80)
数据脚:5脚和20脚=0,其他脚=1(对应D2=0x7F,D3=0x7F)
其控制逻辑是:X3发0x80,接着X4发0x7F7F。
基于这个思路,走马灯的程序如下:
```
static uint16_t data_scan_mode[] = {0x7F7F, 0xBFBF, 0xDFDF, 0xEFEF, 0xF7F7, 0xFBFB, 0xFDFD, 0xFEFE};
void led_flash_test(uint8_t COUNT)
{
uint8_t L1[] = {0, 1, 2, 3, 4, 5, 6, 7};
uint8_t L2[] = {7, 6, 5, 4, 3, 2, 1, 0};
static uint8_t count = 0;
static uint8_t row_count = 0;
static uint8_t row_flag = 0;
uint8_t col_count = 0;
static uint8_t col_index = 0;
if (count++ > COUNT)
{
count = 0;
if (row_count%2)
{
col_count = L2;
}
else
{
col_count = L1;
}
printf("row = %d, col = %d \n", row_count, col_count);
led_74hc595_ctrl_send_byte(ROW_ON(row_count));
led_74hc595_data_send_word(data_scan_mode);
if (col_index++ == 7)
{
col_index = 0;
if (row_flag)
{
row_count--;
}
else
{
row_count++;
}
if (row_count >= 7)
{
row_flag = 1;
}
else if (row_count <= 0)
{
row_flag = 0;
}
}
}
}
```
## 显示心形
![心形示意图](https://s2.loli.net/2022/06/05/JBzxfLpCFTRksdH.jpg)
![心形结果](https://s2.loli.net/2022/06/05/qNtYKuxCHb8eEUM.jpg)
```
static uint16_t data_heart_RED_mode[] = {0xFFFF, 0xFFE7, 0xFFC3, 0xFF81, 0xFF00, 0xFF00, 0xFF99, 0xFFFF};
void led_heart_test(uint8_t COUNT)
{
static uint8_t count = 0;
static uint8_t col_count = 0;
if (count++ > COUNT)
{
count = 0;
led_74hc595_ctrl_send_byte(ROW_ON(col_count));
led_74hc595_data_send_word(data_heart_RED_mode);
if (col_count > 7 )
{
col_count = 0;
}
}
}
```
## 视频
![走马灯效果](https://s2.loli.net/2022/06/05/3T5WP7BqAZEXbGd.gif)
![心形结果](https://s2.loli.net/2022/06/05/qNtYKuxCHb8eEUM.jpg)
![](https://s2.loli.net/2022/03/28/xnJPMjvEfwHs1IS.gif)
感谢分享,项目结束还继续发帖,值得点赞!
页:
[1]