STM32-GPIO

一、GPIO简介

**·**GPIO(General Purpose Input Output)通用输入输出口

**·**可配置8种输入输出模式

**·**引脚电平:0V~3.3V,部分引脚可容忍5V

**·**输出模式下:可控制端口输出高低电平,用以驱动LED、控制蜂鸣器、模拟通信协议输出时序等

**·**输入模式下:可读取端口的高低电平或电压,用于读取按键输入、外界模块电平信号输入、ADC电压采集、模拟通信协议接收数据等

二、GPIO结构

三、GPIO位结构

四、GPIO模式

4.1 浮空/上拉/下拉输入

(GPIO_Mode_IN_FLOATING/GPIO_Mode_IPU/GPIO_Mode_IPD)

4.2 模拟输入(GPIO_Mode_AIN)

4.3 开漏/推挽输出

(GPIO_Mode_Out_OD/GPIO_Mode_Out_PP)

4.4 复用开漏/推挽输出

(GPIO_Mode_AF_OD/GPIO_Mode_AF_PP)

五、GPIO库函数

void GPIO_DeInit(GPIO_TypeDef* GPIOx);//复位GPIO外设

void GPIO_Init(GPIO_TypeDef* GPIOx, GPIO_InitTypeDef* GPIO_InitStruct);//初始化GPIO

void GPIO_StructInit(GPIO_InitTypeDef* GPIO_InitStruct);//给结构体赋默认值

GPIO读取函数

uint8_t GPIO_ReadInputDataBit(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);

//读取输入数据寄存器某一个端口的输入值

uint16_t GPIO_ReadInputData(GPIO_TypeDef* GPIOx);

//读取整个输入数据寄存器,返回一个16位的数据

uint8_t GPIO_ReadOutputDataBit(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);

//读取输出数据寄存器某一个端口的输入值(输出模式)

uint16_t GPIO_ReadOutputData(GPIO_TypeDef* GPIOx);

//读取整个输出数据寄存器

GPIO写入函数

void GPIO_SetBits(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);//设置高电平

void GPIO_ResetBits(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);//设置低电平

void GPIO_WriteBit(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin, BitAction BitVal);

void GPIO_Write(GPIO_TypeDef* GPIOx, uint16_t PortVal);

void GPIO_PinLockConfig(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);

//锁定GPIO配置,防止意外更改

六、实验(GPIO输出)

6.1 LED闪烁

复制代码
#include "stm32f10x.h"                  // Device header
#include "Delay.h"

int main(void)
{
	//一、使用RCC开启GPIO时钟
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
	
	//二、使用GPIO_Init函数初始化GPIO
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1; 
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOA,&GPIO_InitStructure);
	
	
	while (1)
	{
		//=====one:GPIO_WriteBit=====//
//		GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_RESET);
//		Delay_ms(500);
//		GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_SET);
//		Delay_ms(500);
		
		//=====two:GPIO_WriteBit 0/1=====//
//		GPIO_WriteBit(GPIOA,GPIO_Pin_0,(BitAction)0);
//		Delay_ms(500);
//		GPIO_WriteBit(GPIOA,GPIO_Pin_0,(BitAction)1);
//		Delay_ms(500);
		
		//=====three:GPIO_ResetBits  GPIO_SetBits=====//
		GPIO_ResetBits(GPIOA,GPIO_Pin_0);
		Delay_ms(500);
		GPIO_SetBits(GPIOA,GPIO_Pin_0);
		Delay_ms(500);
		
	}
}

6.2 LED流水灯

复制代码
#include "stm32f10x.h"                  // Device header
#include "Delay.h"

int main(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
	
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3 | GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7; 
	//GPIO_InitStructure.GPIO_Pin = GPIO_Pin_All;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOA,&GPIO_InitStructure);
	
	
	while (1)
	{
		GPIO_Write(GPIOA,~0x0001);//0000 0000 0000 0001,PA15-PA0,低电平驱动所以取反
		Delay_ms(100);
		GPIO_Write(GPIOA,~0x0002);//0000 0000 0000 0010
		Delay_ms(100);
		GPIO_Write(GPIOA,~0x0004);//0000 0000 0000 0100
		Delay_ms(100);
		GPIO_Write(GPIOA,~0x0008);//0000 0000 0000 1000
		Delay_ms(100);
		GPIO_Write(GPIOA,~0x0010);//0000 0000 0001 0000
		Delay_ms(100);
		GPIO_Write(GPIOA,~0x0020);//0000 0000 0010 0000
		Delay_ms(100);
		GPIO_Write(GPIOA,~0x0040);//0000 0000 0100 0000
		Delay_ms(100);
		GPIO_Write(GPIOA,~0x0080);//0000 0000 1000 0000
		Delay_ms(100);
	}
}

6.3 蜂鸣器

复制代码
#include "stm32f10x.h"                  // Device header
#include "Delay.h"

int main(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
	
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12; 
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB,&GPIO_InitStructure);
	
	
	while (1)
	{
		GPIO_ResetBits(GPIOB,GPIO_Pin_12);
		Delay_ms(500);
		GPIO_SetBits(GPIOB,GPIO_Pin_12);
		Delay_ms(500);
	}
}

七、实验(GPIO输入)

7.1 按键控制LED

main.c

复制代码
#include "stm32f10x.h"                  // Device header
#include "Delay.h"
#include "LED.h"
#include "key.h"

uint8_t KeyNum;

int main(void)
{
	LED_Init();//LED初始化
	Key_Init();//按键初始化
	
	while (1)
	{
		KeyNum = Key_GetNum();//判断是哪一个按键按下
		if(KeyNum == 1)
		{
			LED1_Turn();
		}
		if(KeyNum == 2)
		{
			LED2_Turn();
		}
	}
}

