为TI比赛准备的题目,老师给的训练题目做了一下,比赛结束了,现在有点时间来记录一下之前做的。
文档由我队成员乾撰写,我将大部分誊抄至此。感谢乾与鹰。
简易信号分析仪
工程下载链接
stm32f103示波器20k的采样率,频率分辨率20Hz,有失真度测量,周期,通过串口一发送,串口屏输出等等等
简易信号分析仪
摘要
本作品为简易信号分析仪,在本设计中,它主要由信号放大模块,单片机控制显示部分构成。该仪器可分析信号频率成分,信号包括正弦波、三角波和方波等三种,且能够运用快速傅里叶变换 FFT 分析测量出单一输入信号时的幅度(峰峰值)、频率;在正弦波输入时可测量正弦信号失真度。
一、方案论证与比较
本系统由信号放大模块,显示模块以及单片机控制显示部分组成。
1.1模块电路设计与比较
1.1.1 信号放大模块设计与比较
由题可知,输入信号电压范围为 100mV~5V,为了提高信号接受灵敏度可将其分为 100mV~1V 与 1V~5V 两部分。100mV~1V 部分利用运放放大,放大后的值范围在 1~5V 左右即可。因此此处我们选择 LM358,它是双运算放大器。内部包括有两个独立的、高增益、内部频率补偿的运算放大器。
1.1.2 控制芯片设计与比较
本装置采用 STM32F103FRCT6 嵌入式-微控制器单片机主控芯片,该单片机IO 接口数量多,内部资源丰富,包涵 12 位 AD 转换、16 位定时器、PWM 控制、USART 接口等,处理能力强大,能够轻松胜任此任务。
1.1.3 显示模块
方案一:采用串口显示屏显示当前幅度、频率、波形类型等信息。
方案二:采用树莓派控制屏幕显示当前幅度、频率、波形类型等信息。
方案三:通过串口发送到电脑上显示。
在第二天的调试下串口显示屏能很好地显示其频率,由于想要进一步显示波形图像导致操作不当损坏了串口显示屏。在采用树莓派控制屏幕显示时,由于刷新速率不够因此最后采用了方案三。
1.2 系统总体描述
测试信号接入后,经过信号放大模块分为两路输出。一路为放大后的信号,通过单片机的 ADC2 采集;一路为未放大的信号,通过单片机的 ADC3 采集。单片机将采集后的数据进行分析,利用 FFT 变换得到其频谱数据。最后将分析后得到的频率,波形等数据发送给显示设备。
二、系统理论分析与计算
2.1 信号放大回路的参数计算
由于接入信号幅值范围为 100mV~5V, 所以为了提高灵敏度,我们加一个
信号放大器可以将 100mV~1V 信号放 5 倍左右。根据实际情况 LM358 可以将信
号放大 5 倍,满足信号补偿要求,并且实际测试中发现可以 100mV 的信号,满
足题目要求。
2.2 接入单片机回路的参数计算
由于 STM32 单片机 ADC 的输入电压范围为:0~3.3V,所以需要将信号放大
回路的电压进行分压再经过射随器接入单片机进行 ADC 采集。
三、电路与程序设计
3.1 电路回路与器件选择
3.1.1 信号放大回路与器件选择
由于不仅需要分析其频率波形等数据,还需要分析其信号失真度,所以我们设置了两类信号输入口。一个作为通用输入,可分析得到其频率波形等数据;一个作为频率信号失真度输入口,可分析得到其失真度。信号进入第一个运放LM358 理论放大 10 倍。将实际放大 5 倍后的信号与原信号分别都分压后通过射随器。经过第二个运放后的两路信号分别被单片机 ADC2,ADC3 采集,进入数据分析。
3.2 程序设计
3.2.1 程序功能描述与设计思路
1、 程序功能描述
分析测量出单一输入信号时的幅度(峰峰值)、频率;在正弦波输入时可测量正弦信号失真度
2、 程序设计思路
将 ADC2 与 ADC3 采集到的数据分别放入两个数组中,分析对比两组数据,根据设定的判断范围选择其中一组数据进行 FFT 变换,得到频率等数据。最后将数据通过串口通信发送给屏幕显示。
3.2.2 程序流程图
四、测试方案与测试结果
4.1 测试方案
通过函数信号发生器给一个输入信号,通过显示模块显示其幅值、频率与波
形类型等。通过显示模块检查是否与输入信号信息对应。
4.2 测试条件与仪器
测试条件:实验室 5407 室温条件下
测试仪器:
(1)数字示波器
(2)DDS 函数源
4.3 测试结果及分析
PS:当时本来是想用串口屏幕来显示的,但是用Hal库出来的串口与标准库出来的串口不一样,串口屏识别不到,但是电脑就能读到,只能用这个电脑的串口助手来显示了。
4.3.1 测试结果(数据)
当输入为正弦信号,f=3KHZ,Vpp=3.3V,ofst=1.65V 时:
当输入信号为正弦信号,f=3KHZ,Vpp=1.0V,ofst=0.5V 时:
当输入信号为方波信号,f=3KHZ,Vpp=3.0V,ofst=1.75V 时:
当输入信号为锯齿波信号,f=3KHZ,Vpp=3.0V,ofst=1.75V 时:
正如上面所说,我的串口屏幕不能用了,所以我想到了用树莓派的python来处理数据。所以也就有了下面的测试数据,树莓派的图形化界面5左右秒刷新一次。
当输入信号为方波信号,f=1KHZ,Vpp=0.1V,ofst=0.05V 时的频谱分析:
当输入信号为三角波,f=10KHZ,Vpp=3.3V,ofst=1.65V 时的频谱分析:
当输入信号为正弦波,f=10KHZ,Vpp=3.3V,ofst=1.65V 时的频谱分析:
4.3.2 测试分析与结论
根据上述测试数据,能对 20Hz 到 10KHz 的信号进行监控,并且接受频率分辨力高于 20Hz。且能够实现自动判断输入信号的类型、周期性,并测量其周期。完成检测输入信号的总功率和各频率分量的频率和功率,总功率测量的相对误差的绝对值小于 5%。
参考文献
stm32f1单片机上用FFT测量信号频率、幅度和相位(高精度、过程详细)
【STM32】使用STM32提供的DSP库进行FFT(附详细代码)
matplotlib 画动态图以及plt.ion()和plt.ioff()的使用
Python库matplotlib显示图形一定时间后自动关闭
最简单的树莓派+python3+串口通信的教程以及出现的问题的解决方式
附录1:电路原理图
附录2:源程序(仅含主程序)
/* USER CODE BEGIN Header */
/**
******************************************************************************
* @file : main.c
* @brief : Main program body
******************************************************************************
* @attention
*
* <h2><center>© Copyright (c) 2020 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under BSD 3-Clause license,
* the "License"; You may not use this file except in compliance with the
* License. You may obtain a copy of the License at:
* opensource.org/licenses/BSD-3-Clause
*
******************************************************************************
*/
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"
#include "adc.h"
#include "tim.h"
#include "usart.h"
#include "gpio.h"
#include "string.h"
#include "stm32_dsp.h"
#include "table_fft.h"
#include "math.h"
#include "oled.h"
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
/* USER CODE END Includes */
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
/* USER CODE END PTD */
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
/* USER CODE END PD */
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
/* USER CODE END PM */
/* Private variables ---------------------------------------------------------*/
/* USER CODE BEGIN PV */
/* USER CODE END PV */
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
void UR1_Send_Info(void);
/* USER CODE BEGIN PFP */
/* USER CODE END PFP */
/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
#include "stdio.h"
#define LED1_ON() HAL_GPIO_WritePin(GPIOC,GPIO_PIN_13,GPIO_PIN_RESET)
#define LED1_OFF() HAL_GPIO_WritePin(GPIOC,GPIO_PIN_13,GPIO_PIN_SET)
#define FREQUENCYRESOLUTION 19.53125
#define NPT 1024
#define ShiftingADCThreshold 530
//#define Kque
//#define Ktri
long InArry[1024]= {0};
//19.5*3Hz {2048,2086,2124,2162,2199,2237,2275,2312,2350,2387,2425,2462,2499,2536,2572,2609,2645,2681,2717,2753,2788,2823,2858,2893,2927,2961,2995,3029,3062,3094,3127,3159,3190,3222,3252,3283,3313,3342,3371,3400,3428,3456,3483,3510,3536,3562,3587,3612,3636,3660,3683,3706,3727,3749,3770,3790,3809,3829,3847,3865,3882,3898,3914,3930,3944,3958,3972,3984,3996,4008,4018,4028,4038,4046,4054,4061,4068,4074,4079,4084,4087,4091,4093,4095,4096,4096,4096,4095,4093,4090,4087,4083,4079,4073,4067,4061,4053,4045,4037,4027,4017,4006,3995,3983,3970,3957,3943,3928,3913,3897,3880,3863,3845,3827,3808,3788,3768,3747,3725,3703,3681,3658,3634,3610,3585,3560,3534,3508,3481,3453,3426,3397,3369,3339,3310,3280,3249,3219,3187,3156,3124,3091,3058,3025,2992,2958,2924,2890,2855,2820,2785,2749,2714,2678,2642,2605,2569,2532,2495,2458,2421,2384,2346,2309,2271,2233,2196,2158,2120,2082,2044,2006,1969,1931,1893,1855,1818,1780,1742,1705,1668,1631,1594,1557,1520,1484,1447,1411,1375,1340,1304,1269,1234,1200,1165,1131,1098,1064,1031,998,966,934,903,871,841,810,780,751,722,693,665,637,610,583,557,531,506,482,457,434,411,388,366,345,324,304,285,266,247,230,212,196,180,165,150,136,123,111,99,87,77,67,58,49,41,34,27,22,16,12,8,5,3,1,0,0,0,2,3,6,9,13,18,23,29,36,43,51,60,70,80,91,102,114,127,140,155,169,185,201,217,235,253,271,290,310,330,351,373,395,417,441,464,489,514,539,565,591,618,645,673,701,730,759,789,819,850,881,912,944,976,1008,1041,1074,1107,1141,1175,1210,1245,1279,1315,1350,1386,1422,1458,1494,1531,1568,1605,1642,1679,1716,1754,1791,1829,1866,1904,1942,1980,2018,2055,2093,2131,2169,2207,2244,2282,2320,2357,2395,2432,2469,2506,2543,2579,2616,2652,2688,2724,2760,2795,2830,2865,2900,2934,2968,3002,3035,3068,3101,3133,3165,3196,3228,3258,3289,3319,3348,3377,3406,3434,3461,3489,3515,3541,3567,3592,3617,3641,3664,3687,3710,3732,3753,3774,3794,3813,3832,3850,3868,3885,3902,3917,3933,3947,3961,3974,3987,3998,4010,4020,4030,4039,4048,4056,4063,4069,4075,4080,4084,4088,4091,4093,4095,4096,4096,4095,4094,4092,4090,4086,4082,4078,4072,4066,4059,4052,4044,4035,4025,4015,4004,3993,3981,3968,3954,3940,3925,3910,3894,3877,3860,3842,3823,3804,3784,3764,3743,3721,3699,3676,3653,3629,3605,3580,3555,3529,3502,3475,3448,3420,3392,3363,3334,3304,3274,3243,3212,3181,3149,3117,3085,3052,3019,2985,2951,2917,2883,2848,2813,2778,2742,2707,2671,2634,2598,2561,2525,2488,2451,2414,2376,2339,2301,2264,2226,2188,2150,2113,2075,2037,1999,1961,1923,1886,1848,1810,1773,1735,1698,1661,1623,1586,1550,1513,1477,1440,1404,1368,1333,1297,1262,1227,1193,1159,1125,1091,1058,1025,992,960,928,896,865,835,804,774,745,716,687,659,632,605,578,552,526,501,477,453,429,406,384,362,341,320,300,281,262,244,226,209,193,177,162,148,134,121,108,96,85,75,65,56,47,40,33,26,20,15,11,8,5,2,1,0,0,1,2,4,7,10,14,19,24,30,37,45,53,62,72,82,93,104,117,130,143,157,172,188,204,221,238,256,275,294,314,334,355,377,399,422,445,469,494,518,544,570,596,623,651,679,707,736,765,795,825,856,887,918,950,982,1014,1047,1081,1114,1148,1182,1217,1251,1286,1322,1357,1393,1429,1465,1502,1538,1575,1612,1649,1686,1723,1761,1798,1836,1874,1911,1949,1987,2025,2063,2101,2139,2176,2214,2252,2290,2327,2365,2402,2439,2476,2513,2550,2587,2623,2659,2695,2731,2767,2802,2837,2872,2906,2941,2975,3008,3042,3074,3107,3139,3171,3203,3234,3264,3295,3324,3354,3383,3411,3439,3467,3494,3520,3547,3572,3597,3622,3646,3669,3692,3714,3736,3757,3778,3798,3817,3836,3854,3872,3888,3905,3920,3935,3950,3964,3977,3989,4001,4012,4022,4032,4041,4049,4057,4064,4070,4076,4081,4085,4089,4092,4094,4095,4096,4096,4095,4094,4092,4089,4086,4081,4077,4071,4065,4058,4050,4042,4033,4023,4013,4002,3990,3978,3965,3951,3937,3922,3907,3890,3874,3856,3838,3819,3800,3780,3760,3738,3717,3695,3672,3648,3624,3600,3575,3550,3524,3497,3470,3443,3415,3386,3357,3328,3298,3268,3237,3206,3175,3143,3111,3078,3045,3012,2979,2945,2911,2876,2841,2806,2771,2735,2700,2664,2627,2591,2554,2518,2481,2443,2406,2369,2331,2294,2256,2219,2181,2143,2105,2067,2029,1992,1954,1916,1878,1840,1803,1765,1728,1690,1653,1616,1579,1542,1506,1469,1433,1397,1361,1326,1290,1255,1221,1186,1152,1118,1084,1051,1018,986,954,922,890,859,829,798,769,739,710,682,654,626,599,573,547,521,496,472,448,425,402,380,358,337,316,296,277,258,240,223,206,190,174,159,145,131,118,106,94,83,73,63,54,46,38,31,25,19,15,10,7,4,2,1,0,0,1,2,4,7,11,15,20,25,32,39,46,55,64,74,84,95,107,119,132,146,160,175,191,207,224,242,260,279,298,318,339,360,381,404,427,450,474,498,523,549,575,602,629,656,684,713,742,771,801,831,862,893,924,956,988,1021,1054,1087,1121,1155,1189,1223,1258,1293,1329,1364,1400,1436,1472,1509,1545,1582,1619,1656,1693,1731,1768,1806,1843,1881,1919,1957,1995,2032,2070,2108,2146,2184};
long FFT[512]={0};
long MagBufArray[512]={0};
unsigned char CountKChoice = 0;
float K[20] = {0};
uint8_t EndNum[3] = {0xFF, 0xFF, 0xFF};
unsigned int Count_Adc2 = 0;
//unsigned int Count_Adc3 = 0;
unsigned int ADC2BigSignalValue[1024] = {0};
//unsigned int ADC3SmlSignalValue[1024] = {0};
_Bool fft_flag2 = 0;
//_Bool fft_flag3 = 0;
//_Bool ChoiceADCGet = 0;
//_Bool ChoiceBigSml = 0;
//unsigned int SendDelay = 0;
unsigned int MaxADC2Amplitude = 0;
//unsigned int MaxADC3Amplitude = 0;
//Output Var
unsigned int Maxtemp = 0; // Maxtemp = Vpp * 100
unsigned char WaveType = 0;
unsigned int Freq = 0;
unsigned int Period = 0;
unsigned char Ksro = 0;
volatile float PowerWave[5] = {0}; //0ΪֱÁ÷·ÖÁ¿£¬1Ϊ»ù²¨£¬ÒÔ´ËÀàÍÆ
float PowerAll = 0;
//Output Var
void SendBerry(void);
void FindMaxFreq(void);
void SerialOutput(void);
void ADC2_Get_Value()
{
uint16_t ADC_Value = 0;
HAL_ADC_Start(&hadc2);
LED1_ON();
if(HAL_ADC_PollForConversion(&hadc2,10)==HAL_OK)//ʱ¼ä10
{
ADC_Value = HAL_ADC_GetValue(&hadc2);
if (Count_Adc2 < 1024)
{
ADC2BigSignalValue[Count_Adc2] = ADC_Value;
if (MaxADC2Amplitude < ADC_Value)
{
MaxADC2Amplitude = ADC_Value;
}
Count_Adc2++;
if (Count_Adc2 == 1023)
{
fft_flag2 = 1;
}
}
else
{
MaxADC2Amplitude = 0;
Count_Adc2 = 0;
}
// LED1_OFF();
HAL_ADC_Stop(&hadc2);
}
}
//void ADC3_Get_Value()
//{
// uint16_t ADC_Value = 0;
// HAL_ADC_Start(&hadc3);
LED1_ON();
// if(HAL_ADC_PollForConversion(&hadc3,10)==HAL_OK)//??10
// {
// ADC_Value = HAL_ADC_GetValue(&hadc3);
// if (Count_Adc3 < 1024)
// {
// ADC3SmlSignalValue[Count_Adc3] = ADC_Value;
// if (MaxADC3Amplitude < ADC_Value)
// {
// MaxADC3Amplitude = ADC_Value;
// }
// Count_Adc3++;
// if (Count_Adc3 == 1023)
// {
// fft_flag3 = 1;
// }
// }
// else
// {
// MaxADC3Amplitude = 0;
// Count_Adc3 = 0;
// }
// LED1_OFF();
// HAL_ADC_Stop(&hadc3);
// }
//}
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
if(htim->Instance == TIM2)
{
// if(ChoiceADCGet == 0)
// {
ADC2_Get_Value();
// ChoiceADCGet = 1;
// }
// else
// {
// ADC3_Get_Value();
// ChoiceADCGet = 0;
// }
}
}
void GetPowerMag()
{
signed short lX,lY;
float X,Y,Mag;
unsigned short i;
for(i=0; i<1024/2; i++)
{
lX = (FFT[i] << 16) >> 16;
lY = (FFT[i] >> 16);
X = 1024 * ((float)lX) / 32768;
Y = 1024 * ((float)lY) / 32768;
Mag = sqrt(X * X + Y * Y) / 1024;
if(i == 0)
MagBufArray[i] = (unsigned long)(Mag * 32768);
else
MagBufArray[i] = (unsigned long)(Mag * 65536);
}
}
/* USER CODE END 0 */
/**
* @brief The application entry point.
* @retval int
*/
int main(void)
{
//
//unsigned int num[1024]={0};//{2048,2068,2088,2109,2129,2150,2170,2191,2211,2232,2252,2272,2293,2313,2333,2354,2374,2394,2414,2434,2454,2474,2494,2514,2534,2554,2574,2594,2613,2633,2653,2672,2692,2711,2730,2750,2769,2788,2807,2826,2845,2864,2883,2901,2920,2938,2957,2975,2993,3011,3029,3047,3065,3083,3100,3118,3135,3153,3170,3187,3204,3221,3237,3254,3271,3287,3303,3319,3335,3351,3367,3382,3398,3413,3428,3443,3458,3473,3488,3502,3517,3531,3545,3559,3573,3586,3600,3613,3626,3639,3652,3664,3677,3689,3701,3713,3725,3737,3748,3760,3771,3782,3793,3803,3814,3824,3834,3844,3854,3863,3873,3882,3891,3900,3908,3917,3925,3933,3941,3949,3956,3964,3971,3978,3984,3991,3997,4004,4010,4015,4021,4026,4031,4036,4041,4046,4050,4054,4058,4062,4066,4069,4072,4075,4078,4081,4083,4085,4087,4089,4090,4092,4093,4094,4095,4095,4095,4095,4095,4095,4095,4094,4093,4092,4091,4089,4087,4085,4083,4081,4078,4076,4073,4070,4066,4063,4059,4055,4051,4046,4042,4037,4032,4027,4022,4016,4010,4005,3998,3992,3986,3979,3972,3965,3957,3950,3942,3934,3926,3918,3910,3901,3892,3883,3874,3865,3855,3846,3836,3826,3815,3805,3794,3784,3773,3761,3750,3739,3727,3715,3703,3691,3679,3666,3654,3641,3628,3615,3602,3588,3575,3561,3547,3533,3519,3505,3490,3476,3461,3446,3431,3416,3400,3385,3369,3354,3338,3322,3306,3290,3273,3257,3240,3223,3207,3190,3173,3155,3138,3121,3103,3086,3068,3050,3032,3014,2996,2978,2960,2941,2923,2904,2886,2867,2848,2829,2810,2791,2772,2753,2734,2714,2695,2675,2656,2636,2617,2597,2577,2557,2537,2518,2498,2478,2458,2437,2417,2397,2377,2357,2337,2316,2296,2276,2255,2235,2214,2194,2174,2153,2133,2112,2092,2071,2051,2030,2010,1989,1969,1948,1928,1908,1887,1867,1846,1826,1806,1785,1765,1745,1724,1704,1684,1664,1644,1624,1604,1584,1564,1544,1524,1504,1485,1465,1445,1426,1406,1387,1368,1348,1329,1310,1291,1272,1253,1234,1215,1197,1178,1160,1141,1123,1105,1087,1069,1051,1033,1015,997,980,962,945,928,911,894,877,860,844,827,811,794,778,762,746,731,715,700,684,669,654,639,624,610,595,581,566,552,538,525,511,498,484,471,458,445,433,420,408,396,384,372,360,348,337,326,315,304,293,283,273,263,253,243,233,224,215,206,197,188,179,171,163,155,147,140,133,125,118,112,105,99,92,86,81,75,70,64,59,55,50,46,41,37,33,30,26,23,20,17,15,12,10,87,69,53,39,28,18,10,05,01,00,00,03,07,14,23,33,46,61,78,97,11,14,16,19,22,25,28,32,35,39,43,48,52,57,62,67,72,78,84,90,96,102,108,115,122,129,136,144,151,159,167,176,184,192,201,210,219,229,238,248,258,268,278,288,299,310,321,332,343,354,366,378,390,402,414,427,439,452,465,478,491,505,518,532,546,560,574,588,603,617,632,647,662,677,692,708,723,739,755,771,787,803,819,836,852,869,886,903,920,937,954,971,989,1007,1024,1042,1060,1078,1096,1114,1132,1151,1169,1188,1206,1225,1244,1263,1282,1301,1320,1339,1358,1378,1397,1417,1436,1456,1475,1495,1515,1534,1554,1574,1594,1614,1634,1654,1674,1695,1715,1735,1755,1776,1796,1816,1837,1857,1877,1898,1918,1939,1959,1980,2000,2020,2041,2061,2082,2102,2123,2143,2164,2184,2205,2225,2245,2266,2286,2307,2327,2347,2367,2388,2408,2428,2448,2468,2488,2508,2528,2548,2568,2587,2607,2627,2646,2666,2686,2705,2724,2744,2763,2782,2801,2820,2839,2858,2877,2895,2914,2932,2951,2969,2987,3006,3024,3042,3059,3077,3095,3112,3130,3147,3164,3182,3198,3215,3232,3249,3265,3282,3298,3314,3330,3346,3362,3378,3393,3408,3424,3439,3454,3468,3483,3498,3512,3526,3540,3554,3568,3582,3595,3609,3622,3635,3648,3660,3673,3685,3698,3710,3721,3733,3745,3756,3767,3778,3789,3800,3810,3821,3831,3841,3851,3860,3870,3879,3888,3897,3906,3914,3922,3931,3939,3946,3954,3961,3969,3976,3982,3989,3995,4002,4008,4013,4019,4025,4030,4035,4040,4044,4049,4053,4057,4061,4065,4068,4071,4074,4077,4080,4082,4084,4086,4088,4090,4091,4093,4094,4094,4095,4095,4095,4095,4095,4095,4094,4093,4092,4091,4090,4088,4086,4084,4082,4079,4077,4074,4071,4067,4064,4060,4056,4052,4048,4043,4039,4034,4029,4023,4018,4012,4006,4000,3994,3988,3981,3974,3967,3960,3952,3945,3937,3929,3921,3912,3904,3895,3886,3877,3868,3858,3849,3839,3829,3819,3808,3798,3787,3776,3765,3754,3742,3731,3719,3707,3695,3683,3670,3658,3645,3632,3619,3606,3593,3579,3565,3552,3538,3523,3509,3495,3480,3465,3451,3436,3421,3405,3390,3374,3359,3343,3327,3311,3295,3278,3262,3245,3229,3212,3195,3178,3161,3144,3126,3109,3091,3074,3056,3038,3020,3002,2984,2965,2947,2929,2910,2892,2873,2854,2835,2816,2797,2778,2759,2740,2720,2701,2682,2662,2643,2623,2603,2583,2564,2544,2524,2504,2484,2464,2444,2424,2404,2383,2363,2343,2323,2302,2282,2262,2241,2221,2201,2180,2160,2139,2119,2098,2078,2057,2037,2016,1996,1975,1955,1934,1914,1894,1873,1853,1832,1812,1792,1771,1751,1731,1711,1690,1670,1650,1630,1610,1590,1570,1550,1530,1511,1491,1471,1452,1432,1413,1393,1374,1354,1335,1316,1297,1278,1259,1240,1221,1203,1184,1166,1147,1129,1110,1092,1074,1056,1038,1021,1003,985,968,951,933,916,899,882,866,849,832,816,800,783,767,751,736,720,704,689,674,659,644,629,614,600,585,571};
unsigned int j = 0;
// uint8_t str_buff[10]="";
// unsigned int Maxtemp = 0;
/* USER CODE BEGIN 1 */
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_TIM2_Init();
// MX_ADC1_Init();
MX_ADC2_Init();
// MX_ADC3_Init();
MX_USART1_UART_Init();
/* USER CODE BEGIN 2 */
HAL_TIM_Base_Start_IT(&htim2);
/* USER CODE END 2 */
// OLED_Init();
// OLED_Clear();
// OLED_ShowCHinese(0,0,0);//ÖÐ
while (1)
{
// OLED_ShowString(0,6,"ASCII:",16);
// OLED_ShowCHinese(0,0,0);//ÖÐ
// LED1_ON();
// for (j=0; j<1024; j++)
// {
// InArry[j] <<= 16;
// }
// cr4_fft_1024_stm32(FFT,InArry,1024);
// GetPowerMag();
// LED1_OFF();
/* USER CODE END WHILE */
//sprintf((char *)str_buff, "t2.txt=\"123456\"%x%x%x",0xff,0xff,0xff);
if (fft_flag2 == 1) // && fft_flag3 == 1)
{
//if (fft_flag2 == 1 && fft_flag3 == 1)
// if (MaxADC2Amplitude > ShiftingADCThreshold) //´óÐźÅ
// {
for (j=0; j<1024; j++)
{
InArry[j] = ADC2BigSignalValue[j];
InArry[j] <<= 16;
Maxtemp = (int)(MaxADC2Amplitude*0.122);//0.0805/0.66);
// ChoiceBigSml = 0;
}
// }
// else //СÐźÅ
// {
// for (j=0; j<1024; j++)
// {
// InArry[j] = ADC3SmlSignalValue[j];
// InArry[j] <<= 16;
// Maxtemp = (int)(MaxADC3Amplitude*0.0161);//0.0805/0.50/10);
// ChoiceBigSml = 1;
// }
// }
sprintf((char *)str_buff, "Vpp = %d.%d%d",
Maxtemp/100, Maxtemp/10%10, Maxtemp%10);
HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000); //Êä³öVpp
cr4_fft_1024_stm32(FFT,InArry,1024);
GetPowerMag();
FindMaxFreq();
SerialOutput();
fft_flag2 = 0;
// fft_flag3 = 0;
}
// HAL_UART_Transmit(&huart1,Real,sizeof(Real),10000);
/* USER CODE BEGIN 3 */
}
/* USER CODE END 3 */
}
void SerialOutput(void)
{
uint8_t str_buff[]="F=000000Hz T=100000us Vpp=0.00V Ksr=00%% Typ=0 Pall=0.00W";
// T=100us-50ms(50000us)
sprintf((char *)str_buff, "F=%d%d%d%d%dHz T=%d%d%d00us Vpp=%d.%d%dV Ksr=%d%d%% Typ=%d Pall=%d.%d%dW",
// F 5
Freq/10000, Freq/1000%10, Freq/100%10, Freq/10%10, Freq%10,
// T 3
Period/100, Period/10%10, Period%10,
//Vpp 3
Maxtemp/100, Maxtemp/10%10, Maxtemp%10,
//Ksr 2
Ksro/10, Ksro%10,
//Typ 1
WaveType,
//Power 3
(int)PowerAll, ((int)(PowerAll*10))%10, ((int)(PowerAll*100))/10%10
);
// uint8_t str_buff[]="n1.val=0";
// sprintf((char *)str_buff, "n1.val=%d%d",
// Freq/1000, Freq/100%10
// );
HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
HAL_UART_Transmit(&huart1,EndNum,sizeof(EndNum),10000);
}
void SendBerry(void)
{
uint8_t str_buff[10]="$000-0000$";
unsigned int i=0;
for (i=0; i<512; i++)
{
sprintf((char *)str_buff, "$%d%d%d-%d%d%d%d#",i/100, i/10%10, i%10, (int)MagBufArray[i]/1000, (int)MagBufArray[i]/100%10, (int)MagBufArray[i]/10%10, (int)MagBufArray[i]%10);
HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
}
}
void FindMaxFreq(void)
{
unsigned int Max[4] = {0}, Ko=0;
unsigned int j = 0;
unsigned int Maxj[4] = {0} ;
// unsigned int PeriodPoint = 0;
float Voltage[4];
uint8_t str_buff[10]="F=00000Hz";
// float K = 0;
// unsigned char Ksro = 0;
float sum[2] = {0};
volatile double tempsum = 0;
double Ksr = 0;
float Ksum = 0;
float VoltagePow[4] = {0};
// float VoltageSumPow[2] = {0};
for (j=1; j<512; j++)
{
if (MagBufArray[j] > Max[0])
{
Max[0] = MagBufArray[j];
Maxj[0] = j;
}
}
for (j=1; j<512; j++)
{
if (j == Maxj[0])
{
continue;
}
if (MagBufArray[j] > Max[1] && MagBufArray[j] > MagBufArray[j+1] && MagBufArray[j] > MagBufArray[j-1])
{
Max[1] = MagBufArray[j];
Maxj[1] = j;
}
}
for (j=1; j<512; j++)
{
if (j == Maxj[0] || j == Maxj[1])
{
continue;
}
if (MagBufArray[j] > Max[2]&& MagBufArray[j] > MagBufArray[j+1] && MagBufArray[j] > MagBufArray[j-1])
{
Max[2] = MagBufArray[j];
Maxj[2] = j;
}
}
for (j=1; j<512; j++)
{
if (j == Maxj[0] || j == Maxj[1] || j == Maxj[2])
{
continue;
}
if (MagBufArray[j] > Max[3] && MagBufArray[j] > MagBufArray[j+1] && MagBufArray[j] > MagBufArray[j-1])
{
Max[3] = MagBufArray[j];
Maxj[3] = j;
}
}
for (j=0; j<4; j++)
{
Maxj[j] *= FREQUENCYRESOLUTION;
}
Freq = Maxj[0];
Period = (int)(10000/Freq);
// for (j=0; j<4; j++)
// {
// sprintf((char *)str_buff, "Vp%d=%d%d%d%d%dV \n", // ·ù¶ÈÅųöÀ´
// j+1 ,((int)(Max[j]*(0.000805)))/10000,((int)(Max[j]*(0.000805)/1000))%10,((int)(Max[j]*(0.000805)))/100%10,((int)(Max[j]*(0.000805)))/10%10,((int)(Max[j]*(0.000805)))%10);
// HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
// }
for (j=0; j<4; j++)
{
Voltage[j] = Max[j]*0.000805;
}
for (j=0; j<4; j++)
{
VoltagePow[j] = Voltage[j]*Voltage[j];
sum[0] += VoltagePow[j];
}
for (j=1; j<4; j++)
{
sum[1] += Voltage[j]*Voltage[j];
}
Ksr = sqrt(sum[1]/sum[0]);
Ksro = (int)(Ksr*100);
// sprintf((char *)str_buff, "Ksr=%d%d%%", // ÐźÅÊ§Õæ¶È
// Ksro/10, Ksro%10);
// HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
if (CountKChoice++ < 20)
{
K[CountKChoice] = Max[0]/Max[1];
for (j=0; j<20; j++)
{
Ksum += K[CountKChoice];
}
Ksum /= 20;
// Ko = (int)(Ksum*100);
// sprintf((char *)str_buff, "K=%d.%d%d", // ÀàÐÍKÅųöÀ´
// Ko/100, Ko/10%10, Ko%10);
// HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
if (Ksum >= 2 && Ksum <5)// 1kHz K = 2-5
{
WaveType = 1;
PowerAll = (Maxtemp*Maxtemp)/2000000; // Vpp = Maxtemp/100,
PowerWave[0] = PowerAll/4;
for (j=1; j<4; j++)
{
PowerWave[j] = VoltagePow[j] / 50;
}
// HAL_UART_Transmit(&huart1, "Sine",sizeof("Sine"),10000);
}
else if (Ksum > 15)
{
WaveType = 0;
PowerAll = 3*(Maxtemp*Maxtemp)/4000000; // 3*Vpp/(Maxtemp*2*(2^-2)*50*10000)
PowerWave[0] = PowerAll*0.666;
for (j=1; j<4; j++)
{
PowerWave[j] = VoltagePow[j] / 50;
}
// HAL_UART_Transmit(&huart1, "Tri",sizeof("Tri"),10000);
}
else
{
WaveType = 2;
PowerAll = (Maxtemp*Maxtemp)/6007286; // Vpp = Maxtemp/100, (0.577*Vpp/2)^2/50/10000
//PowerWave[0] = PowerAll/4;
for (j=1; j<4; j++)
{
PowerWave[j] = VoltagePow[j] / 50;
}
// Ksum = 0;
}
Ksum = 0;
CountKChoice = 0;
}
// for (j=0; j<4; j++)
// {
// sprintf((char *)str_buff, "Vp%d=%d%d%d%d%dV \n", // ·ù¶ÈÅųöÀ´
// j+1 ,Max[j]/10000,Max[j]/1000%10,Max[j]/100%10,Max[j]/10%10,Max[j]%10);
// HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
sprintf((char *)str_buff, "F%d=%d%d%d%d%dHz \n", // ƵÂÊÅųöÀ´
j+1 ,Maxj[j]/10000,Maxj[j]/1000%10,Maxj[j]/100%10,Maxj[j]/10%10,Maxj[j]%10);
HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
// }
// HAL_UART_Transmit(&huart1,"\n",sizeof("\n"),10000);
// sprintf((char *)str_buff, "t2.txt=\"%d%d%d%d%d%d\"",Max/100000,Max/10000%10,Max/1000%10,Max/100%10,Max/10%10,Max%10);
// HAL_UART_Transmit(&huart1,str_buff,sizeof(str_buff),10000);
// HAL_UART_Transmit(&huart1,EndNum,sizeof(EndNum),10000);
}
/**
* @brief System Clock Configuration
* @retval None
*/
void SystemClock_Config(void)
{
RCC_OscInitTypeDef RCC_OscInitStruct = {0};
RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};
/** Initializes the CPU, AHB and APB busses clocks
*/
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
RCC_OscInitStruct.HSIState = RCC_HSI_ON;
RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;
RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI_DIV2;
RCC_OscInitStruct.PLL.PLLMUL = RCC_PLL_MUL8;
if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
{
Error_Handler();
}
/** Initializes the CPU, AHB and APB busses clocks
*/
RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
|RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV1;
RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;
if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_1) != HAL_OK)
{
Error_Handler();
}
PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_ADC;
PeriphClkInit.AdcClockSelection = RCC_ADCPCLK2_DIV4;
if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
{
Error_Handler();
}
}
/* USER CODE BEGIN 4 */
/* USER CODE END 4 */
/**
* @brief This function is executed in case of error occurrence.
* @retval None
*/
void Error_Handler(void)
{
/* USER CODE BEGIN Error_Handler_Debug */
/* User can add his own implementation to report the HAL error return state */
/* USER CODE END Error_Handler_Debug */
}
#ifdef USE_FULL_ASSERT
/**
* @brief Reports the name of the source file and the source line number
* where the assert_param error has occurred.
* @param file: pointer to the source file name
* @param line: assert_param error line source number
* @retval None
*/
void assert_failed(uint8_t *file, uint32_t line)
{
/* USER CODE BEGIN 6 */
/* User can add his own implementation to report the file name and line number,
tex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */
/* USER CODE END 6 */
}
#endif /* USE_FULL_ASSERT */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
stm32代码下载链接
附录3 树莓派的代码
#-*- coding:utf-8 -*-
import serial
import time
import matplotlib.pyplot as plt
ser = serial.Serial("/dev/ttyAMA0", 115200) # 位置1
ser.flushInput() # 位置2
ser.write("begin".encode("utf-8")) # 位置3
RecvList = {}
tempread = ''
first = ''
def main():
maxindex = 1
CompVul = 0
while True:
first = ser.read(1)
if first[0] == 36:
tempread = ser.read(9)
if tempread[8] == 35:
RecvList[int(tempread[0:3])] = int(tempread[4:8])
if len(RecvList) == 512:
# ser.close()
plt.clf()
plt.ion()
for i in range(512):
plt.plot([i,i],[0,RecvList[i]])
if (CompVul < RecvList[i] and i != 0):
CompVul = RecvList[i]
maxindex = i
for i in range(512):
if (CompVul < RecvList[0] and i != 0):
CompVul = RecvList[i]
maxindex = i
plt.text(0,RecvList[0],'(0, %d) DC=%fV'%(RecvList[0], RecvList[0]*0.000805))
#plt.text(maxindex, CompVul, '(%d,%d) F=%dHz Vp=%fV \n'%(maxindex,CompVul,maxindex*19.5+8,CompVul*0.000805))
plt.text(0, -50, '(%d,%d) F=%dHz Vp=%fV \n'%(maxindex,CompVul,maxindex*19.5,CompVul*0.000805))
RecvList.clear()
plt.pause(1)
#ser.flushInput()
# ser.open()
if __name__ == '__main__':
main()