STM32學習_GPIO簡介

一、GPIO輸出部分

STM32從入門到精通—GPIO簡介_初始化

STM32從入門到精通—GPIO簡介_初始化_02

STM32從入門到精通—GPIO簡介_#include_03

STM32從入門到精通—GPIO簡介_#include_04

STM32從入門到精通—GPIO簡介_#include_05

STM32從入門到精通—GPIO簡介_#include_06

STM32從入門到精通—GPIO簡介_初始化_07

- 實現 LED 點亮的代碼:

#include "stm32f10x.h"                  // Device header

int main(void)
{
	// 開啓 RCC 時鐘
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
	// 配置結構體,用於初始化 GPIO
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	// 初始化GPIOA
	GPIO_Init(GPIOA,&GPIO_InitStructure);
	
	GPIO_ResetBits(GPIOA,GPIO_Pin_0);   // 設置 GPIOA,GPIO_Pin_0 為低電平,燈亮
	GPIO_SetBits(GPIOA,GPIO_Pin_0);     // 設置 GPIOA,GPIO_Pin_0 為高電平,燈滅
	
	GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_RESET);			// 設置 GPIOA,GPIO_Pin_0 為低電平,燈亮
	GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_SET);		  	// 設置 GPIOA,GPIO_Pin_0 為低電平,燈滅
	
	while(1)
	{
		
	}
}

- 實現 LED 閃爍的代碼:

#include "stm32f10x.h"                  // Device header
#include "Delay.h" 

int main(void)
{
	// 開啓 RCC 時鐘
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
	// 配置結構體,用於初始化 GPIO
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	// 初始化GPIOA
	GPIO_Init(GPIOA,&GPIO_InitStructure);
	
	while(1)
	{
		GPIO_ResetBits(GPIOA,GPIO_Pin_0);					// 設置 GPIOA,GPIO_Pin_0 為低電平,燈亮
		Delay_ms(500);
		GPIO_SetBits(GPIOA,GPIO_Pin_0);						// 設置 GPIOA,GPIO_Pin_0 為低電平,燈滅
		Delay_ms(500);
		
		GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_RESET);			// 設置 GPIOA,GPIO_Pin_0 為低電平,燈亮
		Delay_ms(500);
		GPIO_WriteBit(GPIOA,GPIO_Pin_0,Bit_SET);		  	// 設置 GPIOA,GPIO_Pin_0 為低電平,燈滅
		Delay_ms(500);
	}
}

STM32從入門到精通—GPIO簡介_引腳_08

STM32從入門到精通—GPIO簡介_引腳_09

- 實現 LED 流水燈的代碼:

#include "stm32f10x.h"                  // Device header
#include "Delay.h" 

int main(void)
{
	// 開啓 RCC 時鐘
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
	// 配置結構體,用於初始化 GPIO
	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_InitStructure.GPIO_Pin = GPIO_Pin_All;   		// 選擇全部的端口
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	// 初始化GPIOA
	GPIO_Init(GPIOA,&GPIO_InitStructure);
	
	while(1)
	{
		GPIO_Write(GPIOA,~0x0001);			// 0000 0000 0000 0001
		Delay_ms(500);
		GPIO_Write(GPIOA,~0x0002);			// 0000 0000 0000 0010
		Delay_ms(500);
		GPIO_Write(GPIOA,~0x0004);			// 0000 0000 0000 0100
		Delay_ms(500);
		GPIO_Write(GPIOA,~0x0008);			// 0000 0000 0000 1000
		Delay_ms(500);
		GPIO_Write(GPIOA,~0x0010);			// 0000 0000 0001 0000
		Delay_ms(500);
		GPIO_Write(GPIOA,~0x0020);			// 0000 0000 0010 0000
		Delay_ms(500);
		GPIO_Write(GPIOA,~0x0040);			// 0000 0000 0100 0000
		Delay_ms(500);
		GPIO_Write(GPIOA,~0x0080);			// 0000 0000 1000 0000
		Delay_ms(500);
	}
}

STM32從入門到精通—GPIO簡介_初始化_10

- 實現 蜂鳴器的代碼:

#include "stm32f10x.h"                  // Device header
#include "Delay.h" 

int main(void)
{
	// 開啓 RCC 時鐘,易錯點:時鐘沒有從 GPIOA 換成 GPIOB,導致蜂鳴器不響
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
	// 配置結構體,用於初始化 GPIO 
	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;
	// 初始化GPIOA
	GPIO_Init(GPIOB,&GPIO_InitStructure);
	
	while(1)
	{
		// 輸出低電平,蜂鳴器響
		GPIO_ResetBits(GPIOB,GPIO_Pin_12);
		Delay_ms(100);
		GPIO_SetBits(GPIOB,GPIO_Pin_12);
		Delay_ms(100);
		GPIO_ResetBits(GPIOB,GPIO_Pin_12);
		Delay_ms(100);
		GPIO_SetBits(GPIOB,GPIO_Pin_12);
		Delay_ms(700);		
	}
}

二、GPIO輸入部分

STM32從入門到精通—GPIO簡介_初始化_11

STM32從入門到精通—GPIO簡介_引腳_12

STM32從入門到精通—GPIO簡介_#include_13

STM32從入門到精通—GPIO簡介_引腳_14

STM32從入門到精通—GPIO簡介_引腳_15

STM32從入門到精通—GPIO簡介_引腳_16

STM32從入門到精通—GPIO簡介_初始化_17

STM32從入門到精通—GPIO簡介_初始化_18

STM32從入門到精通—GPIO簡介_#include_19

STM32從入門到精通—GPIO簡介_初始化_20

STM32從入門到精通—GPIO簡介_引腳_21

STM32從入門到精通—GPIO簡介_初始化_22

STM32從入門到精通—GPIO簡介_初始化_23

目錄結構,創建代碼前先完善目錄,並在魔術棒內添加路徑配置

- 按鍵控制代碼展示:

main.c 主函數代碼:

#include "stm32f10x.h"                  // Device header
#include "Delay.h" 
#include "LED.h"
#include "Key.h"

uint8_t KeyNum;

int main(void)
{
	LED_Init();
	Key_Init();
	
	while(1)
	{
		KeyNum = Key_GetNum();
		if(KeyNum == 1)
		{
			LED1_Turn();
		}
		if(KeyNum == 2)
		{
			LED2_Turn();
		}
	}
}

LED.c 和 LED.h 代碼:

#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);
}

void LED1_ON(void)     // 點亮 Led1
{
	GPIO_ResetBits(GPIOA,GPIO_Pin_1);
}
void LED1_OFF(void)     // 熄滅 Led1
{
	GPIO_SetBits(GPIOA,GPIO_Pin_1);
}

void LED1_Turn(void)     // 翻轉 Led1 GPIO,實現按下點亮,再按下熄滅
{
	if(GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_1) == 0)		 // 關於這個函數,下面會給個表格
	{
		GPIO_SetBits(GPIOA,GPIO_Pin_1);
	}
	else
	{
		GPIO_ResetBits(GPIOA,GPIO_Pin_1);
	}	
}

// 和上面一樣,這裏不贅述
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);
	}	
}
#ifndef __LED_H
#define __LED_H

void LED_Init(void);

void LED1_ON(void);
void LED1_OFF(void);
void LED2_ON(void);
void LED2_OFF(void);

void LED1_Turn(void);
void LED2_Turn(void);


#endif

Key.c 和 Key.h 代碼:

#include "stm32f10x.h"                  // Device header
#include "Delay.h"

/**
  * 函    數:按鍵初始化
  * 參    數:無
  * 返 回 值:無
  */
void Key_Init(void)
{
	/*開啓時鐘*/
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);		//開啓GPIOB的時鐘
	
	/*GPIO初始化*/
	GPIO_InitTypeDef GPIO_InitStructure;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1 | GPIO_Pin_11;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB, &GPIO_InitStructure);						//將PB1和PB11引腳初始化為上拉輸入
}

/**
  * 函    數:按鍵獲取鍵碼
  * 參    數:無
  * 返 回 值:按下按鍵的鍵碼值,範圍:0~2,返回0代表沒有按鍵按下
  * 注意事項:此函數是阻塞式操作,當按鍵按住不放時,函數會卡住,直到按鍵鬆手
  */
