stm32 - GPIO

stm32 - GPIO

  • GPIO结构图
  • GPIO原理图
    • 输入
      • 上拉/下拉/浮空
      • 施密特触发器
      • 片上外设
    • 输出
      • 推挽/开漏/关闭输出方式
    • GPIO88种模式
      • 复用输出
  • GPIO寄存器
    • 端口配置寄存器_CRL
    • 端口输入数据寄存器_IDR
    • 端口输出数据寄存器_ODR
    • 端口位设置/清除寄存器_BSRR
    • 端口位清除寄存器_BRR
    • 端口配置锁定寄存器
  • 例子
    • 点灯
    • 流水灯
    • 蜂鸣器
    • 按键和灯
    • 蜂鸣器和光敏电阻

GPIO结构图

GPIO全都挂载在APB2总线上的
每个GPIOA 都有16个引脚
寄存器:输入寄存器和输出寄存器,输出寄存器引脚输出电平,输入寄存器从引脚读取当前电平
每个寄存器有32位,但是每个寄存器都只对应16个引脚,所以只使用寄存器中的低16 位
驱动器负责增大信号的驱动能力
在这里插入图片描述

GPIO原理图

在这里插入图片描述

输入

上拉/下拉/浮空

>

为了给输入一个默认的输入电平
为了避免引脚悬空导致输入数据的不稳定,需要加上上拉电阻或下拉电阻
上拉电阻:浮空引脚,保证引脚的高电平
下拉电阻:浮空引脚,保证引脚的低电平

上拉输入:高电平输入
下拉输入:低电平输入

施密特触发器

对输入电压进行整形,防止干扰
如果输入电压大于某一阈值,输出就会瞬间升为高电平
如果输入电压小于某一阈值,输出就会瞬间降为低电平

在这里插入图片描述

片上外设

  • 模拟输入 ADC等
  • 复用输入 数字量

输出

  • 输出寄存器:写某一位控制某一个引脚(用位设置和位清楚寄存器更好)
  • 片上外设

推挽/开漏/关闭输出方式

在这里插入图片描述

  • 推挽输出

高低电平均有强驱动能力
P-MOS和N-MOS均有效
输出数据寄存器为1时,上管导通PMOS导通,下管NMOS断开,输出直接接到VDD,输出高电平
输出数据寄存器为0时,上管导通PMOS断开,下管NMOS导通,输出直接接到VSS,输出低电平

  • 开漏输出

低电平有强驱动能力,高电平没有驱动能力
P-MOS无效,N-MOS有效
输出数据寄存器为1时,上管导通PMOS无效,下管NMOS断开,输出相当于断开,相当于高阻模式
输出数据寄存器为0时,上管导通PMOS无效,下管NMOS导通,输出直接接到VSS,输出低电平

开漏输出接外部的上拉5V电源

  • 关闭输出

引脚配置为输入模式的时候
两个MOS管均无效

GPIO88种模式

在这里插入图片描述

复用输出

由片上外设进行输出

GPIO寄存器

端口配置寄存器_CRL

GPIOX_CRL
一共32位,每4位对应一个IO的配置,可配置8个引脚

端口输入数据寄存器_IDR

GPIOX_IDR
32位,低16位对应16个引脚

端口输出数据寄存器_ODR

GPIOX_ODR
32位,低16位对应16个引脚

端口位设置/清除寄存器_BSRR

GPIOX_BSRR
32位,高16位用于进行位清除,低16位用于进行位设置

端口位清除寄存器_BRR

32位,低16位用于进行位清除

端口配置锁定寄存器

端口锁定

例子

点灯

main.cpp

#include "stm32f10x.h"
#include "Delay.h"int main()
{// 初始化APB2外设时钟RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); // 配置GPIO - ODR/CLRGPIO_InitTypeDef GPIO_InitStructure;			// 配置结构体GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; 	// GPIO_Mode_Out_PP 推挽输出
//	GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_OD; 	// GPIO_Mode_Out_OD 开漏输出 	GPIO_InitStructure.GPIO_Pin=GPIO_Pin_0;			// GPIOA的0号引脚GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; // 50MHZ GPIO_Init(GPIOA,&GPIO_InitStructure); // A0推挽输出//	GPIO_SetBits(GPIOA,GPIO_Pin_0); 	// 设置为高电平
//	GPIO_ResetBits(GPIOA,GPIO_Pin_0); 	// 设置为低电平
//	GPIO_Write();
//	GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_RESET); // Bit_RESET 低电平	
//	GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_SET); // Bit_SET 高电平while (1){
//		GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_RESET); 	// Bit_RESET 低电平GPIO_ResetBits(GPIOA,GPIO_Pin_0);			// version2Delay_ms(500);
//		GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_SET); 	// Bit_SET 高电平GPIO_SetBits(GPIOA,GPIO_Pin_0);				// version2Delay_ms(500);}
}

delay.c

