如何用STC32产生SPWM波

2 篇文章 0 订阅
1 篇文章 0 订阅
前言

提示:这里可以添加本文要记录的大概内容:

  SPWM(Sinusoidal PWM)全称是正弦脉冲宽度调制,是一种 广泛应用于电机驱动,逆变电源等领域的调制技术。SPWM波是一种按正弦规律变化的一种PWM波形,是PWM的一种延伸,是一种可以等效成正弦波效果的PWM技术。

      SPWM的基本原理就是面积等效原理,即冲量相等而形状不同的窄脉冲加在具有惯性的环节上时,其效果基本相同。 我们在生成SPWM的过程中通常使用的采样方式有:自然采样法和规则采样法。


提示:以下是本篇文章正文内容,下面案例可供参考

一、如何生成SPWM波数组

利用网友提供的SPWM波生成工具,可以生成任意的点数的波形。

或者使用excel生成也是一样的:

二、主要程序:

/******************************************
本程序输出频率固定, 如果需要变频, 请用户自己设计变频方案.

本程序从P6.0(PWM1P)输出正相脉冲, 从P6.1(PWM1N)输出反相脉冲(互补).

下载时, 选择时钟 24MHz (用户可自行修改频率).

******************************************/

#include <STC32G.H>

#include "stdio.h"
#include "intrins.h"
#include "T_SineTable.h"

typedef 	unsigned char	u8;
typedef 	unsigned int	u16;
typedef 	unsigned long	u32;

#define MAIN_Fosc        24000000UL

/****************************** 用户定义宏 ***********************************/
#define PWM1_1      0x00	//P:P1.0  N:P1.1
#define PWM1_2      0x01	//P:P2.0  N:P2.1
#define PWM1_3      0x02	//P:P6.0  N:P6.1

#define PWM2_1      0x00	//P:P1.2/P5.4  N:P1.3
#define PWM2_2      0x04	//P:P2.2  N:P2.3
#define PWM2_3      0x08	//P:P6.2  N:P6.3

#define PWM3_1      0x00	//P:P1.4  N:P1.5
#define PWM3_2      0x10	//P:P2.4  N:P2.5
#define PWM3_3      0x20	//P:P6.4  N:P6.5

#define PWM4_1      0x00	//P:P1.6  N:P1.7
#define PWM4_2      0x40	//P:P2.6  N:P2.7
#define PWM4_3      0x80	//P:P6.6  N:P6.7
#define PWM4_4      0xC0	//P:P3.4  N:P3.3

#define ENO1P       0x01
#define ENO1N       0x02
#define ENO2P       0x04
#define ENO2N       0x08
#define ENO3P       0x10
#define ENO3N       0x20
#define ENO4P       0x40
#define ENO4N       0x80
/*****************************************************************************/

/*************  本地常量声明    **************/


/*************  本地变量声明    **************/
u16 PWM1_Duty;
u8	PWM1_Index;	//SPWM查表索引
u16 PWM2_Duty;
u8	PWM2_Index;	//SPWM查表索引
u16 PWM3_Duty;
u8	PWM3_Index;	//SPWM查表索引

/*************  本地函数声明    **************/


