STM32CubeMX TM1637驱动数码管

一、TM1637简介    

        TM1637 是一种带键盘扫描接口的LED(发光二极管显示器)驱动控制专用电路,内部集成有MCU 数字接口、数据锁存器、LED 高压驱动、键盘扫描等电路。本产品性能优良,质量可靠。主要应用于电磁炉、 微波炉及小家电产品的显示屏驱动。采用DIP/SOP20的封装形式。

 采用功率CMOS 工艺
 显示模式(8 段×6 位),支持共阳数码管输出
 键扫描(8×2bit),增强型抗干扰按键识别电路
 辉度调节电路(占空比 8 级可调)
 两线串行接口(CLK,DIO)
 振荡方式:内置RC 振荡(450KHz+5%)
 内置上电复位电路
 内置自动消隐电路
 封装形式:DIP20/SOP20

        微处理器的数据通过两线总线接口和 TM1637 通信,在输入数据时当 CLK 是高电平时,DIO 上的信号 必须保持不变;只有 CLK 上的时钟信号为低电平时,DIO 上的信号才能改变。数据输入的开始条件是 CLK 为高电平时,DIO 由高变低;结束条件是 CLK 为高时,DIO 由低电平变为高电平。 

        TM1637 的数据传输带有应答信号 ACK,当传输数据正确时,会在第八个时钟的下降沿,芯片内部会 产生一个应答信号 ACK 将 DIO 管脚拉低,在第九个时钟结束之后释放 DIO 口线。

STM32CubeMX TM1637驱动数码管_第1张图片

二、CubeMX配置

时钟配置

STM32CubeMX TM1637驱动数码管_第2张图片

定时器4配置,产生us延时

STM32CubeMX TM1637驱动数码管_第3张图片

引脚配置这里配置PB0为TM1637_CLK,PB1为TM1637_SDA STM32CubeMX TM1637驱动数码管_第4张图片

生成代码

STM32CubeMX TM1637驱动数码管_第5张图片 三、程序代码

tm1637.h


#ifndef __TM1637_H
#define __TM1637_H

#include "main.h"

#define TM1637_CLK_H()	HAL_GPIO_WritePin(GPIOB,TM1637_CLK_Pin,GPIO_PIN_SET)
#define TM1637_CLK_L()	HAL_GPIO_WritePin(GPIOB,TM1637_CLK_Pin,GPIO_PIN_RESET)
#define TM1637_SDA_H()	HAL_GPIO_WritePin(GPIOB,TM1637_SDA_Pin,GPIO_PIN_SET)
#define TM1637_SDA_L()	HAL_GPIO_WritePin(GPIOB,TM1637_SDA_Pin,GPIO_PIN_RESET)



void TM1637_START(void);
void TM1637_STOP(void);                 //结束条件
 
void TM1637_WRITE_BYTE_DATA(unsigned char mydata);
void TM1637_CHECK_ack(void);

void TM1637_WRITE_DISPLAY_BYTE_FIX_ADDRESS(unsigned char addr, unsigned char my_data);

#endif

tm1637.c

#include "tm1637.h"
extern TIM_HandleTypeDef htim4;
 
const unsigned char SEGMENT_CODE[]=  {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7C,0x39,0x5E,0x79,0x71};
 
 
unsigned int delay_time=1;//us延时设为 1 数码管不会抖动

 void delay_us(uint16_t us)
{     //微秒延时
	uint16_t differ = 0xffff-us-5;				
	__HAL_TIM_SET_COUNTER(&htim4,differ);	//设定TIM1计数器起始值
	HAL_TIM_Base_Start(&htim4);		//启动定时器	
	
	while(differ < 0xffff-5){	//判断
		differ = __HAL_TIM_GET_COUNTER(&htim4);		//查询计数器的计数值
	}
	HAL_TIM_Base_Stop(&htim4);
}

 
 