#include "stm32f10x.h"/*** @brief  微秒级延时* @param  xus 延时时长,范围:0~233015* @retval 无*/
void Delay_us(uint32_t xus)
{SysTick->LOAD = 72 * xus;				//设置定时器重装值SysTick->VAL = 0x00;					//清空当前计数值SysTick->CTRL = 0x00000005;				//设置时钟源为HCLK,启动定时器while(!(SysTick->CTRL & 0x00010000));	//等待计数到0SysTick->CTRL = 0x00000004;				//关闭定时器
}/*** @brief  毫秒级延时* @param  xms 延时时长,范围:0~4294967295* @retval 无*/
void Delay_ms(uint32_t xms)
{while(xms--){Delay_us(1000);}
}/*** @brief  秒级延时* @param  xs 延时时长,范围:0~4294967295* @retval 无*/
void Delay_s(uint32_t xs)
{while(xs--){Delay_ms(1000);}
} 

流水灯

#include "stm32f10x.h"
#include "Delay.h"int main()
{// 初始化APB2外设时钟RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); /* ====== 流水灯 ====== */// 配置GPIO - ODR/CLR registerGPIO_InitTypeDef GPIO_InitStructure;			// 配置结构体GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; 	// GPIO_Mode_Out_PP 推挽输出	/** #define GPIO_Pin_0                 ((uint16_t)0x0001)* #define GPIO_Pin_1                 ((uint16_t)0x0002)* #define GPIO_Pin_2                 ((uint16_t)0x0004)* #define GPIO_Pin_3                 ((uint16_t)0x0008)* #define GPIO_Pin_4                 ((uint16_t)0x0010)* #define GPIO_Pin_5                 ((uint16_t)0x0020)* #define GPIO_Pin_6                 ((uint16_t)0x0040)* #define GPIO_Pin_7                 ((uint16_t)0x0080)* GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3 | GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7* 等价于 0x0001 | 0x0002 ... 位之间并不冲突*/
//	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;			// GPIOA的0号引脚GPIO_InitStructure.GPIO_Pin=GPIO_Pin_All;GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; // 50MHZ GPIO_Init(GPIOA,&GPIO_InitStructure); // A0推挽输出while (1){for (int i=0;i<8;i++){GPIO_Write(GPIOA,~(0x0001<<i));
//			GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_RESET);Delay_ms(100);}}
}

蜂鸣器

