基于STC15系列库操作LED灯

一、准备工作

  1. 基于STC15系列库的工程模板

参考:51单片机工程模板的建立(基于STC15系列库)-CSDN博客

  1. Keil编译器

二、程序编写

  1. 新建 led.c 和 led.h 文件并存放于 user/led 文件夹下;
  1. 新建 user.c 和 user.h 文件并存放于 user 文件夹下;
  1. 将 user.c 文件 led.c 文件添加进工程分组 user 组别下;
  1. 将 user.h 文件目录和 led.h 文件目录添加进头文件检索目录内;
  1. 在 main.c 文件中添加以下代码内容;
cpp 复制代码
#include "user.h"

void main()
{
	User_Init();            //上电初始化,在该函数内实现上电后所需要的所有初始化操作

	while(1)
    {
        LED_OnOrOff(LED_ON);        //打开LED
        delay_ms(500);
        LED_OnOrOff(LED_OFF);       //关闭LED
        delay_ms(500);
    }
}
  1. 在 led.c 函数中添加以下代码内容;
cpp 复制代码
#include "led.h"

//设置LED电路引脚
#define LED_Px GPIO_P1
#define LED_Py GPIO_Pin_0

//设置LED引脚为推挽输出模式
void LED_Init(void)
{
	GPIO_InitTypeDef GPIO_InitStructure;

	GPIO_InitStructure.Mode = GPIO_OUT_PP;
	GPIO_InitStructure.Pin  = LED_Py;

	GPIO_Inilize(LED_Px, &GPIO_InitStructure);
}

//制作开关LED的驱动函数
void LED_OnOrOff(unsigned char LED_Sta)
{
	if(LED_Sta)
	{
        GPIO_PIN_Set(LED_Px, LED_Py);
	}
	else
	{
        GPIO_PIN_ReSet(LED_Px, LED_Py);
	}
}

//制作GPIO的初始化函数
void GPIO_Init(void)
{
	LED_Init();    //对LED引脚初始化
}
  1. 在 led.h 文件中添加以下代码内容;
cpp 复制代码
#ifndef __LED_H__
#define __LED_H__

#include "gpio.h"

//宏定义灯的开关标识符号,便于程序理解
#define LED_ON  0
#define LED_OFF 1


//声明所有在led.c文件中定义的函数
void LED_Init(void);

void LED_OnOrOff(unsigned char LED_Sta);

void GPIO_Init(void);

#endif
  1. 在 user.c 文件中添加以下代码内容;
cpp 复制代码
#include "user.h"

void User_Init(void)
{
    GPIO_Init();      //通用IO端口初始化
}
  1. 在 user.h 文件中添加以下代码内容;
cpp 复制代码
#ifndef __USER_H__
#define __USER_H__

//文件引用
#include "config.h"
#include "led.h"
#include "delay.h"

//函数声明
void User_Init(void);

#endif
  1. 按正常库设计逻辑,LED驱动工程到此已经结束,用户应该可以编译运行,并下载看程序效果了,很遗憾,本程序出现了报错;因为在 led.c 文件中使用了两个官方库未定义的函数:
cpp 复制代码
//制作开关LED的驱动函数
void LED_OnOrOff(unsigned char LED_Sta)
{
	if(LED_Sta)
	{
        GPIO_PIN_Set(LED_Px, LED_Py);           //官方库未定义
	}
	else
	{
        GPIO_PIN_ReSet(LED_Px, LED_Py);         //官方库未定义
	}
}

这两个函数的功能很简单用于对特定引脚置位或重置操作,即拉高或拉低电平信号;由于在以后的众多功能中都需要这么操作,在该官方库中我自作主张添加了以上两个函数;具体内容见步骤11、步骤12;

  1. 在 gpio.h 文件 u8 GPIO_Inilize(u8 GPIO, GPIO_InitTypeDef *GPIOx); 函数上方添加以下代码内容;
