需求:使用AI单片机设计一款简单的USB功率计
1、要求能测量电压0-20V、电流0-5A;
2、指示灯1s闪烁或呼吸灯;
3、底层本,简单,易上手,焊接。
整个过程包含GPIO、UART、ADC、IIC,标准库函数方式进行编程。
方案:技术评估

1、电流通过INA180A1芯片转化为电压进行采集;
2、电压通过高精度电阻分压进行采集;
3、USB2TTL模块进行串口通信,LED闪烁,OLED显示
硬件设计:SCH+PCB+PCBA+手工SMT

软件开发:标准库开发
GPIO:
- /**
- * @brief GPIO_Init
- * @param None
- * @retval None
- */
- void GPIO_Init(void)
- {
- P3_MODE_IO_PU(GPIO_Pin_0);
- P3_MODE_IO_PU(GPIO_Pin_1);
- P3_MODE_IO_PU(GPIO_Pin_2);
- P3_MODE_IO_PU(GPIO_Pin_3);
- P3_MODE_IO_PU(GPIO_Pin_7);
-
- LED = 1;
- }
复制代码
UART:
- /**
- * @brief LED_Init
- * @param None
- * @retval None
- */
- void UART_Init(void)
- {
- COMx_InitDefine UART_InitStruct = {0};
- UART_InitStruct.BaudRateDouble = DISABLE;
- UART_InitStruct.Morecommunicate = DISABLE;
- UART_InitStruct.UART_BaudRate = 115200;
- UART_InitStruct.UART_BRT_Use = BRT_Timer1;
- UART_InitStruct.UART_Mode = UART_8bit_BRTx;
- UART_InitStruct.UART_RxEnable = DISABLE;
-
- UART_Configuration(UART1, &UART_InitStruct);
- NVIC_UART1_Init(ENABLE,Priority_0);
-
- UART1_SW(UART1_SW_P30_P31);
- }
复制代码
I2C:
- /**
- * @brief I2C_Cfg
- * @param None
- * @retval None
- */
- void I2C_Cfg(void)
- {
- I2C_InitTypeDef I2C__InitStruct = {0};;
-
- I2C__InitStruct.I2C_Enable = ENABLE;
- I2C__InitStruct.I2C_Mode = I2C_Mode_Master;
- I2C__InitStruct.I2C_MS_WDTA = DISABLE;
- I2C__InitStruct.I2C_Speed = 13; //总线速度=Fosc/2/(Speed*2+4)=24M/2/(13*2+4)=400kHz
- I2C_Init(&I2C__InitStruct);
-
- I2C_SW(I2C_P33_P32);
- }
复制代码
- void I2C_WriteByte(uint8_t byte,uint8_t mode) //OLED驱动写函数
- {
- Start(); //发送起始命令
- SendData(0x78); //发送设备地址+写命令
- RecvACK();
- if(mode)
- {
- SendData(0x40); //发送存储地址;
- }
- else
- {
- SendData(0x00); //发送存储地址;
- }
- RecvACK();
- SendData(byte);
- RecvACK();
- Stop(); //发送停止命令
- }
复制代码
ADC:
- /**
- * @brief ADC_Init
- * @param None
- * @retval None
- */
- void ADC_Init(void)
- {
- ADC_InitTypeDef ADC__InitStruct = {0};
-
- ADC__InitStruct.ADC_AdjResult = ADC_RIGHT_JUSTIFIED;
- ADC__InitStruct.ADC_CsHold = 1;
- ADC__InitStruct.ADC_CsSetup = 0;
- ADC__InitStruct.ADC_SMPduty = 15;
- ADC__InitStruct.ADC_Speed = ADC_SPEED_2X16T;
- ADC_Inilize(&ADC__InitStruct);
-
- ADC_PowerControl(ENABLE);
- delay_ms(1);
- }
复制代码
OLED:
- void OLED_Init(void)
- {
- I2C_Cfg();
- delay_ms(200);
-
- OLED_WR_Byte(0xAE,OLED_CMD);//--turn off oled panel
- OLED_WR_Byte(0x00,OLED_CMD);//---set low column address
- OLED_WR_Byte(0x10,OLED_CMD);//---set high column address
- OLED_WR_Byte(0x40,OLED_CMD);//--set start line address Set Mapping RAM Display Start Line (0x00~0x3F)
- OLED_WR_Byte(0xB0,OLED_CMD);
- OLED_WR_Byte(0x81,OLED_CMD);//--set contrast control register
- OLED_WR_Byte(0xCF,OLED_CMD); // Set SEG Output Current Brightness
- OLED_WR_Byte(0xA1,OLED_CMD);//--Set SEG/Column Mapping 0xa0左右反置 0xa1正常
- OLED_WR_Byte(0xC8,OLED_CMD);//Set COM/Row Scan Direction 0xc0上下反置 0xc8正常
- OLED_WR_Byte(0xA6,OLED_CMD);//--set normal display
- OLED_WR_Byte(0xA8,OLED_CMD);//--set multiplex ratio(1 to 64)
- OLED_WR_Byte(0x3f,OLED_CMD);//--1/64 duty
- OLED_WR_Byte(0xD3,OLED_CMD);//-set display offset Shift Mapping RAM Counter (0x00~0x3F)
- OLED_WR_Byte(0x00,OLED_CMD);//-not offset
- OLED_WR_Byte(0xd5,OLED_CMD);//--set display clock divide ratio/oscillator frequency
- OLED_WR_Byte(0x80,OLED_CMD);//--set divide ratio, Set Clock as 100 Frames/Sec
- OLED_WR_Byte(0xD9,OLED_CMD);//--set pre-charge period
- OLED_WR_Byte(0xF1,OLED_CMD);//Set Pre-Charge as 15 Clocks & Discharge as 1 Clock
- OLED_WR_Byte(0xDA,OLED_CMD);//--set com pins hardware configuration
- OLED_WR_Byte(0x12,OLED_CMD);
- OLED_WR_Byte(0xDB,OLED_CMD);//--set vcomh
- OLED_WR_Byte(0x40,OLED_CMD);//Set VCOM Deselect Level
- OLED_WR_Byte(0x20,OLED_CMD);//-Set Page Addressing Mode (0x00/0x01/0x02)
- OLED_WR_Byte(0x02,OLED_CMD);//
- OLED_WR_Byte(0x8D,OLED_CMD);//--set Charge Pump enable/disable
- OLED_WR_Byte(0x14,OLED_CMD);//--set(0x10) disable
- // OLED_WR_Byte(0xA4,OLED_CMD);// Disable Entire Display On (0xa4/0xa5)
- // OLED_WR_Byte(0xA6,OLED_CMD);// Disable Inverse Display On (0xa6/a7)
- OLED_Clear();
- OLED_WR_Byte(0xAF,OLED_CMD); /*display ON*/
- }
复制代码
Main:
- void main(void)
- {
- float current = 0.0;
- float voltage = 0.0;
- float power = 0.0;
- char OLED[9] = {0};
-
- EAXSFR();
-
- GPIO_Init();
- UART_Init();
- ADC_Init();
-
- EA = 1;
-
- OLED_Init();//初始化OLED
- OLED_ColorTurn(1);//0正常显示,1 反色显示
- OLED_DisplayTurn(0);//0正常显示 1 屏幕翻转显示
-
- delay_ms(20);
-
- while(1)
- {
- current = Get_ADCResult(ADC_CH0) * 3.3 / 4096 * 2 ;
- delay_ms(3);
- voltage = Get_ADCResult(ADC_CH1) * 3.3 / 4096 * 11;
- power = current * voltage;
- printf("Current = %ld, Voltage = %ld, Power = %ld\r\n", current, voltage, power);
-
-
- sprintf(OLED,"I:%.3fA", current);
- OLED_ShowString(28,0,OLED,16);
-
- sprintf(OLED,"U:%.3fV", voltage);
- OLED_ShowString(28,2,OLED,16);
-
- sprintf(OLED,"P:%.3fW", power);
- OLED_ShowString(28,4,OLED,16);
-
- LED = !LED;
- delay_ms(250);delay_ms(250);delay_ms(250);delay_ms(250);
- }
- }
复制代码
BOM:

(不涉及邮费,建议多买几个物料)
成品:效果展示
(可自己添加外壳,螺柱固定等)
总结:
1、设计简单,把它当一个小产品去开发,从需求、方案、软硬件等标准流程进行,由小到大,由简入繁;
2、硬件SCH+PCB+PCBA+手工SMT,嘉立创免费打样PCB是为学习、工作提供了太多试错机会,学会画板,焊接,调试,下载;
3、软硬件结合,硬件如何设计,软件如何对应写代码,标准库设计,方便移植。
后记:
(USB2TTL模块也可以用STC8H2K12U-SOP16进行设计,2路串口,波特率支持10Mbps,电源可控,特别适合STC开发)
STC8H2K12U USB Meter.7z
(131.98 KB, 下载次数: 25)
|