#include "stm32f10x.h"
#include "Delay.h"int main()
{// 初始化APB2外设时钟RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE); // 配置GPIO - ODR/CLRGPIO_InitTypeDef GPIO_InitStructure;			// 配置结构体GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; 	// GPIO_Mode_Out_PP 推挽输出
//	GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_OD; 	// GPIO_Mode_Out_OD 开漏输出 	GPIO_InitStructure.GPIO_Pin= GPIO_Pin_12;			// GPIOA的0号引脚GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; // 50MHZ GPIO_Init(GPIOB,&GPIO_InitStructure); // A0推挽输出//	GPIO_SetBits(GPIOB,GPIO_Pin_12); 	// 设置为高电平
//	GPIO_ResetBits(GPIOB,GPIO_Pin_12); 	// 设置为低电平
//	GPIO_WriteBit(GPIOB,GPIO_Pin_12,Bit_RESET); // Bit_RESET 低电平	
//	GPIO_WriteBit(GPIOB,GPIO_Pin_12,Bit_SET); // Bit_SET 高电平while (1){
//		GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_RESET); 	// Bit_RESET 低电平GPIO_ResetBits(GPIOB,GPIO_Pin_12);			// version2Delay_ms(500);
//		GPIO_WriteBit(GPIOB,GPIO_Pin_12,Bit_SET); 	// Bit_SET 高电平GPIO_SetBits(GPIOB,GPIO_Pin_12);				// version2Delay_ms(500);}}

按键和灯

main.c

#include "stm32f10x.h"
#include "Delay.h"
#include "LED.h"
#include "key.h"int main()
{uint8_t keyNum=0;LED_Init();Key_Init();while (1){keyNum=key_getNum();switch (keyNum){case 1: {LED_ON(1);LED_OFF(2);keyNum=0;break;}case 11: {LED_ON(2);LED_OFF(1);keyNum=0;break;}default: break;}/* turn 切换*/ 
//		if (keyNum==1)
//		{
//			LED_ON(1);
//		}
//		if (keyNum==11)
//		{
//			LED_OFF(1);
//		}
//		}
}

LED.h

#ifndef __LED_H__
#define __LED_H__void LED_Init();
void LED_ON(unsigned char pin_num);
void LED_OFF(unsigned char pin_num);
void LED_Turn(unsigned char pin_num);#endif

LED.c

#include "stm32f10x.h"
#include "LED.h"void LED_Init()
{// 初始化APB2外设时钟RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); // 配置GPIO - ODR/CLRGPIO_InitTypeDef GPIO_InitStructure;			// 配置结构体GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; 	// GPIO_Mode_Out_PP 推挽输出
//	GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_OD; 	// GPIO_Mode_Out_OD 开漏输出 	GPIO_InitStructure.GPIO_Pin= GPIO_Pin_1 | GPIO_Pin_2;			// GPIOA的0号引脚GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; // 50MHZ GPIO_Init(GPIOA,&GPIO_InitStructure); // A0推挽输出// 默认输出高电平 不点灯GPIO_SetBits(GPIOA,GPIO_Pin_1 | GPIO_Pin_2);
}void LED_ON(unsigned char pin_num)
{switch (pin_num){case 0: {GPIO_ResetBits(GPIOA,GPIO_Pin_0);break;}case 1: {GPIO_ResetBits(GPIOA,GPIO_Pin_1);break;}case 2: {GPIO_ResetBits(GPIOA,GPIO_Pin_2);break;}case 3: {GPIO_ResetBits(GPIOA,GPIO_Pin_3);break;}case 4: {GPIO_ResetBits(GPIOA,GPIO_Pin_4);break;}case 5: {GPIO_ResetBits(GPIOA,GPIO_Pin_5);break;}case 6: {GPIO_ResetBits(GPIOA,GPIO_Pin_6);break;}case 7: {GPIO_ResetBits(GPIOA,GPIO_Pin_7);break;}		}
}void LED_OFF(unsigned char pin_num)
{switch (pin_num){case 0: {GPIO_SetBits(GPIOA,GPIO_Pin_0);break;}case 1: {GPIO_SetBits(GPIOA,GPIO_Pin_1);break;}case 2: {GPIO_SetBits(GPIOA,GPIO_Pin_2);break;}case 3: {GPIO_SetBits(GPIOA,GPIO_Pin_3);break;}case 4: {GPIO_SetBits(GPIOA,GPIO_Pin_4);break;}case 5: {GPIO_SetBits(GPIOA,GPIO_Pin_5);break;}case 6: {GPIO_SetBits(GPIOA,GPIO_Pin_6);break;}case 7: {GPIO_SetBits(GPIOA,GPIO_Pin_7);break;}		}
}void LED_Turn(unsigned char pin_num)
{switch (pin_num){case 0: {if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_0)==0){GPIO_SetBits(GPIOA,GPIO_Pin_0);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_0)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_0);}break;}case 1: {			if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_1)==0){GPIO_SetBits(GPIOA,GPIO_Pin_1);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_1)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_1);}break;}case 2: {			if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_2)==0){GPIO_SetBits(GPIOA,GPIO_Pin_2);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_2)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_2);}break;}case 3: {			if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_3)==0){GPIO_SetBits(GPIOA,GPIO_Pin_3);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_3)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_3);}break;}case 4: {			if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_4)==0){GPIO_SetBits(GPIOA,GPIO_Pin_4);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_4)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_4);}break;}case 5: {			if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_5)==0){GPIO_SetBits(GPIOA,GPIO_Pin_5);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_5)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_5);}break;}case 6: {			if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_6)==0){GPIO_SetBits(GPIOA,GPIO_Pin_6);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_6)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_6);}break;}case 7: {			if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_7)==0){GPIO_SetBits(GPIOA,GPIO_Pin_7);}else if (GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_7)==1){GPIO_ResetBits(GPIOA,GPIO_Pin_7);}break;}	}
}

key.h

#ifndef __KEY_H__
#define __KEY_H__void Key_Init();
uint8_t key_getNum();
#endif

key.c

#include "stm32f10x.h"
#include "key.h"
#include "Delay.h"void Key_Init()
{// 初始化APB2外设时钟RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);// 配置GPIO - ODR/CLRGPIO_InitTypeDef GPIO_InitStructure;			// 配置结构体GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IPU; 	// GPIO_Mode_IPU 上拉输入 - 根据原理图(内部 上拉输入配置)GPIO_InitStructure.GPIO_Pin= GPIO_Pin_1 | GPIO_Pin_11;			// GPIOB的1,11号引脚GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; // 50MHZ 仅与输入有关GPIO_Init(GPIOB,&GPIO_InitStructure); 			// B0推挽输出
}uint8_t key_getNum()
{uint8_t keyNum=0;/** GPIO_ReadInputDataBit 读取输入数据寄存器某一端口(引脚)的输入值,高低电平* GPIO_ReadInputData   读取整个输入数据寄存器* GPIO_ReadOutputDataBit 读取输出数据寄存器某一个位,输出模式下,用来看一下自己输出的是什么* GPIO_ReadOutputData 读取整个输出数据寄存器*/ // 输入数据if (GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_1)==0){Delay_ms(20);while (GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_1)==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=11;}return keyNum;
}

蜂鸣器和光敏电阻

main.c