cpp 复制代码
typedef struct
{
	u8	Mode;		//IO模式,  		GPIO_PullUp,GPIO_HighZ,GPIO_OUT_OD,GPIO_OUT_PP
	u8	Pin;		//要设置的端口	
} GPIO_InitTypeDef;

//添加置位与重置函数声明
u8 GPIO_PIN_Set(u8 GPIO, u8 GPIO_Pin_x);
u8 GPIO_PIN_ReSet(u8 GPIO, u8 GPIO_Pin_x);

u8 GPIO_Inilize(u8 GPIO, GPIO_InitTypeDef *GPIOx);
  1. 在 gpio.c 文件 u8 GPIO_Inilize(u8 GPIO, GPIO_InitTypeDef *GPIOx); 函数上方添加以下代码内容;
cpp 复制代码
//添加置位函数定义
u8 GPIO_PIN_Set(u8 GPIO, u8 GPIO_Pin_x)
{
    if(GPIO > GPIO_P5)				return 1;	//空操作
    if(GPIO_Pin_x > GPIO_Pin_7)	    return 2;	//空操作

    if(GPIO == GPIO_P0)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P00 = 1;
        if(GPIO_Pin_x == GPIO_Pin_1)    P01 = 1;
        if(GPIO_Pin_x == GPIO_Pin_2)    P02 = 1;
        if(GPIO_Pin_x == GPIO_Pin_3)    P03 = 1;
        if(GPIO_Pin_x == GPIO_Pin_4)    P04 = 1;
        if(GPIO_Pin_x == GPIO_Pin_5)    P05 = 1;
        if(GPIO_Pin_x == GPIO_Pin_6)    P06 = 1;
        if(GPIO_Pin_x == GPIO_Pin_7)    P07 = 1;
    }
    else if(GPIO == GPIO_P1)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P10 = 1;
        if(GPIO_Pin_x == GPIO_Pin_1)    P11 = 1;
        if(GPIO_Pin_x == GPIO_Pin_2)    P12 = 1;
        if(GPIO_Pin_x == GPIO_Pin_3)    P13 = 1;
        if(GPIO_Pin_x == GPIO_Pin_4)    P14 = 1;
        if(GPIO_Pin_x == GPIO_Pin_5)    P15 = 1;
        if(GPIO_Pin_x == GPIO_Pin_6)    P16 = 1;
        if(GPIO_Pin_x == GPIO_Pin_7)    P17 = 1;
    }
    else if(GPIO == GPIO_P2)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P20 = 1;
        if(GPIO_Pin_x == GPIO_Pin_1)    P21 = 1;
        if(GPIO_Pin_x == GPIO_Pin_2)    P22 = 1;
        if(GPIO_Pin_x == GPIO_Pin_3)    P23 = 1;
        if(GPIO_Pin_x == GPIO_Pin_4)    P24 = 1;
        if(GPIO_Pin_x == GPIO_Pin_5)    P25 = 1;
        if(GPIO_Pin_x == GPIO_Pin_6)    P26 = 1;
        if(GPIO_Pin_x == GPIO_Pin_7)    P27 = 1;
    }
    else if(GPIO == GPIO_P3)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P30 = 1;
        if(GPIO_Pin_x == GPIO_Pin_1)    P31 = 1;
        if(GPIO_Pin_x == GPIO_Pin_2)    P32 = 1;
        if(GPIO_Pin_x == GPIO_Pin_3)    P33 = 1;
        if(GPIO_Pin_x == GPIO_Pin_4)    P34 = 1;
        if(GPIO_Pin_x == GPIO_Pin_5)    P35 = 1;
        if(GPIO_Pin_x == GPIO_Pin_6)    P36 = 1;
        if(GPIO_Pin_x == GPIO_Pin_7)    P37 = 1;
    }
    else if(GPIO == GPIO_P4)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P40 = 1;
        if(GPIO_Pin_x == GPIO_Pin_1)    P41 = 1;
        if(GPIO_Pin_x == GPIO_Pin_2)    P42 = 1;
        if(GPIO_Pin_x == GPIO_Pin_3)    P43 = 1;
        if(GPIO_Pin_x == GPIO_Pin_4)    P44 = 1;
        if(GPIO_Pin_x == GPIO_Pin_5)    P45 = 1;
        if(GPIO_Pin_x == GPIO_Pin_6)    P46 = 1;
        if(GPIO_Pin_x == GPIO_Pin_7)    P47 = 1;
    }
    else if(GPIO == GPIO_P5)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P50 = 1;
        if(GPIO_Pin_x == GPIO_Pin_1)    P51 = 1;
        if(GPIO_Pin_x == GPIO_Pin_2)    P52 = 1;
        if(GPIO_Pin_x == GPIO_Pin_3)    P53 = 1;
        if(GPIO_Pin_x == GPIO_Pin_4)    P54 = 1;
        if(GPIO_Pin_x == GPIO_Pin_5)    P55 = 1;
        if(GPIO_Pin_x == GPIO_Pin_6)    P56 = 1;
        if(GPIO_Pin_x == GPIO_Pin_7)    P57 = 1;
    }

    return 0;
}

