本帖最后由 suncat0504 于 2024-6-8 20:50 编辑
本次实验使用现成的电流传感器模块获取电流数据。模块用的是ACS758LCB霍尔电流模块,体积小。这个模块我买了很久,都没有做过实验,属于那种看了喜欢,想用了试试的那种。
提供以下几个接口:
1、5V
2、GND
3、TXD
4、VOUT
5、D-CMP
TXD是以9600波特率输出的数据。发送的两个字节的数据帧,BCD码模式。第一个字节的高四位,表示正负,A表示为正,B表示为负。低四位和第二个字节的高四位用来表示电流值的整数。第二个字节的低四位表示电流的小数位。
D-CMP用来接外部比较基准电压,VOUT是比较结果的输出。通过比较外部基准电压和采样电流模块的电压,来判断我们收集的电流是否超出了范围。如果超出范围,Vout会输出高电平,作为报警信号。
很明显,这个模块是用来测试直流更合适。考虑到用来控制可充电电池的充电的,因此用起来没问题。问题是这个模块的电流上限是30A,普通充电电池的电流不会这么大。能否适用于小电流的采样,只能通过实验来试试了。
因为暂时用不到4、5的比较输出功能,实际接线只需要1、2、3即可。在配合单片机操作之前,先看看模块的工作情况,只需要接入电源、地,连上串口接收模块。
板子上有一个发光管坏掉了,导致缺笔段,不影响观感。串口得到的结果:
A000,表示结果为正的0.0A;B001,表示为-0.1A,还不错。
使用芯源开发板的话,需要额外准备一个串口接收来自电流模块的数据。
根据手册和开发板的IO排针输出状况,
使用PA09作为串口接收用。为了调试程序以及显示测量结果,这里先接入一个OLED屏。为此建立一个工程,导入OLED的处理程序。
接下来,引入串口处理程序。串口使用中断方式,每采集到完整的两个字节的数据后,处理并显示到OLED上。
主程序中主要处理代码:
- uint8_t readbuff[32] = {'\0'}; // 串口接收缓冲区
- uint8_t procflag = 0; // 处理中标志,遇到该标志,串口接收的数据暂时不保存到缓冲区中
- uint8_t readpos = 0; // 串口数据接收用指针
- void getTestResult(void) {
- int8_t isok = 0;
- uint8_t v1 = 0; // 整数部分
- uint8_t v2 = 0; // 小数部分
- char numstr[10]={'\0'};
-
- readbuff[2] = '\0';
- if ((readbuff[0] & 0xA0) > 0) {
- numstr[0]='A';
- isok=1;
- } else if ((readbuff[0] & 0xB0) > 0) {
- // 负数
- numstr[0]='B';
- isok=-1;
- }
- if (isok != 0) {
- numstr[1]=(readbuff[0] & 0x0f)+48;
- numstr[2]=((readbuff[1] &0xf0)>>4)+48;
- numstr[3]=(readbuff[1] & 0x0f)+48;
- numstr[4]='\0';
- GUI_ShowString(0, 0, (uint8_t*)numstr, 16, 1);
-
- // 正数
- v1 = (readbuff[0] & 0x0f) * 10;
- v1 = v1+((readbuff[1] & 0xf0)>>4);
- v2 = readbuff[1] & 0x0f;
-
- sprintf(numstr, "%2.1f", ((float)v1+0.1*v2) * isok);
- GUI_ShowString(0, 16, (uint8_t*)numstr, 16, 1);
- }
- }
- /**
- ******************************************************************************
- ** \brief Main function of project
- **
- ** \return uint32_t return value, if needed
- **
- ******************************************************************************/
- int32_t main(void) {
-
-
- //配置RCC
- RCC_Configuration();
- //配置GPIO
- GPIO_Configuration();
- //配置UART
- UART_Configuration();
- //配置NVIC
- NVIC_Configuration();
- //使能UARTx RC中断
- USART_ITConfig(DEBUG_USARTx, USART_IT_RC, ENABLE);
- //USART_SendString(DEBUG_USARTx, "\r\nCW32F030 UART Interrupt\r\n");
- OLED_Init();
- OLED_Clear(0);
- //GUI_ShowString(0, 0, (uint8_t*)"Start test...", 8, 1);
- while(1) {
- //中断收发
- if (procflag == 1) {
- // 收到两个自己字节的数据
- getTestResult();
- procflag=0;
-
- }
- }
- }
串口的初始化代码:
中断处理中的处理代码:
- /**
- * @brief This funcation handles UART1
- * 串口中断
- */
- void UART1_IRQHandler(void) {
- /* USER CODE BEGIN */
- uint8_t TxRxBuffer;
- if(USART_GetITStatus(CW_UART1, USART_IT_RC) != RESET) {
- // 接收串口数据
- TxRxBuffer = USART_ReceiveData_8bit(CW_UART1);
- if (procflag == 0) {
- //USART_SendData_8bit(CW_UART1, TxRxBuffer);
- if ((TxRxBuffer & 0xA0) > 0 || (TxRxBuffer & 0xB0) > 0) {
- readpos = 0;
- }
- readbuff[readpos] = TxRxBuffer;
- readpos=(readpos+1)%2;
- if (readpos == 0) {
- // 完成两个字节的接收, 建立接收完成标志
- procflag = 1;
- }
- }
- //
- USART_ClearITPendingBit(CW_UART1, USART_IT_RC);
- }
- /* USER CODE END */
- }
下一步将接入实际测试电流做测试。
|