#include "stm32f10x.h"
#include "Delay.h"
#include "LED.h"
#include "key.h"
#include "Buzzer.h"
#include "PhotoSensor.h"int main()
{uint8_t keyNum=0;Buzzer_Init(12);PhotoSensor_Init(13);while (1){/* === 蜂鸣器 ===*/
//		Buzzer_Turn(12);
//		Delay_ms(500);
//		Buzzer_Turn(12);
//		Delay_ms(500);/* === 光敏传感器 ===*/
//		PhotoSensor_Turn(13);
//		Delay_ms(500);
//		PhotoSensor_Turn(13);
//		Delay_ms(500);/* === 光敏传感器2 ,光敏传感器控制蜂鸣器 ===*/if (PhotoSensor_Get(13)==1){Buzzer_ON(12);}else{Buzzer_OFF(12);}}
}

Buzzer.h

#ifndef __BUZZER_H__
#define __BUZZER_H__void Buzzer_Init(unsigned char pin_num);
void Buzzer_ON(unsigned char pin_num);
void Buzzer_OFF(unsigned char pin_num);
void Buzzer_Turn(unsigned char pin_num);#endif

Buzzer.c

#include "stm32f10x.h"
#include "Buzzer.h"void Buzzer_Init(unsigned char pin_num)
{uint16_t GPIO_Pin_num=0;switch (pin_num){case 0: {GPIO_Pin_num=GPIO_Pin_0;break;}case 1: {GPIO_Pin_num=GPIO_Pin_1;break;}case 2: {GPIO_Pin_num=GPIO_Pin_2;break;}case 3: {GPIO_Pin_num=GPIO_Pin_3;break;}case 4: {GPIO_Pin_num=GPIO_Pin_4;break;}case 5: {GPIO_Pin_num=GPIO_Pin_5;break;}case 6: {GPIO_Pin_num=GPIO_Pin_6;break;}case 7: {GPIO_Pin_num=GPIO_Pin_7;break;}case 8: {GPIO_Pin_num=GPIO_Pin_8;break;}case 9: {GPIO_Pin_num=GPIO_Pin_9;break;}case 10: {GPIO_Pin_num=GPIO_Pin_10;break;}case 11: {GPIO_Pin_num=GPIO_Pin_11;break;}case 12: {GPIO_Pin_num=GPIO_Pin_12;break;}case 13: {GPIO_Pin_num=GPIO_Pin_13;break;}case 14: {GPIO_Pin_num=GPIO_Pin_14;break;}}// 初始化APB2外设时钟RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE); // 配置GPIO - ODR/CLRGPIO_InitTypeDef GPIO_InitStructure;			// 配置结构体GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; 	// GPIO_Mode_Out_PP 推挽输出
//	GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_OD; 	// GPIO_Mode_Out_OD 开漏输出 	GPIO_InitStructure.GPIO_Pin= GPIO_Pin_num;			// GPIOB的0号引脚GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; // 50MHZ GPIO_Init(GPIOB,&GPIO_InitStructure); // A0推挽输出// 默认输出高电平 不点灯GPIO_SetBits(GPIOB,GPIO_Pin_num);
}void Buzzer_ON(unsigned char pin_num)
{switch (pin_num){case 0: {GPIO_ResetBits(GPIOB,GPIO_Pin_0);break;}case 1: {GPIO_ResetBits(GPIOB,GPIO_Pin_1);break;}case 2: {GPIO_ResetBits(GPIOB,GPIO_Pin_2);break;}case 3: {GPIO_ResetBits(GPIOB,GPIO_Pin_3);break;}case 4: {GPIO_ResetBits(GPIOB,GPIO_Pin_4);break;}case 5: {GPIO_ResetBits(GPIOB,GPIO_Pin_5);break;}case 6: {GPIO_ResetBits(GPIOB,GPIO_Pin_6);break;}case 7: {GPIO_ResetBits(GPIOB,GPIO_Pin_7);break;}case 8: {GPIO_ResetBits(GPIOB,GPIO_Pin_8);break;}case 9: {GPIO_ResetBits(GPIOB,GPIO_Pin_9);break;}case 10: {GPIO_ResetBits(GPIOB,GPIO_Pin_10);break;}case 11: {GPIO_ResetBits(GPIOB,GPIO_Pin_11);break;}case 12: {GPIO_ResetBits(GPIOB,GPIO_Pin_12);break;}case 13: {GPIO_ResetBits(GPIOB,GPIO_Pin_13);break;}case 14: {GPIO_ResetBits(GPIOB,GPIO_Pin_14);break;}case 15: {GPIO_ResetBits(GPIOB,GPIO_Pin_15);break;}		}
}void Buzzer_OFF(unsigned char pin_num)
{switch (pin_num){case 0: {GPIO_SetBits(GPIOB,GPIO_Pin_0);break;}case 1: {GPIO_SetBits(GPIOB,GPIO_Pin_1);break;}case 2: {GPIO_SetBits(GPIOB,GPIO_Pin_2);break;}case 3: {GPIO_SetBits(GPIOB,GPIO_Pin_3);break;}case 4: {GPIO_SetBits(GPIOB,GPIO_Pin_4);break;}case 5: {GPIO_SetBits(GPIOB,GPIO_Pin_5);break;}case 6: {GPIO_SetBits(GPIOB,GPIO_Pin_6);break;}case 7: {GPIO_SetBits(GPIOB,GPIO_Pin_7);break;}case 8: {GPIO_SetBits(GPIOB,GPIO_Pin_8);break;}case 9: {GPIO_SetBits(GPIOB,GPIO_Pin_9);break;}case 10: {GPIO_SetBits(GPIOB,GPIO_Pin_10);break;}case 11: {GPIO_SetBits(GPIOB,GPIO_Pin_11);break;}case 12: {GPIO_SetBits(GPIOB,GPIO_Pin_12);break;}case 13: {GPIO_SetBits(GPIOB,GPIO_Pin_13);break;}case 14: {GPIO_SetBits(GPIOB,GPIO_Pin_14);break;}case 15: {GPIO_SetBits(GPIOB,GPIO_Pin_15);break;}			}
}void Buzzer_Turn(unsigned char pin_num)
{// version 2uint16_t GPIO_Pin_num=0;switch (pin_num){case 0: {GPIO_Pin_num=GPIO_Pin_0;break;}case 1: {GPIO_Pin_num=GPIO_Pin_1;break;}case 2: {GPIO_Pin_num=GPIO_Pin_2;break;}case 3: {GPIO_Pin_num=GPIO_Pin_3;break;}case 4: {GPIO_Pin_num=GPIO_Pin_4;break;}case 5: {GPIO_Pin_num=GPIO_Pin_5;break;}case 6: {GPIO_Pin_num=GPIO_Pin_6;break;}case 7: {GPIO_Pin_num=GPIO_Pin_7;break;}case 8: {GPIO_Pin_num=GPIO_Pin_8;break;}case 9: {GPIO_Pin_num=GPIO_Pin_9;break;}case 10: {GPIO_Pin_num=GPIO_Pin_10;break;}case 11: {GPIO_Pin_num=GPIO_Pin_11;break;}case 12: {GPIO_Pin_num=GPIO_Pin_12;break;}case 13: {GPIO_Pin_num=GPIO_Pin_13;break;}case 14: {GPIO_Pin_num=GPIO_Pin_14;break;}}if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_num)==0){GPIO_SetBits(GPIOB,GPIO_Pin_num);}else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_num)==1){GPIO_ResetBits(GPIOB,GPIO_Pin_num);}// version 1
//	switch (pin_num)
//	{
//		case 0: {
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_0)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_0);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_0)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_0);
//			}
//			break;
//		}
//		case 1: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_1)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_1);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_1)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_1);
//			}
//			break;
//		}
//		case 2: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_2)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_2);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_2)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_2);
//			}
//			break;
//		}
//		case 3: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_3)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_3);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_3)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_3);
//			}
//			break;
//		}
//		case 4: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_4)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_4);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_4)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_4);
//			}
//			break;
//		}
//		case 5: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_5)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_5);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_5)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_5);
//			}
//			break;
//		}
//		case 6: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_6)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_6);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_6)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_6);
//			}
//			break;
//		}
//		case 7: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_7)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_7);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_7)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_7);
//			}
//			break;
//		}	
//	}
}