//添加重置函数定义
u8 GPIO_PIN_ReSet(u8 GPIO, u8 GPIO_Pin_x)
{
    if(GPIO > GPIO_P5)				return 1;	//空操作
    if(GPIO_Pin_x > GPIO_Pin_7)	    return 2;	//空操作

    if(GPIO == GPIO_P0)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P00 = 0;
        if(GPIO_Pin_x == GPIO_Pin_1)    P01 = 0;
        if(GPIO_Pin_x == GPIO_Pin_2)    P02 = 0;
        if(GPIO_Pin_x == GPIO_Pin_3)    P03 = 0;
        if(GPIO_Pin_x == GPIO_Pin_4)    P04 = 0;
        if(GPIO_Pin_x == GPIO_Pin_5)    P05 = 0;
        if(GPIO_Pin_x == GPIO_Pin_6)    P06 = 0;
        if(GPIO_Pin_x == GPIO_Pin_7)    P07 = 0;
    }
    else if(GPIO == GPIO_P1)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P10 = 0;
        if(GPIO_Pin_x == GPIO_Pin_1)    P11 = 0;
        if(GPIO_Pin_x == GPIO_Pin_2)    P12 = 0;
        if(GPIO_Pin_x == GPIO_Pin_3)    P13 = 0;
        if(GPIO_Pin_x == GPIO_Pin_4)    P14 = 0;
        if(GPIO_Pin_x == GPIO_Pin_5)    P15 = 0;
        if(GPIO_Pin_x == GPIO_Pin_6)    P16 = 0;
        if(GPIO_Pin_x == GPIO_Pin_7)    P17 = 0;
    }
    else if(GPIO == GPIO_P2)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P20 = 0;
        if(GPIO_Pin_x == GPIO_Pin_1)    P21 = 0;
        if(GPIO_Pin_x == GPIO_Pin_2)    P22 = 0;
        if(GPIO_Pin_x == GPIO_Pin_3)    P23 = 0;
        if(GPIO_Pin_x == GPIO_Pin_4)    P24 = 0;
        if(GPIO_Pin_x == GPIO_Pin_5)    P25 = 0;
        if(GPIO_Pin_x == GPIO_Pin_6)    P26 = 0;
        if(GPIO_Pin_x == GPIO_Pin_7)    P27 = 0;
    }
    else if(GPIO == GPIO_P3)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P30 = 0;
        if(GPIO_Pin_x == GPIO_Pin_1)    P31 = 0;
        if(GPIO_Pin_x == GPIO_Pin_2)    P32 = 0;
        if(GPIO_Pin_x == GPIO_Pin_3)    P33 = 0;
        if(GPIO_Pin_x == GPIO_Pin_4)    P34 = 0;
        if(GPIO_Pin_x == GPIO_Pin_5)    P35 = 0;
        if(GPIO_Pin_x == GPIO_Pin_6)    P36 = 0;
        if(GPIO_Pin_x == GPIO_Pin_7)    P37 = 0;
    }
    else if(GPIO == GPIO_P4)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P40 = 0;
        if(GPIO_Pin_x == GPIO_Pin_1)    P41 = 0;
        if(GPIO_Pin_x == GPIO_Pin_2)    P42 = 0;
        if(GPIO_Pin_x == GPIO_Pin_3)    P43 = 0;
        if(GPIO_Pin_x == GPIO_Pin_4)    P44 = 0;
        if(GPIO_Pin_x == GPIO_Pin_5)    P45 = 0;
        if(GPIO_Pin_x == GPIO_Pin_6)    P46 = 0;
        if(GPIO_Pin_x == GPIO_Pin_7)    P47 = 0;
    }
    else if(GPIO == GPIO_P5)
    {
        if(GPIO_Pin_x == GPIO_Pin_0)    P50 = 0;
        if(GPIO_Pin_x == GPIO_Pin_1)    P51 = 0;
        if(GPIO_Pin_x == GPIO_Pin_2)    P52 = 0;
        if(GPIO_Pin_x == GPIO_Pin_3)    P53 = 0;
        if(GPIO_Pin_x == GPIO_Pin_4)    P54 = 0;
        if(GPIO_Pin_x == GPIO_Pin_5)    P55 = 0;
        if(GPIO_Pin_x == GPIO_Pin_6)    P56 = 0;
        if(GPIO_Pin_x == GPIO_Pin_7)    P57 = 0;
    }

    return 0;
}
  1. 保存所有文件并编译即可完成LED驱动例程;

  2. 工程文件:基于STC15系列库的LED工程样例资源-CSDN文库