uint8_t Key_GetNum(void)
{
	uint8_t KeyNum = 0;		//定義變量,默認鍵碼值為0
	
	if (GPIO_ReadInputDataBit(GPIOB, GPIO_Pin_1) == 0)			//讀PB1輸入寄存器的狀態,如果為0,則代表按鍵1按下
	{
		Delay_ms(20);											//延時消抖
		while (GPIO_ReadInputDataBit(GPIOB, GPIO_Pin_1) == 0);	//等待按鍵鬆手
		Delay_ms(20);											//延時消抖
		KeyNum = 1;												//置鍵碼為1
	}
	
	if (GPIO_ReadInputDataBit(GPIOB, GPIO_Pin_11) == 0)			//讀PB11輸入寄存器的狀態,如果為0,則代表按鍵2按下
	{
		Delay_ms(20);											//延時消抖
		while (GPIO_ReadInputDataBit(GPIOB, GPIO_Pin_11) == 0);	//等待按鍵鬆手
		Delay_ms(20);											//延時消抖
		KeyNum = 2;												//置鍵碼為2
	}
	
	return KeyNum;			//返回鍵碼值,如果沒有按鍵按下,所有if都不成立,則鍵碼為默認值0
}
#ifndef __KEY_H
#define __KEY_H

void Key_Init(void);
uint8_t Key_GetNum(void);

#endif

表格只保留小白最常用的操作,用PA1(通用引腳)PC13(LED常用)做示例,重點標註你提到的GPIO_ReadOutputDataBit

操作類型

標準庫函數

功能説明(大白話)

示例代碼(直接能用)

開啓GPIO時鐘

RCC_APB2PeriphClockCmd()

給GPIO端口“通電”,必須第一步做

開啓GPIOA時鐘:

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);開啓GPIOC時鐘:

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE);

GPIO引腳初始化

GPIO_Init()

配置引腳的工作模式(比如輸出/輸入)

配置PA1為推輓輸出:

c<br>GPIO_InitTypeDef GPIO_InitStruct;<br>GPIO_InitStruct.GPIO_Pin = GPIO_Pin_1;<br>GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;<br>GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;<br>GPIO_Init(GPIOA, &GPIO_InitStruct);<br>

設置引腳為高電平

GPIO_SetBits()

把引腳拉成高電平(比如讓PC13的LED熄滅)

PA1設為高電平:

GPIO_SetBits(GPIOA, GPIO_Pin_1);PC13設為高電平:

GPIO_SetBits(GPIOC, GPIO_Pin_13);

設置引腳為低電平

GPIO_ResetBits()

把引腳拉成低電平(比如讓PC13的LED點亮)

PA1設為低電平:

GPIO_ResetBits(GPIOA, GPIO_Pin_1);PC13設為低電平:

GPIO_ResetBits(GPIOC, GPIO_Pin_13);

讀取引腳的輸出電平

GPIO_ReadOutputDataBit()

查“軟件設置的引腳電平”(不是實際外部電平)

讀取PA1的輸出電平:

c<br>// 返回SET(1)表示高電平,RESET(0)表示低電平<br>uint8_t level = GPIO_ReadOutputDataBit(GPIOA, GPIO_Pin_1);<br>

讀取引腳的實際輸入電平

GPIO_ReadInputDataBit()

查“引腳實際接的外部電平”(比如讀按鍵)

讀取PA0的實際電平:

uint8_t key_level = GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_0);

讀取整個端口的輸出數據

GPIO_ReadOutputData()

一次性讀整個GPIO口的所有引腳輸出電平(少用)

讀取GPIOA所有引腳輸出電平:

uint16_t data = GPIO_ReadOutputData(GPIOA);

讀取整個端口的輸入數據

GPIO_ReadInputData()

一次性讀整個GPIO口的所有引腳實際電平(少用)

讀取GPIOA所有引腳實際電平:

uint16_t data = GPIO_ReadInputData(GPIOA);

- GPIO操作的3個核心步驟

