Spwm算法研究,波形问题

2019-07-20 19:49发布

本帖最后由 imfly89 于 2016-9-22 11:11 编辑

利用STM32F4,高级定时器产生的三路SPWM。具体思路:对一个正弦波周期进行预采样,采样点数是12个点(SinePoint),既30度一个点。然后f(x) = N/2 + N/2-1 * sin(2πx/N) x∈[0…N-1],有这个公式取表格,N就是我量化的量,我取的32768,生成了12个数据表格。载波频率我设置了 Fp=15Khz,TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; 调制波的频率想在5-250hz之间可调的,所以设置了参数Fs。对于每一频率的正弦波调制波则对应的载波比就是Fp/Fs = N ,也就是说N个PWM波调制一个周期的正弦波,而又一个正弦波我只采样了12个点,所以在这N个波形里,采样x点与采样x+1点之间的PWM个说就是N/12 ,因为x点与x+1点有多个PWM波,所以我会在x点与x+1点插入差值,使得PWM占空比不会突变的太多,插入方法是计算x与x+1点的差值,然后差值/两点之间PWM的个数,该值就是平均值了,既我每次PWM中断,占空比对应上一次的PWM中断所增加的量。
代码:
const int SPsinetable[] =
{
//采样数 12 , 30度一个点                N = 32768
//f(x) = N/2 + N/2-1 * sin(2πx/N) x∈[0…N-1]
0x4000,0x6000,0x776C,0x7FFF,
0x776C,0x6000,0x4000,0x2001,
0x0894,0x0001,0x0894,0x2000
};

                t1 = SPsinetable[angle1%SinePoint] ;  //A相
                t2 = SPsinetable[(angle1+SinePoint/3 )% SinePoint]  ; //B相,120度
                t3 = SPsinetable[(angle1+SinePoint*2/3)% SinePoint] ;//C相   240度


                if(SPsinetable[angle1%SinePoint] > SPsinetable[(angle1+1)%SinePoint])        //A相,判断当前采样点与下一个采样点的大小,决定占空比是加还是减
                {
                        CompareTwo = SPsinetable[angle1%SinePoint] - SPsinetable[(angle1+1)%SinePoint] ;        //计算与下一个采样点的差值
                        AveTwo =        ((long)CompareTwo * (long)Addflag + (float)PhasePoint*0.5 )/ (PhasePoint+1); //插入平均值,四舍五入,Addflag:比如10次,差度是10,每次就是1,第一次+1*1,第二次+2*1,第三次+3*1
                        t1 -= (uint16_t)AveTwo ;        //计算周期占空比增量
                }
                else
                {
                        CompareTwo = SPsinetable[(angle1+1)%SinePoint] - SPsinetable[angle1%SinePoint] ;
                        AveTwo =        ((long)CompareTwo * (long)Addflag + (float)PhasePoint*0.5 )/ (PhasePoint+1);
                        t1 += (uint16_t)AveTwo;
                }

               //B C相同理计算,省空间就不列了
                Addflag ++ ;

                t1 = tpwm *  t1  >> 15 ;  //占空比计算,>>15是因为之前的量化了10的15次方
                t2 = tpwm *  t2  >> 15 ;
                t3 = tpwm *  t3  >> 15 ;


PWM中断程序:                             if(TIM_GetFlagStatus(TIM1, TIM_FLAG_Update) == SET)
                {
                        
                        if(Spwm_R_Flag) //开启标志
                        {                        
                                if(PwmTimes > PhasePoint)        //每个采样点之间的脉冲计数
                                {
                                        PwmTimes = 0 ;
                                        Addflag = 0 ;
                                        if(AngleR > (SinePoint-1)) AngleR = 0 ;  //采样完成一个周期,进行下一个周期
                                        AngleR ++ ;        //取下一个采样点
                                }
                                SVMR(RefSpeedR, AngleR);        //RefSpeedR,与此无关,忽略SVMR()就是占空比计算函数
                                PwmTimes ++ ;
                        }
                    }
以上就是我的SPWM的主要思路,目前情况是输出的波形经过RC滤波出来的波形  调制波频率越大,幅值却越小(见图)。高手指点说是我的算法问题,思来想去我想不通我算法漏洞在哪,所以发到论坛来大家一起参谋,顺便把我问题解决了,在此先谢谢大家了
             ,




友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。