LED.c

复制代码
#include "stm32f10x.h"                  // Device header

void LED_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
	
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1 | GPIO_Pin_2;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOA,&GPIO_InitStructure);
	
	GPIO_SetBits(GPIOA,GPIO_Pin_1 | GPIO_Pin_2);//初始化高电平
}

//=====LED1=====//
void LED1_ON(void)
{
	GPIO_ResetBits(GPIOA,GPIO_Pin_1);
}

void LED1_OFF(void)
{
	GPIO_SetBits(GPIOA,GPIO_Pin_1);
}

void LED1_Turn(void)
{
	if(GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_1) == 0)	//读取LED输出的高低电平,控制翻转
	{
		GPIO_SetBits(GPIOA,GPIO_Pin_1);
	}
	else
	{
		GPIO_ResetBits(GPIOA,GPIO_Pin_1);
	}
	
}

//=====LED2=====//
void LED2_ON(void)
{
	GPIO_ResetBits(GPIOA,GPIO_Pin_2);
}

void LED2_OFF(void)
{
	GPIO_SetBits(GPIOA,GPIO_Pin_2);
}

void LED2_Turn(void)
{
	if(GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_2) == 0)
	{
		GPIO_SetBits(GPIOA,GPIO_Pin_2);
	}
	else
	{
		GPIO_ResetBits(GPIOA,GPIO_Pin_2);
	}
}

key.c

复制代码
#include "stm32f10x.h"                  // Device header
#include "Delay.h"

//===按键初始化===//
void Key_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
	
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;//上拉输入
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_14 | GPIO_Pin_11;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB,&GPIO_InitStructure);
}

//===获取按键返回码===//
uint8_t Key_GetNum(void)
{
	uint8_t KeyNum = 0;
	if(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_14) == 0)
	{
		Delay_ms(20);//消抖
		while(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_14) == 0);//如果不松手则卡着
		Delay_ms(20);
		KeyNum = 1;
	}	
	if(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_11) == 0)
	{
		Delay_ms(20);//消抖
		while(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_11) == 0);
		Delay_ms(20);
		KeyNum = 2;
	}
	return KeyNum;
}

7.2 光敏传感器控制蜂鸣器

main.c

复制代码
#include "stm32f10x.h"                  // Device header
#include "Delay.h"
#include "Buzzer.h"
#include "LightSensor.h"

int main(void)
{
	Buzzer_Init();//蜂鸣器初始化
	LightSensor_Init();//光敏传感器初始化
	
	while (1)
	{
		if(LightSensor_Get() == 1){	
			Buzzer_ON();
		}
		else{
			Buzzer_OFF();
		}
	}
}

Buzzer.c

复制代码
#include "stm32f10x.h"                  // Device header

//===蜂鸣器初始化===//
void Buzzer_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
	
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB,&GPIO_InitStructure);
	
	GPIO_SetBits(GPIOB,GPIO_Pin_12);//初始化高电平
}


void Buzzer_ON(void)
{
	GPIO_ResetBits(GPIOB,GPIO_Pin_12);
}

void Buzzer_OFF(void)
{
	GPIO_SetBits(GPIOB,GPIO_Pin_12);
}

void Buzzer_Turn(void)
{
	if(GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_12) == 0)	//读取蜂鸣器输出的高低电平,控制翻转
	{
		GPIO_SetBits(GPIOB,GPIO_Pin_12);
	}
	else
	{
		GPIO_ResetBits(GPIOB,GPIO_Pin_12);
	}	
}

LightSensor.c

复制代码
#include "stm32f10x.h"                  // Device header

//===光敏传感器初始化===//
void LightSensor_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
	
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;//上拉输入
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB,&GPIO_InitStructure);
}

//===获取返回码===//
uint8_t LightSensor_Get(void)
{
	return GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_13);
}

八、总结

GPIO使用方法:

①初始化时钟

②定义结构体,赋值结构体

③使用GPIO_Init()函数初始化GPIO

相关推荐
Shang180989357261 分钟前
MS2107高性能USB 2.0视频信号和音频采集,支持NTSC/PAL制式,适用于低成本视频采集设备
嵌入式硬件·fpga开发·音视频·硬件工程·信息与通信·dsp开发
学工科的皮皮志^_^2 小时前
网口学习理解
经验分享·笔记·嵌入式硬件·学习·fpga开发·以太网
沐欣工作室_lvyiyi3 小时前
基于物联网的家畜管理的监测与控制系统(论文+源码)
单片机·物联网·毕业设计·家畜管理
大牛攻城狮3 小时前
使用stm32cubeide stm32f103 freeRTOS 实现Modbus RTU协议寄存器读写过程详解
stm32·freertos·modbus·stm32cubeide·modbus rtu·stm32从机·工程代码
蓑衣客VS索尼克3 小时前
第二篇:按键交互入门:STM32 GPIO输入与消抖处理
stm32·单片机·嵌入式硬件
蓬荜生灰3 小时前
第5章—STM32工程创建
stm32·单片机·嵌入式硬件
hazy1k3 小时前
51单片机基础-定时器中断
stm32·单片机·嵌入式硬件·51单片机
恒锐丰小吕4 小时前
矽塔 SA8204 输入耐压36V 2.5A可调过流保护 集成故障报告的智能过压/过流保护芯片
嵌入式硬件·硬件工程
太空1号5 小时前
VxWorks入门小白菜鸟教程3 —— 编译运行VxWorksSDK示例hello_cmake_rtp(Windows篇)
windows·嵌入式硬件
小莞尔5 小时前
【51单片机】【protues仿真】基于51单片机火灾报警控制系统
c语言·单片机·嵌入式硬件·物联网·51单片机