無論控制LED還是讀按鍵,都要按這個流程來,少一步都不行

步驟1:開啓GPIO時鐘

// 以操作PC13(LED)為例,開啓GPIOC時鐘
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE);

小白提醒:忘記開時鐘是最常見的錯誤,代碼寫了也沒反應!

步驟2:初始化GPIO引腳

需要用一個叫GPIO_InitTypeDef結構體來配置引腳參數,小白只需關注3個參數:

  • GPIO_Pin:選要操作的引腳(比如GPIO_Pin_13
  • GPIO_Mode:引腳模式(常用2種:
  • GPIO_Mode_Out_PP:推輓輸出(適合驅動LED、繼電器,最常用)
  • GPIO_Mode_IPU:上拉輸入(適合讀按鍵,避免引腳懸空)
  • GPIO_Speed:輸出速度(選GPIO_Speed_50MHz就行,對LED、按鍵無影響)

示例(配置PC13為推輓輸出):

GPIO_InitTypeDef GPIO_InitStruct;  // 定義配置結構體
GPIO_InitStruct.GPIO_Pin = GPIO_Pin_13;  // 選擇PC13引腳
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;  // 推輓輸出模式
GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;  // 輸出速度50MHz
GPIO_Init(GPIOC, &GPIO_InitStruct);  // 執行初始化

步驟3:用函數操作引腳(電平設置/讀取)

// 比如讓PC13點亮(低電平)
GPIO_ResetBits(GPIOC, GPIO_Pin_13);
// 讀取PC13的輸出電平
uint8_t level = GPIO_ReadOutputDataBit(GPIOC, GPIO_Pin_13);

- 關鍵函數詳解:GPIO_ReadOutputDataBit

小白最容易搞混“讀取輸出電平”和“讀取輸入電平”,用表格對比一下:

函數

讀取的是什麼?

舉個例子(PC13)

GPIO_ReadOutputDataBit()

讀取軟件設置的電平(輸出寄存器ODR的值)

你用GPIO_SetBits()把PC13設為高電平,即使外部電路把PC13拉低,這個函數仍返回高電平(SET)

GPIO_ReadInputDataBit()

讀取引腳實際的外部電平(輸入寄存器IDR的值)

你用GPIO_SetBits()把PC13設為高電平,但外部電路把PC13拉低,這個函數返回低電平(RESET)

小白總結

  • 想知道“我讓引腳輸出什麼電平”,用GPIO_ReadOutputDataBit()
  • 想知道“引腳實際接的是什麼電平”,用GPIO_ReadInputDataBit()

- 光敏電阻控制蜂鳴器

STM32從入門到精通—GPIO簡介_引腳_24

main.c 主函數代碼

#include "stm32f10x.h"                  // Device header
#include "Delay.h" 
#include "Buzzer.h"
#include "LightSensor.h"

uint8_t KeyNum;

int main(void)
{

	Buzzer_Init();
	LightSensor_Init();
	
	while(1)
	{
		if(LightSensor_Get() == 1)
		{
			Buzzer_ON();
		}
		else
		{
			Buzzer_OFF();
		}
	}
}

蜂鳴器代碼:

#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);
	}	
}
#ifndef __BUZZER_H
#define __BUZZER_H

void Buzzer_Init(void);
void Buzzer_ON(void);
void Buzzer_OFF(void);
void Buzzer_Turn(void);

#endif

光敏傳感器代碼:

#include "stm32f10x.h"                  // Device header

void LightSensor_Init(void)
{
	/*開啓時鐘*/
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);		//開啓GPIOB的時鐘
	
	/*GPIO初始化*/
	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);
}
#ifndef __LIGHT_SENSOR_H
#define __LIGHT_SENSOR_H


void LightSensor_Init(void);
uint8_t LightSensor_Get(void);


#endif

對比項

有源蜂鳴器

無源蜂鳴器

備註(STM32使用建議)

核心結構

內置振盪電路(含三極管、振盪芯片)

僅電磁線圈+振膜,無振盪電路

有源的“源”指內置振盪源,並非“電源”

驅動方式

直接接直流電壓(如3.3V/5V)即可發聲