/********************* 主函数 *************************/
void main(void)
{
    WTST = 0;  //设置程序指令延时参数,赋值为0可将CPU执行指令的速度设置为最快
    EAXFR = 1; //扩展寄存器(XFR)访问使能
    CKCON = 0; //提高访问XRAM速度

    P0M1 = 0x00;   P0M0 = 0x00;   //设置为准双向口
    P1M1 = 0x00;   P1M0 = 0x00;   //设置为准双向口
    P2M1 = 0x00;   P2M0 = 0x00;   //设置为准双向口
    P3M1 = 0x00;   P3M0 = 0x00;   //设置为准双向口
    P4M1 = 0x00;   P4M0 = 0x00;   //设置为准双向口
    P5M1 = 0x00;   P5M0 = 0x00;   //设置为准双向口
    P6M1 = 0x00;   P6M0 = 0x00;   //设置为准双向口
    P7M1 = 0x00;   P7M0 = 0x00;   //设置为准双向口

    PWM1_Duty = 70;
	PWM2_Duty = 1677;
	PWM3_Duty = 1805;

    PWMA_CCER1 = 0x00; //写 CCMRx 前必须先清零 CCxE 关闭通道
    PWMA_CCER2 = 0x00;
    PWMA_CCMR1 = 0x60; //通道模式配置
    PWMA_CCMR2 = 0x60;
    PWMA_CCMR3 = 0x60;
//    PWMA_CCMR4 = 0x60;
    PWMA_CCER1 = 0x55; //配置通道输出使能和极性
    PWMA_CCER2 = 0x05;

    PWMA_ARRH = 0x09; //设置周期时间
    PWMA_ARRL = 0x60;
	
//	PWMA_PSCRH = 0x00;
//	PWMA_PSCRH = 0x0B;

    PWMA_CCR1H = (u8)(PWM1_Duty >> 8); //设置占空比时间
    PWMA_CCR1L = (u8)(PWM1_Duty);
	PWMA_CCR2H = (u8)(PWM2_Duty >> 8); //设置占空比时间
    PWMA_CCR2L = (u8)(PWM2_Duty);
	PWMA_CCR3H = (u8)(PWM3_Duty >> 8); //设置占空比时间
    PWMA_CCR3L = (u8)(PWM3_Duty);

     PWMA_DTR = 0x0C;   //设置死区时间

    PWMA_ENO = 0x00;
    PWMA_ENO |= ENO1P; //使能输出
    PWMA_ENO |= ENO1N; //使能输出
    PWMA_ENO |= ENO2P; //使能输出
    PWMA_ENO |= ENO2N; //使能输出
    PWMA_ENO |= ENO3P; //使能输出
    PWMA_ENO |= ENO3N; //使能输出
//    PWMA_ENO |= ENO4P; //使能输出
//    PWMA_ENO |= ENO4N; //使能输出

    PWMA_PS = 0x00;  //高级 PWM 通道输出脚选择位
    PWMA_PS |= PWM1_3; //选择 PWM1_3 通道
    PWMA_PS |= PWM2_3; //选择 PWM2_3 通道
    PWMA_PS |= PWM3_3; //选择 PWM3_3 通道
//    PWMA_PS |= PWM4_3; //选择 PWM4_3 通道

    PWMA_BKR = 0x80; //使能主输出
    PWMA_IER = 0x01; //使能中断
    PWMA_CR1 |= 0x01; //开始计时

    EA = 1;     //打开总中断

    while(1)
    {
    }
}


/******************** 中断函数 **************************/
void PWMA_ISR() interrupt PWMA_VECTOR 
{ 
    if(PWMA_SR1 & 0X01)
    {
        PWMA_SR1 &=~0X01; 
        PWM1_Duty = A_SinTable[PWM1_Index];
        if(++PWM1_Index >= 200)	PWM1_Index = 0;
//		PWM1_Index++;

        PWMA_CCR1H = (u8)(PWM1_Duty >> 8); //设置占空比时间
        PWMA_CCR1L = (u8)(PWM1_Duty);
		
		PWM2_Duty = B_SinTable[PWM2_Index];
        if(++PWM2_Index >= 200)	PWM2_Index = 0;
//		PWM2_Index++;

        PWMA_CCR2H = (u8)(PWM2_Duty >> 8); //设置占空比时间
        PWMA_CCR2L = (u8)(PWM2_Duty);
		
		PWM3_Duty = C_SinTable[PWM3_Index];
        if(++PWM3_Index >= 200)	PWM3_Index = 0;
//		PWM3_Index++;

        PWMA_CCR3H = (u8)(PWM3_Duty >> 8); //设置占空比时间
        PWMA_CCR3L = (u8)(PWM3_Duty);
    }
    PWMA_SR1 = 0;
}

  • 8
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值