photosensor.h

#ifndef __PHOTOSENSOR_H__
#define __PHOTOSENSOR_H__void PhotoSensor_Init(unsigned char pin_num);
void PhotoSensor_ON(unsigned char pin_num);
void PhotoSensor_OFF(unsigned char pin_num);
void PhotoSensor_Turn(unsigned char pin_num);
uint8_t PhotoSensor_Get(unsigned char pin_num);#endif

photosensor.c

#include "stm32f10x.h"
#include "PhotoSensor.h"void PhotoSensor_Init(unsigned char pin_num)
{uint16_t GPIO_Pin_num=0;switch (pin_num){case 0: {GPIO_Pin_num=GPIO_Pin_0;break;}case 1: {GPIO_Pin_num=GPIO_Pin_1;break;}case 2: {GPIO_Pin_num=GPIO_Pin_2;break;}case 3: {GPIO_Pin_num=GPIO_Pin_3;break;}case 4: {GPIO_Pin_num=GPIO_Pin_4;break;}case 5: {GPIO_Pin_num=GPIO_Pin_5;break;}case 6: {GPIO_Pin_num=GPIO_Pin_6;break;}case 7: {GPIO_Pin_num=GPIO_Pin_7;break;}case 8: {GPIO_Pin_num=GPIO_Pin_8;break;}case 9: {GPIO_Pin_num=GPIO_Pin_9;break;}case 10: {GPIO_Pin_num=GPIO_Pin_10;break;}case 11: {GPIO_Pin_num=GPIO_Pin_11;break;}case 12: {GPIO_Pin_num=GPIO_Pin_12;break;}case 13: {GPIO_Pin_num=GPIO_Pin_13;break;}case 14: {GPIO_Pin_num=GPIO_Pin_14;break;}}// 初始化APB2外设时钟RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE); // 配置GPIO - ODR/CLRGPIO_InitTypeDef GPIO_InitStructure;			// 配置结构体GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IPU; 	// 上拉输入	GPIO_InitStructure.GPIO_Pin= GPIO_Pin_num;			// GPIOB的0号引脚GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; // 50MHZ GPIO_Init(GPIOB,&GPIO_InitStructure);}void PhotoSensor_ON(unsigned char pin_num)
{switch (pin_num){case 0: {GPIO_ResetBits(GPIOB,GPIO_Pin_0);break;}case 1: {GPIO_ResetBits(GPIOB,GPIO_Pin_1);break;}case 2: {GPIO_ResetBits(GPIOB,GPIO_Pin_2);break;}case 3: {GPIO_ResetBits(GPIOB,GPIO_Pin_3);break;}case 4: {GPIO_ResetBits(GPIOB,GPIO_Pin_4);break;}case 5: {GPIO_ResetBits(GPIOB,GPIO_Pin_5);break;}case 6: {GPIO_ResetBits(GPIOB,GPIO_Pin_6);break;}case 7: {GPIO_ResetBits(GPIOB,GPIO_Pin_7);break;}case 8: {GPIO_ResetBits(GPIOB,GPIO_Pin_8);break;}case 9: {GPIO_ResetBits(GPIOB,GPIO_Pin_9);break;}case 10: {GPIO_ResetBits(GPIOB,GPIO_Pin_10);break;}case 11: {GPIO_ResetBits(GPIOB,GPIO_Pin_11);break;}case 12: {GPIO_ResetBits(GPIOB,GPIO_Pin_12);break;}case 13: {GPIO_ResetBits(GPIOB,GPIO_Pin_13);break;}case 14: {GPIO_ResetBits(GPIOB,GPIO_Pin_14);break;}case 15: {GPIO_ResetBits(GPIOB,GPIO_Pin_15);break;}		}
}void PhotoSensor_OFF(unsigned char pin_num)
{switch (pin_num){case 0: {GPIO_SetBits(GPIOB,GPIO_Pin_0);break;}case 1: {GPIO_SetBits(GPIOB,GPIO_Pin_1);break;}case 2: {GPIO_SetBits(GPIOB,GPIO_Pin_2);break;}case 3: {GPIO_SetBits(GPIOB,GPIO_Pin_3);break;}case 4: {GPIO_SetBits(GPIOB,GPIO_Pin_4);break;}case 5: {GPIO_SetBits(GPIOB,GPIO_Pin_5);break;}case 6: {GPIO_SetBits(GPIOB,GPIO_Pin_6);break;}case 7: {GPIO_SetBits(GPIOB,GPIO_Pin_7);break;}case 8: {GPIO_SetBits(GPIOB,GPIO_Pin_8);break;}case 9: {GPIO_SetBits(GPIOB,GPIO_Pin_9);break;}case 10: {GPIO_SetBits(GPIOB,GPIO_Pin_10);break;}case 11: {GPIO_SetBits(GPIOB,GPIO_Pin_11);break;}case 12: {GPIO_SetBits(GPIOB,GPIO_Pin_12);break;}case 13: {GPIO_SetBits(GPIOB,GPIO_Pin_13);break;}case 14: {GPIO_SetBits(GPIOB,GPIO_Pin_14);break;}case 15: {GPIO_SetBits(GPIOB,GPIO_Pin_15);break;}			}
}void PhotoSensor_Turn(unsigned char pin_num)
{// version 2uint16_t GPIO_Pin_num=0;switch (pin_num){case 0: {GPIO_Pin_num=GPIO_Pin_0;break;}case 1: {GPIO_Pin_num=GPIO_Pin_1;break;}case 2: {GPIO_Pin_num=GPIO_Pin_2;break;}case 3: {GPIO_Pin_num=GPIO_Pin_3;break;}case 4: {GPIO_Pin_num=GPIO_Pin_4;break;}case 5: {GPIO_Pin_num=GPIO_Pin_5;break;}case 6: {GPIO_Pin_num=GPIO_Pin_6;break;}case 7: {GPIO_Pin_num=GPIO_Pin_7;break;}case 8: {GPIO_Pin_num=GPIO_Pin_8;break;}case 9: {GPIO_Pin_num=GPIO_Pin_9;break;}case 10: {GPIO_Pin_num=GPIO_Pin_10;break;}case 11: {GPIO_Pin_num=GPIO_Pin_11;break;}case 12: {GPIO_Pin_num=GPIO_Pin_12;break;}case 13: {GPIO_Pin_num=GPIO_Pin_13;break;}case 14: {GPIO_Pin_num=GPIO_Pin_14;break;}}if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_num)==0){GPIO_SetBits(GPIOB,GPIO_Pin_num);}else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_num)==1){GPIO_ResetBits(GPIOB,GPIO_Pin_num);}// version 1
//	switch (pin_num)
//	{
//		case 0: {
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_0)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_0);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_0)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_0);
//			}
//			break;
//		}
//		case 1: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_1)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_1);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_1)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_1);
//			}
//			break;
//		}
//		case 2: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_2)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_2);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_2)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_2);
//			}
//			break;
//		}
//		case 3: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_3)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_3);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_3)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_3);
//			}
//			break;
//		}
//		case 4: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_4)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_4);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_4)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_4);
//			}
//			break;
//		}
//		case 5: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_5)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_5);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_5)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_5);
//			}
//			break;
//		}
//		case 6: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_6)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_6);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_6)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_6);
//			}
//			break;
//		}
//		case 7: {			
//			if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_7)==0)
//			{
//				GPIO_SetBits(GPIOB,GPIO_Pin_7);
//			}
//			else if (GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_7)==1)
//			{
//				GPIO_ResetBits(GPIOB,GPIO_Pin_7);
//			}
//			break;
//		}	
//	}
}uint8_t PhotoSensor_Get(unsigned char pin_num)
{uint16_t GPIO_Pin_num=0;switch (pin_num){case 0: {GPIO_Pin_num=GPIO_Pin_0;break;}case 1: {GPIO_Pin_num=GPIO_Pin_1;break;}case 2: {GPIO_Pin_num=GPIO_Pin_2;break;}case 3: {GPIO_Pin_num=GPIO_Pin_3;break;}case 4: {GPIO_Pin_num=GPIO_Pin_4;break;}case 5: {GPIO_Pin_num=GPIO_Pin_5;break;}case 6: {GPIO_Pin_num=GPIO_Pin_6;break;}case 7: {GPIO_Pin_num=GPIO_Pin_7;break;}case 8: {GPIO_Pin_num=GPIO_Pin_8;break;}case 9: {GPIO_Pin_num=GPIO_Pin_9;break;}case 10: {GPIO_Pin_num=GPIO_Pin_10;break;}case 11: {GPIO_Pin_num=GPIO_Pin_11;break;}case 12: {GPIO_Pin_num=GPIO_Pin_12;break;}case 13: {GPIO_Pin_num=GPIO_Pin_13;break;}case 14: {GPIO_Pin_num=GPIO_Pin_14;break;}}return GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_num);
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/92098.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Window 安装多个版本的 java 并按需切换