需輸入一定頻率的方波信號(如1kHz~5kHz)才能發聲

有源:STM32用GPIO輸出高低電平就能控制;無源:需用PWM或延時翻轉GPIO產生方波

聲音控制

只能控制響/不響,音調固定

可通過改變方波頻率控制音調(如不同頻率出不同聲音)

做音樂播放選無源,僅做報警提示選有源

工作電壓

有固定電壓(如3V、5V,錯壓易燒燬)

電壓範圍寬(如3V~5V),由方波幅值決定

需匹配STM32引腳輸出電平(3.3V)

引腳標識

通常標“+”“-”(正負極性,反接不響)

無正負極(兩根引腳可互換)

有源反接不會燒,但不工作;無源無極性限制

外觀特徵

頂部蓋板多為黑色/紅色,底部電路板可見芯片

頂部蓋板多為白色/透明,內部可見線圈和振膜

肉眼可快速區分(新手實用技巧)

STM32驅動示例

GPIO_ResetBits(GPIOB, GPIO_Pin_0);(低電平響,需看接線)

用延時生成方波:

c<br>while(1){<br>GPIO_SetBits(GPIOB, GPIO_Pin_0);<br>Delay_us(500);<br>GPIO_ResetBits(GPIOB, GPIO_Pin_0);<br>Delay_us(500);<br>}<br>(1kHz方波)

有源驅動代碼簡單,無源需生成方波

成本與適用場景

成本稍高,適合簡單報警(如按鍵提示、故障報警)

成本稍低,適合音樂播放、複雜音效(如電子琴)

新手入門先玩有源,易上手


- 光敏電阻模塊工作原理

光敏模塊是STM32入門常用的環境光檢測模塊,核心是光敏電阻,配合簡單的電路實現“光強→電信號”的轉換,新手易上手。

1. 核心元件:光敏電阻的工作原理

光敏電阻(也叫光導管)是一種半導體光敏元件,基於光電導效應工作:

  • 當光線照射到光敏電阻表面時,其內部的半導體材料會產生更多的載流子,導致電阻值急劇減小(光線越強,電阻越小);
  • 當無光線(黑暗環境)時,光敏電阻的電阻值很大(可達數兆歐)。

簡單説:光強 ↗ → 電阻 ↘;光弱 ↗ → 電阻 ↗

2. 光敏模塊的電路結構(兩種常見類型)

市面上的光敏模塊主要分數字輸出型模擬輸出型,新手常用數字輸出型(接線簡單)。

- 數字輸出型光敏模塊(最常用)

電路組成:
  • 光敏電阻 + 固定電阻 → 分壓電路;
  • 比較器(如LM393)→ 將分壓電壓與參考電壓比較,輸出高低電平。
工作過程:
  1. 模塊上有一個電位器,可調節參考電壓(即靈敏度);
  2. 當環境光強超過設定值時,光敏電阻阻值變小,分壓後的電壓低於參考電壓,比較器輸出低電平
  3. 當環境光強低於設定值時,光敏電阻阻值變大,分壓後的電壓高於參考電壓,比較器輸出高電平
關鍵特點:

輸出只有高/低兩種電平,可直接接STM32的GPIO輸入引腳,用GPIO_ReadInputDataBit()讀取。

- 模擬輸出型光敏模塊

電路組成:

僅由光敏電阻 + 固定電阻組成的分壓電路,無比較器。

工作過程:

輸出端直接輸出分壓後的模擬電壓(範圍0~3.3V/5V),電壓值隨光強連續變化(光越強,電壓越高;光越弱,電壓越低)。

關鍵特點:

需接STM32的ADC引腳(如PA0),通過ADC採集電壓值,計算出具體的光強大小(精度更高)。


寫在最後

  1. 有源蜂鳴器和無源蜂鳴器的核心區別是是否內置振盪電路,新手入門選有源更易實現;
  2. 光敏模塊通過光敏電阻的阻值變化將光強轉為電信號,數字輸出型適合簡單的開關控制,模擬輸出型適合高精度的光強檢測。
    結合STM32的GPIO和ADC操作,能快速實現對這兩種模塊的控制,是新手練手的好案例。