STM32-HAL库05-GPIO直接4位驱动数码管

STM32-HAL库05-GPIO直接4位驱动数码管

一、数码管的引脚确定

之前购买了一个TM1638驱动的数码管,但是驱动时间上达不到我的预期目标,所以就想着自己直接用GPIO引脚进行驱动,然后就单独从板子上拆下来了数码管,这就带来了一个问题,不知道数码管的引脚分布,因此就只能一个一个去试了。

首先选择数码管带有标志性的一个面作为基准面:
在这里插入图片描述
然后利用万用表的蜂鸣档选择两个临近的引脚,如果没有任何反应,则说明这两个引脚为共阴端(或者共阳)或者都为触发端。

这时就一个引脚,移动另外一个,直到有亮光出现,此时万用表一定是一段接着共性端,一段接着触发端,但是还不能确定方向,此时固定住万用表的红色线,移动黑色线,当再次发生亮光时:
(1)与第一次发生亮光比,亮光位置处于同一位中的不同位置,则说明该数码管为共阳极,万用表红色线此时为某一共性端。
(2)与第一次发生亮光比,亮光位置处于不同位的相同位置,则说明该数码管为共阴极,万用表红色线此时为某一触发端。

再选定某个共性端,挨个测出触发端的具体标号(ABCDEFG)。

最后选定某一触发端,挨个测出四个共性端标号(G1G2G3G4)

二、数码管驱动

由于本文中只用到了数字码,因此只设定0-9数字的GPIO控制函数。

配置头文件

#ifndef __TM1638_H
#define __TM1638_H	 
 
//========移植的时候,根据所选芯片引入相应的头文件==========在main.h里面查看
#include "stm32f1xx_hal.h"
#include "gpio.h"

#define A1 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_SET);	
#define A0 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_RESET);

#define B1 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_6, GPIO_PIN_SET);	
#define B0 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_6, GPIO_PIN_RESET);

#define C1 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_7, GPIO_PIN_SET);	
#define C0 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_7, GPIO_PIN_RESET);

#define D1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_0, GPIO_PIN_SET);	
#define D0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_0, GPIO_PIN_RESET);

#define E1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_1, GPIO_PIN_SET);	
#define E0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_1, GPIO_PIN_RESET);

#define F1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_15, GPIO_PIN_SET);	
#define F0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_15, GPIO_PIN_RESET);

#define G1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_10, GPIO_PIN_SET);	
#define G0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_10, GPIO_PIN_RESET);

#define GP1 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_8, GPIO_PIN_SET);	
#define GP0 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_8, GPIO_PIN_RESET);

#define G1_1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_11, GPIO_PIN_SET);	
#define G1_0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_11, GPIO_PIN_RESET);

#define G2_1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_12, GPIO_PIN_SET);	
#define G2_0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_12, GPIO_PIN_RESET);

#define G3_1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_13, GPIO_PIN_SET);	
#define G3_0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_13, GPIO_PIN_RESET);

#define G4_1 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_14, GPIO_PIN_SET);	
#define G4_0 HAL_GPIO_WritePin(GPIOB, GPIO_PIN_14, GPIO_PIN_RESET);

void Showone_inadd(uint8_t add,uint8_t data);
void Off_all(void);
void Show_current(float current);
void Show_int(uint16_t a);
#endif

配置源文件

#include "gpio.h"
#include "TM1638.h"

