概述
电压检测是测量电路中电压的一种重要方法,它在许多电气和电子应用中都有广泛的用途。以下是需要电压检测的一些主要原因:
- 确保设备安全:电压检测可以确保电气设备在其额定电压范围内运行。如果设备在过高或过低的电压下运行,可能会导致设备损坏、故障甚至火灾。
- 保护电子设备:电子设备通常对电压波动非常敏感,电压检测可以及时发现问题,保护设备免受损害。
- 提高能源效率:通过电压检测,我们可以监测电气系统的负载、功率和效率,从而优化能源使用,降低能耗。
- 故障诊断:电压检测有助于发现电气系统中的故障和异常,便于维修人员迅速定位问题并进行维修。
- 确保系统稳定性:对于某些电气设备,如发电厂、变电站等,电压检测是确保供电系统稳定运行的关键。
- 设计和研发:在电子产品的设计和研发阶段,电压检测有助于工程师评估电路性能,优化设计。
- 满足法规要求:某些行业和地区可能有严格的电压标准和规定,电压检测有助于确保设备符合这些要求。
总之,电压检测在保障设备安全、提高能效、确保系统稳定性以及满足法规要求等方面都具有重要意义。
在我们当前案例中, 18650锂电池是我们重要设备, 而且它很贵重,一旦过充或者过放, 它将无法使用, 所以我们需要监测锂电池的电压.
18650锂离子电池的过充过放电压值因生产厂家和化学组成有所不同,但通常有一个大致的范围。通常,过充电压值在 4.2V 到 4.25V 之间,过放电压值在 2.5V 到 3.0V 之间。过充和过放电可能会导致电池性能下降、循环寿命缩短甚至安全隐患。所以我们可以设定当18650的电压低于3.5V的时候, 设备断电报警, 让用户及时去充电
电池电压的变化是模拟信号, 我们需要使用ADC去读取, 在这里我选择使用的是PC5,下面我们就按照常用步骤来开发:
- gpio配置
- adc配置
- adc读取
ADC的两种模式
在模数转换器(ADC, Analog-to-Digital Converter)中,插入模式和普通模式是指两种不同的数据采集和转换方式。它们之间的主要区别在于采样顺序、通道切换方式和优先级。
- 插入模式(Injected Mode): 插入模式是一种特殊的数据采集方式,它允许在规律的连续采样过程中临时插入对其他通道的采样。插入模式具有较高的优先级,当有插入请求时,会暂停正在进行的普通模式采样,优先处理插入模式的采样任务。插入模式的采样完成后,普通模式采样会继续进行。插入模式通常用于需要快速响应的应用场景,例如突发事件的监测。
- 普通模式(Regular Mode): 普通模式是ADC的一种常规数据采集方式,通常按照预设的通道顺序进行连续或单次采样。在普通模式下,ADC按照设置的采样顺序和频率对各个通道进行采样,将模拟信号转换为数字信号。普通模式适用于大多数数据采集任务,尤其是对实时性要求不高的场景。
总之,插入模式和普通模式是针对不同应用场景的ADC采样方式。插入模式适用于需要快速响应和高优先级处理的场景,而普通模式适用于常规的连续或单次采样任务。
在电压的采样过程中, 我们可以选择插入模式, 也可以选择普通模式.
示例代码
实现步骤:
- 思考用哪个GPIO,确定引脚PB1
- 要开启什么样的功能,是ADC,TIMER,DMA中的哪一个? 确定ADC0_9
- 选择使用ADC的普通模式,还是插入模式
- 选好之后:
- 如何初始化
- 如何获取数据
- 数据拿到之后该如何进行换算
这里面的代码有些复杂, 但是很多代码都是固定写法, 我们可以从gd32官方给的例子里面直接拷贝.
#include "bsp_battery.h"
#include <stdio.h>
#define RCU_BATTERY RCU_GPIOB
#define PORT_BATTERY GPIOB
#define PIN_BATTERY GPIO_PIN_1
#define ADC_RCU_BATTERY RCU_ADC0
#define ADC_BATTERY ADC0
#define ADC_CHANNEL_BATTERY ADC_CHANNEL_9
void bsp_battery_gpio_init(){
// 开启时钟
rcu_periph_clock_enable(RCU_BATTERY);
// 设置gpio
gpio_mode_set(PORT_BATTERY, GPIO_MODE_ANALOG,GPIO_PUPD_NONE,PIN_BATTERY);
}
void bsp_battery_adc_init(){
// 开启时钟线
rcu_periph_clock_enable(ADC_RCU_BATTERY);
// 配置时钟倍频
adc_clock_config(ADC_ADCCK_PCLK2_DIV4);
// 通道配置
adc_channel_length_config(ADC_BATTERY,ADC_INSERTED_CHANNEL,1);
// 配置采集哪个通道 0表示的是角标
adc_inserted_channel_config(ADC_BATTERY,0,ADC_CHANNEL_9,ADC_SAMPLETIME_480);
adc_external_trigger_config(ADC_BATTERY,ADC_INSERTED_CHANNEL,DISABLE);
adc_data_alignment_config(ADC_BATTERY,ADC_DATAALIGN_RIGHT);
adc_special_function_config(ADC0,ADC_SCAN_MODE,ENABLE);
adc_enable(ADC_BATTERY);
adc_calibration_enable(ADC_BATTERY);
}
void bsp_battery_init(void){
bsp_battery_gpio_init();
bsp_battery_adc_init();
}
float bsp_battery_get(){
adc_software_trigger_enable(ADC_BATTERY,ADC_INSERTED_CHANNEL);
uint32_t data = ADC_IDATA0(ADC_BATTERY);
float vol = data*1.0/4096 * 3.3 * 4;
return vol;
}
void bsp_battery_test(){
bsp_battery_init();
while(1){
float bat = bsp_battery_get();
printf("battery:%f\r\n",bat);
delay_1ms(500);
}
}