三、总结

使用STC15系列库在小工程上的复杂程度提升了很多倍,这会使的很多同学放弃使用库函数来学习,这是无法避免的;但我们不能忽视使用库所带来的优势,程序的可读性大大加强,程序的统一操作使程序在相互之间的流通性大大提升,也许你们还没有意识到库的优势,但还是希望你们保持一颗热情的心继续深入学习一下,也许很快你就能体会到库的魅力;

相关推荐
森焱森4 小时前
水下航行器外形分类详解
c语言·单片机·算法·架构·无人机
小殷学长6 小时前
【单片机毕业设计17-基于stm32c8t6的智能倒车监测系统】
stm32·单片机·课程设计
TESmart碲视7 小时前
HKS201-M24 大师版 8K60Hz USB 3.0 适用于 2 台 PC 1台显示器 无缝切换 KVM 切换器
单片机·嵌入式硬件·物联网·游戏·计算机外设·电脑·智能硬件
small_wh1te_coder8 小时前
硬件嵌入式学习路线大总结(一):C语言与linux。内功心法——从入门到精通,彻底打通你的任督二脉!
linux·c语言·汇编·嵌入式硬件·算法·c
花落已飘9 小时前
STM32中实现shell控制台(shell窗口输入实现)
stm32·单片机·嵌入式硬件
牵牛老人11 小时前
Qt处理USB摄像头开发说明与QtMultimedia与V4L2融合应用
stm32·单片机·qt
宇钶宇夕12 小时前
针对工业触摸屏维修的系统指南和资源获取途径
单片机·嵌入式硬件·自动化
和风化雨12 小时前
stm32的三种开发方式
stm32·单片机·嵌入式硬件
kanhao10013 小时前
三态逻辑详解:单片机GPIO、计算机总线系统举例
单片机·嵌入式硬件
小眼睛FPGA14 小时前
【RK3568+PG2L50H开发板实验例程】FPGA部分/紫光同创 IP core 的使用及添加
科技·嵌入式硬件·ai·fpga开发·gpu算力