[STM32学习]定时器实现码表(数码管显示)

实验:要求完成码表,具体要求如下:

要求:显示格式XX.YY。
    按键1 可控制计数暂停还是启动
    按键2 清零(必需在暂停后才可以操作
    按键3 存储当前码表的时间,存储成功后显示y(必需在暂停后才可以操作
    按键4 显示存储的码表时间(必需在暂停后才可以操作
    按键5 记录的码表时间向下翻页(必需在暂停后才可以操作

简单分析:

      码表,其实就是显示秒的下一个单位,电子手表上一般都有码表的功能,秒到分钟一般是59秒进行,而码表的下一个单位,则要计到99上才能进位到1秒,所以需要修改定时器,将定时器修改成10ms溢出中断一次,这样记录100次后就达到了1秒。

Tim4Init(719, 999);		//	定时10ms 720*1000/72000000 = 1/100

我们在完成实验之前一定要搞清楚它的硬件电路,分析好引脚所对应的IO口,下图为数码管硬件设计图,完全可以按照电路图设计。

由上图可以知道,该数码管为四位八段数码管,引脚分析如下

数码管电路STM32的IO口
A1PB2
A2PB3
A3PB4
A4PB5
aPE0
bPE1
cPE2
dPE3
ePE4
fPE5
gPE6
dpPC13

通过上述电路图可知,数码管为共阳极数码管,PB2-PB5低电平选中数码管,其中,注意:PB3和PB3引脚默认状态下不是普通的IO口,所以需要用到其复用功能:

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE);		//	开启服用引脚时钟,保证引脚第二功能正常使用
GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable,ENABLE); //关闭JTAG,使能SWD

数码管为共阳极数码管,其编码为:

//	共阳极编码 0-9 a- f
unsigned char seg[] = {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0x88,0x83,0xc6,0xa1,0x86,0x8e};

接下来是按键的截下图,如下:

 引脚对应关系:

按键STM32 的IO引脚
KEY1PC0
KEY2PC1
KEY3PC2
KEY4PC3
KEY5PC4

接下来依据任务要求完成代码:

按键初始化:

/********************************************
函数名称:void KeyInit(void)
函数参数:无参,返回值为空
函数功能:实现按键功能初始化
作者:***
时间:2022.3.8
修改作者:
修改实现:
修改说明:
*********************************************/
void KeyInit(void)
{
	// KEY接在PC0-PC4上,一共5个按键
	//初始化步骤
	/**
		1.开启所对应的时钟
		2.选择所需要的IO口
		3.设置IO口的工作模式
		4.初始化上述配置
	**/
	GPIO_InitTypeDef GPIO_InitStruct;											//	结构体变量申明
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC,ENABLE);	//	开启时钟
	GPIO_InitStruct.GPIO_Pin = GPIO_Pin_0|GPIO_Pin_1|GPIO_Pin_2|GPIO_Pin_3
								|GPIO_Pin_4;	//  选择PC0-PC4口
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN_FLOATING;			//	浮空输入模式
	
	GPIO_Init(GPIOC,&GPIO_InitStruct);													//	配置初始化
	
}

数码管初始化:

/********************************************
函数名称:void SegInit(void)
函数参数:无参,返回值为空
函数功能:实现数码管初始化
作者:***
时间:2022.3.17
修改作者:
修改实现:
修改说明:
*********************************************/
void SegInit(void)
{
	//初始化步骤
	/**
		1.开启所对应的时钟
		2.选择所需要的IO口
		3.设置IO口的工作模式
		4.设置IO的输出速率(当IO口设置成输出模式才需要)
		5.初始化上述配置
		6.初始化IO的初值
	**/
	GPIO_InitTypeDef GPIO_InitStruct;											//	结构体变量申明
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);	//	开启时钟
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC,ENABLE);	//	开启时钟
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOE,ENABLE);	//	开启时钟
	
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE);		//	开启服用引脚时钟,保证引脚第二功能正常使用

	GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable,ENABLE); //关闭JTAG,使能SWD

	//	设置片选引脚
	GPIO_InitStruct.GPIO_Pin = GPIO_Pin_2|GPIO_Pin_3|GPIO_Pin_4|GPIO_Pin_5;	//  选择PB2-PB5口
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;								//	推挽输出
	GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;							//	设置输出速率50MHz
	GPIO_Init(GPIOB,&GPIO_InitStruct);													//	配置初始化
	
	//	设置七段引脚
	GPIO_InitStruct.GPIO_Pin = GPIO_Pin_0|GPIO_Pin_1|GPIO_Pin_2|GPIO_Pin_3
								|GPIO_Pin_4|GPIO_Pin_5|GPIO_Pin_6;	//  选择PE0-PE6口
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;								//	推挽输出
	GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;							//	设置输出速率50MHz
	GPIO_Init(GPIOE,&GPIO_InitStruct);													//	配置初始化
	
	//	设置DP(小数点)引脚
	GPIO_InitStruct.GPIO_Pin = GPIO_Pin_13;	//  选择PE0-PE6口
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;								//	推挽输出
	GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;							//	设置输出速率50MHz
	GPIO_Init(GPIOC,&GPIO_InitStruct);													//	配置初始化
	
	GPIO_Write(GPIOE, 0X007F);		//	设置七段引脚为高电平   0111 1111
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);		//	小数点
	GPIO_WriteBit(GPIOB,GPIO_Pin_2|GPIO_Pin_3|GPIO_Pin_4|GPIO_Pin_5,Bit_SET);		//	设置片选引脚为高电平
	
}

定时器中断服务函数:

/********************************************
函数名称:TIM4_IRQHandler(void)
函数参数:
				无参,无返回参数
函数功能:定时器定时10ms
作者:***
时间:2022.5.19
修改作者:
修改时间:
修改说明:
修改作者:
修改时间:
修改说明:
*********************************************/
void TIM4_IRQHandler(void)
{
	if(TIM_GetITStatus(TIM4, TIM_IT_Update) == 1)		//	标志计数溢出中断产生
	{
		tim4Cnt++;			//	秒统计
		if(tim4Cnt>9999)		//	99:99			99*100+99
		{
			tim4Cnt = 0;
		}
	}
	TIM_ClearITPendingBit(TIM4, TIM_IT_Update);	
}

按键功能实现:

/********************************************
函数名称:int KeyScan6(void)
函数参数:无
函数功能:要求:显示格式XX.YY。
				按键1可控制计数暂停还是启动
				按键2 清零(必需在暂停后才可以操作)
				按键3 存储当前码表的时间,存储成功后显示y
				按键4 显示存储的码表时间
				按键5 记录的码表时间向下翻页
作者:***
时间:2022.5.19
修改作者:
修改实现:
修改说明:
*********************************************/
void KeyScan6(void)
{
	if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_0) == 0	)			//	判断按键是否按下
	{
		delay_ms(10);	//	消抖
		if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_0) == 0	)
		{
			flag = -1*flag;	//	-1和1跳转
		}
		while(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_0) == 0);
	}
	if(1 == flag)	//	计数
	{
		TIM_Cmd(TIM4,ENABLE);
	}
	if(-1 == flag) //	暂停
	{
		TIM_Cmd(TIM4,DISABLE);		//	关闭定时器
		
		if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_1) == 0	)			//	判断按键是否按下
		{
			delay_ms(10);	//	消抖
			if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_1) == 0	)
			{
				tim4Cnt = 0;		//	在暂停的条件下实现码表清0 
			}
			while(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_1) == 0);
		}
		if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_2) == 0	)			//	判断按键是否按下
		{
			delay_ms(10);	//	消抖
			if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_2) == 0	)
			{
				saveTime[key3Cnt] = tim4Cnt;
				key3Cnt++;			//	按键按下次数统计
				if(key3Cnt>9)
				{
					key3Cnt = 0;			//	计数归0
				}
				//SegDis10();			//	显示y
			}
			while(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_2) == 0)		//	按键松开检查
			{
				SegDis10();			//	显示y
			}
		}
		
		if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_3) == 0	)			//	判断按键是否按下
		{
			delay_ms(10);	//	消抖
			if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_3) == 0	)
			{		
				tim4Cnt = saveTime[0];
			}
			while(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_3) == 0);		//	按键松开检查
		}
		
		if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_4) == 0	)			//	判断按键是否按下
		{
			delay_ms(10);	//	消抖
			if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_4) == 0	)
			{
				key5Cnt++;    					//	按键按下计数 
				if(key5Cnt>9)
				{
					key5Cnt = 0;		//	归0
				}
				tim4Cnt = saveTime[key5Cnt];
			}
			while(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_4) == 0);		//	按键松开检查
		}		
	}
	
	SegDis9();
}

数码管功能实现:


/********************************************
函数名称:void SegDis9(int value)
函数参数:无参,返回值为空
函数功能:
					要求:显示格式XX.YY。
作者:***
时间:2022.5.17
修改作者:
修改实现:
修改说明:
*********************************************/
void SegDis9(void)
{
		
	//	数码管a
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_RESET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_SET);	//	
	GPIO_Write(GPIOE, seg[tim4Cnt/1000]);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);	//	小数点不需要显示
	delay_ms(5);
	//	数码管b
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_RESET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_SET);	//	
	GPIO_Write(GPIOE, seg[tim4Cnt/100%10]);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_RESET);	//	小数点不需要显示
	delay_ms(5);
	//	数码管c
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_RESET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_SET);	//	
	GPIO_Write(GPIOE, seg[tim4Cnt/10%10]);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);	//	小数点不需要显示
	delay_ms(5);
	//	数码管d
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_RESET);	//	
	GPIO_Write(GPIOE, seg[tim4Cnt%10]);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);	//	小数点不需要显示
	delay_ms(5);
}

/********************************************
函数名称:void SegDis10(int value)
函数参数:无参,返回值为空
函数功能:
					要求:y。
					共阳极编码y的值:0X91
作者:***
时间:2022.5.17
修改作者:
修改实现:
修改说明:
*********************************************/
void SegDis10(void)
{
	//	数码管a
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_RESET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_SET);	//	
	GPIO_Write(GPIOE, 0X91);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);	//	小数点不需要显示
	delay_ms(5);
	//	数码管b
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_RESET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_SET);	//	
	GPIO_Write(GPIOE, 0X91);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);	//	小数点不需要显示
	delay_ms(5);
	//	数码管c
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_RESET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_SET);	//	
	GPIO_Write(GPIOE, 0X91);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);	//	小数点不需要显示
	delay_ms(5);
	//	数码管d
	GPIO_WriteBit(GPIOB,GPIO_Pin_2,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_3,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_4,Bit_SET);		//	
	GPIO_WriteBit(GPIOB,GPIO_Pin_5,Bit_RESET);	//	
	GPIO_Write(GPIOE, 0X91);								//	可以实现多位写入
	GPIO_WriteBit(GPIOC,GPIO_Pin_13,Bit_SET);	//	小数点不需要显示
	delay_ms(5);
}

实现效果:

源码下载地址:定时器实现码表(数码管显示)-C文档类资源-CSDN文库

  • 9
    点赞
  • 45
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

小材大用

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

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

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

打赏作者

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

抵扣说明:

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

余额充值