void Showone_inadd(uint8_t add,uint8_t data)
{
	switch (add)
	{
		case 1:
			G1_1;G2_0;G3_0;G4_0;break;
		case 2:
			G1_0;G2_1;G3_0;G4_0;break;	
		case 3:
			G1_0;G2_0;G3_1;G4_0;break;	
		case 4:
			G1_0;G2_0;G3_0;G4_1;break;
	    default:
			break;
	}
	
	switch (data)
	{
		case 1:
			A1;B0;C0;D1;E1;F1;G1;GP1;break;
		case 2:
			A0;B0;C1;D0;E0;F1;G0;GP1;break;
		case 3:
			A0;B0;C0;D0;E1;F1;G0;GP1;break;		
		case 4:
			A1;B0;C0;D1;E1;F0;G0;GP1;break;
		case 5:
			A0;B1;C0;D0;E1;F0;G0;GP1;break;
		case 6:
			A0;B1;C0;D0;E0;F0;G0;GP1;break;
		case 7:
			A0;B0;C0;D1;E1;F1;G1;GP1;break;	
		case 8:
			A0;B0;C0;D0;E0;F0;G0;GP1;break;	
		case 9:
			A0;B0;C0;D1;E1;F0;G0;GP1;break;	
		case 0:
			A0;B0;C0;D0;E0;F0;G1;GP1;break;			
	}
	
	if (add == 3)
	{
		GP0;
	}
}

void Show_current(float current)
{
	float incurrent;
	uint16_t intcurrent;
	uint8_t  data1;
	uint8_t  data2;
	uint8_t  data3;
	uint8_t  data4;	
	incurrent = current;
	
	if (incurrent < 0)
	{
		incurrent = -incurrent;
	}
	if (incurrent >99.99)
	{
		incurrent =99.99;
	}

	intcurrent = incurrent *100.0;
	data1 = intcurrent/1000;
	intcurrent = intcurrent - data1*1000;
	data2 = intcurrent/100;
	intcurrent = intcurrent - data2*100;	
	data3 = intcurrent/10;
	intcurrent = intcurrent - data3*10;	
	data4 = intcurrent;
	
	Showone_inadd(1,data1);
	Off_all();
	Showone_inadd(2,data2);
	Off_all();
	Showone_inadd(3,data3);
	Off_all();
	Showone_inadd(4,data4);
	Off_all();
}

void Show_int(uint16_t a)
{
	uint16_t intcurrent;
	uint8_t  data1;
	uint8_t  data2;
	uint8_t  data3;
	uint8_t  data4;	
	
	intcurrent = a;
	data1 = intcurrent/1000;
	intcurrent = intcurrent - data1*1000;
	data2 = intcurrent/100;
	intcurrent = intcurrent - data2*100;	
	data3 = intcurrent/10;
	intcurrent = intcurrent - data3*10;	
	data4 = intcurrent/1;
	
	Off_all();
	Showone_inadd(1,data1);
	Off_all();
	Showone_inadd(2,data2);
	Off_all();
	Showone_inadd(3,data3);
	Off_all();
	Showone_inadd(4,data4);
	Off_all();
	
}

void Off_all(void)
{
	G1_0;G2_0;G3_0;G4_0;
	A1;B1;C1;D1;E1;F1;G1;GP1;
}

main函数中进行调用