void TM1637_START()                   //开始条件
{
  
        TM1637_CLK_H();
        delay_us(delay_time);
    
        TM1637_SDA_H();
        delay_us(delay_time);
    
        TM1637_SDA_L();
        delay_us(delay_time);
    
        TM1637_CLK_L();
        delay_us(delay_time);
            
}
 
 
void TM1637_STOP()                     //结束条件
{
        
        TM1637_CLK_L();
        delay_us(delay_time);
    
        TM1637_SDA_L();
        delay_us(delay_time);
    
        TM1637_CLK_H();
        delay_us(delay_time);
    
        TM1637_SDA_H();
        delay_us(delay_time);
    
}
 
 
void TM1637_WRITE_BYTE_DATA(unsigned char mydata)          //送数据    低位先传
{
 
 
        unsigned char  i;
 
        for(i=0;i<8;i++)
        {
            TM1637_CLK_L();
            delay_us(delay_time);        
            
            if(mydata&0x01)
            {
               TM1637_SDA_H();
            }
            else
            {
               TM1637_SDA_L();
            }
            
            delay_us(delay_time);
        
            TM1637_CLK_H();
            delay_us(delay_time);
        
            mydata>>=1;
            delay_us(delay_time);
        
        }
 
        TM1637_CLK_L();
        delay_us(delay_time);
 
 
 
}
 
 
 
 
void TM1637_CHECK_ack()
{
    
        // 检查应答位,
        
     
        TM1637_CLK_L();
    
        delay_us(delay_time);
 
        //DIN 在第9个脉冲被拉低,要检查的
        while(HAL_GPIO_ReadPin(GPIOB,GPIO_PIN_1)==1)    
        {
            
        }
     
     
        TM1637_CLK_H();
        delay_us(delay_time);
     
        TM1637_CLK_L();
        delay_us(delay_time);
 
 
}
 
 
 
/*
     
     采用固定地址模式=============
 
     TM1637---支持6位8段数码管========================================
     
     如果有4个数码管,此程序被反复执行4次
     addr===     0~5,TM1637支持6个数码管
     my_data==== 第0个数码管的数据
 
 
*/
void TM1637_WRITE_DISPLAY_BYTE_FIX_ADDRESS(unsigned char addr, unsigned char my_data)
{
    
        unsigned char get_segment=0;
    
        
        //时序  (1) start
        TM1637_START(); 
 
        //(2)发送commmd1==0X44就是固定地址
        TM1637_WRITE_BYTE_DATA(0x40+addr);
        TM1637_CHECK_ack();
        //注意这个有STOP
        TM1637_STOP();
     
     
        TM1637_START();
        //(3)发送起始地址, 
        TM1637_WRITE_BYTE_DATA(0xC0+addr);
        //要等DIN在第9个脉冲被拉低
        TM1637_CHECK_ack();
 
     
         get_segment =  SEGMENT_CODE[my_data] ;
        //(4) 发送该地址的数据
        TM1637_WRITE_BYTE_DATA(get_segment|0x80);//|0x80 此处发送0x80是打开时间中间的2个点
        //要等DIN在第9个脉冲被拉低
        TM1637_CHECK_ack(); 
     
        TM1637_STOP();    
 
        //==============
        TM1637_START(); 
        TM1637_WRITE_BYTE_DATA(0X8C);              //开显示
        TM1637_STOP();

 
}

main.c

 /* USER CODE BEGIN 2 */
uint16_t g_usCO2ppm = 1234;
uint8_t g_ucaDispCode[4];
  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
          g_ucaDispCode[0] = g_usCO2ppm/1000;
		  g_ucaDispCode[1] = g_usCO2ppm/100%10;
		  g_ucaDispCode[2] = g_usCO2ppm/10%10;
		  g_ucaDispCode[3] = g_usCO2ppm%10;
            TM1637_WRITE_DISPLAY_BYTE_FIX_ADDRESS(0,g_ucaDispCode[0]);
            TM1637_WRITE_DISPLAY_BYTE_FIX_ADDRESS(1,g_ucaDispCode[1]);       
            TM1637_WRITE_DISPLAY_BYTE_FIX_ADDRESS(2,g_ucaDispCode[2]);
            TM1637_WRITE_DISPLAY_BYTE_FIX_ADDRESS(3,g_ucaDispCode[3]); 

    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
  }
  /* USER CODE END 3 */

 注意:

程序没有启用按键读取功能,只简单显示。ack也没有判断,直接延时跳过。

添加路径

STM32CubeMX TM1637驱动数码管_第6张图片

查看stlink 更改下载完自动复位

STM32CubeMX TM1637驱动数码管_第7张图片

STM32CubeMX TM1637驱动数码管_第8张图片

STM32CubeMX TM1637驱动数码管_第9张图片

运行效果

STM32CubeMX TM1637驱动数码管_第10张图片

链接: https://pan.baidu.com/s/1Zfsa5qiYoBfVb26oX4moAg?pwd=dafj 提取码: dafj 

原文 STM32 经过TM1637驱动四位数码管_tm1637数码管-CSDN博客

你可能感兴趣的:(stm32,嵌入式硬件,单片机)