1、按需下载对应版本的 java 官网链接&#xff1a;Java Downloads | Oracle 2、执行安装程序&#xff0c;根据安装向导一步一步走就行&#xff0c;每个版本安装在不同的目录下。 3、配置环境变量 a&#xff09;为每个版本 java 新建不同名称的 JAVA_HOME 系统变量&#xff0…

【Java 进阶篇】JDBC插入数据详解

在Java应用程序中&#xff0c;与数据库交互是一项常见的任务。其中&#xff0c;插入数据操作是一种基本的数据库操作之一。本文将详细介绍如何使用Java JDBC&#xff08;Java Database Connectivity&#xff09;来执行插入数据操作。无论您是初学者还是有一定经验的开发人员&am…

数仓精品理论-做大数据还有没有前途?

数仓精品理论-做大数据还有没有前途&#xff1f; 做大数据还有没有前途&#xff1f;大数据三要三不要我来讲讲大数据前景 做大数据还有没有前途&#xff1f; 先说&#xff0c;答案是肯定的&#xff0c;但一定要记住三要三不要。 datapulse官网&#xff1a; github:https://data…

LeetCode 热题 HOT 100:回溯专题

LeetCode 热题 HOT 100&#xff1a;https://leetcode.cn/problem-list/2cktkvj/ 文章目录 17. 电话号码的字母组合22. 括号生成39. 组合总和46. 全排列补充&#xff1a;47. 全排列 II &#xff08;待优化)78. 子集79. 单词搜索124. 二叉树中的最大路径和200. 岛屿数量437. 路径…