int main(void)
{
  /* USER CODE BEGIN 1 */

  /* USER CODE END 1 */

  /* MCU Configuration--------------------------------------------------------*/

  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();

  /* USER CODE BEGIN Init */

  /* USER CODE END Init */

  /* Configure the system clock */
  SystemClock_Config();

  /* USER CODE BEGIN SysInit */

  /* USER CODE END SysInit */

  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  MX_ADC1_Init();
  MX_USART1_UART_Init();
  MX_SPI1_Init();
  /* USER CODE BEGIN 2 */
  HAL_ADCEx_Calibration_Start(&hadc1);    //AD校准
  //OLED_Init();
  //OLED_ShowString(0,0,(unsigned char *)"Current:");
  
  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
	    HAL_GPIO_WritePin(GPIOA, GPIO_PIN_11, GPIO_PIN_SET);
		switch(station)
		{
			case 0://开机初始化过程
				    HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_RESET);//打开LED,绿灯常亮
				    HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_SET);//打开EN
				    HAL_GPIO_WritePin(GPIOB, GPIO_PIN_7, GPIO_PIN_SET);//打开继电器
				    station = 1;//进入下一个状态:电流检测监控
				    break;
			case 1://电流检测状态
					HAL_ADC_Start(&hadc1);     //启动ADC转换
					HAL_ADC_PollForConversion(&hadc1, 50);   //等待转换完成,50为最大等待时间,单位为ms
					if(HAL_IS_BIT_SET(HAL_ADC_GetState(&hadc1), HAL_ADC_STATE_REG_EOC))
					{
						ADC_Value = HAL_ADC_GetValue(&hadc1);   //获取AD值
						i = ((ADC_Value*0.00081)-1.65)*7.57576;
					}
					if (i <-4 || i >=4)
					{
						HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_SET);//打开LED,绿灯熄灭
						HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_RESET);//关闭EN
						HAL_GPIO_WritePin(GPIOB, GPIO_PIN_7, GPIO_PIN_RESET);//断开继电器
						station =2;//进入过流报警状态
					}
					Show_current(i);
					break;
			case 2://过流报警状态
					HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_RESET);//关闭EN
					HAL_GPIO_WritePin(GPIOB, GPIO_PIN_7, GPIO_PIN_RESET);//断开继电器
					HAL_Delay(200);
					if (HAL_GPIO_ReadPin(GPIOC, GPIO_PIN_13) ==0)
					{
						HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_SET);
					}
					else
					{
						HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_RESET);
					}
					break;
			default :
                    break;			
		}	  
		HAL_GPIO_WritePin(GPIOA, GPIO_PIN_11, GPIO_PIN_RESET);
    /* USER CODE END WHILE */

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

三、结果说明

数码管驱动用时40us,电流检测部分用时20us,总用时符合预期需求。

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
回答: 在STM32驱动HC05蓝牙模块时,可以使用HAL进行驱动。HALSTM32提供的一套硬件抽象层,可以简化驱动的编程过程。具体步骤如下: 1. 首先,需要初始化USART串口,将其配置为与HC05通信的串口。可以使用HAL_UART_Init函数进行初始化,并设置相应的波特率、数据位、停止位等参数。 2. 接下来,需要配置GPIO引脚,将其设置为USART的功能引脚。可以使用HAL_GPIO_Init函数进行配置。 3. 然后,可以使用HAL_UART_Transmit函数发送数据给HC05模块,或使用HAL_UART_Receive函数接收HC05模块发送的数据。 需要注意的是,具体的配置和使用方法可能会因不同的STM32型号和HAL版本而有所差异。因此,在实际应用中,建议参考相关的STM32芯片手册和HAL文档,以确保正确配置和使用HC05模块。 引用\[2\]中提到了静态显示驱动的方法,这是一种直流驱动方式,每个数码管的每一个端码都有一个单片机的I/O端口进行驱动。这种方法编程简单,显示亮度高,但占用的I/O端口较多。如果需要驱动多个数码管,可以考虑使用译码器进行驱动,以减少所需的I/O端口数量。 引用\[3\]中提到了使用STM32F103C8T6单片机通过HAL方式对0.96寸OLED屏幕进行驱动的方法。这里使用了硬件IIC进行驱动,相比软件IIC,硬件IIC可以提供更高的传输速率和更稳定的通信。 综上所述,可以使用HAL对HC05蓝牙模块进行驱动,具体的配置和使用方法可以参考相关的STM32芯片手册和HAL文档。同时,还可以借鉴静态显示驱动和硬件IIC驱动的方法,以满足不同的驱动需求。 #### 引用[.reference_title] - *1* *2* [STM32HAL驱动数码管](https://blog.csdn.net/svfsvadfv/article/details/129476601)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^insert_down28v1,239^v3^insert_chatgpt"}} ] [.reference_item] - *3* [STM32(HAL驱动OLED](https://blog.csdn.net/weixin_44597885/article/details/129232682)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^insert_down28v1,239^v3^insert_chatgpt"}} ] [.reference_item] [ .reference_list ]

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Tony0925

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值