手机电脑数码小程序商城的作用是什么

手机几乎是每个成年人人手一个以上&#xff0c;市场非常大&#xff0c;加之产品更新迭代速度快&#xff0c;每年都会推出多个型号、造型等&#xff0c;因此对高收入群体或爱机人群来说&#xff0c;新手机往往一年或二年时间就会换&#xff0c;或者直接购买当备用机等。 每个城…

关于解决 unable to start ssh-agent service, error :1058

前言 操作系统&#xff1a;win11 命令终端&#xff1a;Powershell 当我在终端输入命令 启动 ssh-agent 代理的时候 ssh-agent -s 很不幸出现了 unable to start ssh-agent service, error :1058以下错误 问题的解决 查看我们ssh-agent 服务是否运行&#xff0c;执行如下命令…

快看看你的手机有没有:谷歌Android全面封杀此类软件!

谷歌坐不住了&#xff0c;因为Android应用商店中&#xff0c;充斥着大量可窃取用户数据的应用&#xff0c;所以必然要出手整治了。 一款名叫“SonicSpy”软件是整个事情的导火索&#xff0c;而该应用是典型的窃取用户数据的应用&#xff0c;其除了可以从手机中提取个人数据外&…

C++ 学习系列 -- std::stack 与 std::queue

一 std::stack 与 std::queue 分别是什么&#xff1f; 两者均是 c 中的序列化容器&#xff0c;区别在于&#xff1a; std::stack 元素是先进后出 std::queue 元素是先进先出 二 std::stack 与 std::queue 原理 1 std:statck 2. std::queue 两者底层容器可以是 list 也可以…

黑豹程序员-架构师学习路线图-百科:HTML-网页三剑客

为什么需要HTML 在网站技术发达之前&#xff0c;千年来我们获取信息是通过书籍。电脑流行后我们看文章、小说通过txt文件。看图通过单独的图片流量工具看单个的图片文件。 而HTML把文字和图片一起展示&#xff0c;让今天的电子书成为可能。 另外一点&#xff0c;我们的信息是…

蜂蜜配送销售商城小程序的作用是什么

蜂蜜是农产品中重要的一个类目&#xff0c;其受众之广市场需求量大&#xff0c;但由于非人人必需品&#xff0c;因此传统线下门店经营也面临着痛点&#xff0c;线上入驻平台也有很多限制难以打造自有品牌&#xff0c;无法管理销售商品及会员、营销等&#xff0c;缺少自营渠道&a…

Linux常见操作命令(1)

​ 前言&#xff1a;作者也是初学Linux&#xff0c;可能总结的还不是很到位 ♈️今日夜电波&#xff1a;达尔文—林俊杰 0:30━━━━━━️&#x1f49f;──────── 4:06 &#x1f504; ◀️ …

集合在多线程下安全问题

如果在多线程下&#xff0c;同时操作同一个数据源&#xff0c;就会出现数据安全问题&#xff1a; A线程取出值为10&#xff0c;准备加5. 同时B线程也取出来10&#xff0c;减了5 C取出的时候有可能时15&#xff0c;也有可能时5。产生了数据安全问题。 方法有很多例如&#xff1a…

Acwing 143. 最大异或对

Acwing 143. 最大异或对 题目描述思路讲解代码展示 题目描述 思路讲解 这道题的启示是&#xff1a;字典树不单单可以高效存储和查找字符串集合,还可以存储二进制数字 思路:将每个数以二进制方式存入字典树,找的时候从最高位去找有无该位的异. 代码展示 #include<iostream…

uboot启动流程-涉及_main汇编函数

一. uboot启动流程涉及函数 本文简单分析一下 save_boot_params_ret调用的函数&#xff1a;_main汇编函数。 本文继之前文章的学习&#xff0c;地址如下&#xff1a; uboot启动流程-涉及s_init汇编函数_凌肖战的博客-CSDN博客 二. uboot启动流程涉及的 _main汇编函数 经过之…

鞋类 整鞋试验方法 剥离强度

声明 本文是学习GB-T 3903.3-2011 鞋类 整鞋试验方法 剥离强度. 而整理的学习笔记,分享出来希望更多人受益,如果存在侵权请及时联系我们 1 范围 GB/T 3903 的本部分规定了整鞋鞋底与鞋帮或外底与外中底之间剥离强度的试验方法。 本部分适用于采用模压、硫化、注塑、灌注、胶…

Springboot对MVC、tomcat扩展配置

Springboot在web层的开发基本都是采用Springmvc框架技术&#xff0c;但是Springmvc中的某些配置在boot是没有的&#xff0c;我们就应该根据自己的需求进行对mvc扩展配置 Springboot1.x版本如何配置 通过注解Configuration一个类&#xff0c;继承webmvcconfigureradapter&#…

macOS 14 Sonoma 如何删除不需要的 4k 动态壁纸

概览 在升级到 macOS 14&#xff08;Sonoma&#xff09;之后&#xff0c;小伙伴们惊喜发现  提供了诸多高清&#xff08;4k&#xff09;动态壁纸的支持。 现在&#xff0c;从锁屏到解锁进入桌面动态到静态的切换一气呵成、无比丝滑。 壁纸显现可谓是有了“天水相连为一色&…

【SpringBoot学习】收藏的学习资料,精!

文章目录 Spring实战&#xff08;第五版&#xff09;&#xff1a; https://potoyang.gitbook.io/spring-in-action-v5/di-er-bu-fen-ji-cheng-spring南京大学-软件体系架构,结合SpringBoot Spring实战&#xff08;第五版&#xff09;&#xff1a; https://potoyang.gitbook.io/…

【农业生产模拟】WOFOST模型与PCSE模型实践

查看原文>>>【农业生产模拟】WOFOST模型与PCSE模型实践 WOFOST&#xff08;WorldFoodStudies&#xff09;和PCSE&#xff08;PythonCropSimulationEnvironment&#xff09;是两个用于农业生产模拟的模型&#xff1a;WOFOST是一个经过多年开发和验证的模型&#xff0c…

ElementUI之增删改及表单验证

⭐⭐本文章收录与ElementUI原创专栏&#xff1a;ElementUI专栏 ⭐⭐ ElementUI的官网&#xff1a;ElementUI官网 目录 一.前言 二.使用ElementUI完成增删改 2.1 后台代码 2.2 前端代码 三.使用ElementUI完成表单验证 一.前言 本章是继上一篇的基础之上在做完善&#xff0…