STM32或者RSIC-V输出SPWM波形

直接上代码吧,其余的内容可以到别的地方搜索,包括什么是SPWM

 

/*@Note
PWM output routine:
TIM1_CH1(PA8)
This example demonstrates that the TIM_CH1(PA8) pin outputs PWM in PWM mode 1 and
PWM mode 2.

*/

#include "debug.h"

/* PWM Output Mode Definition */
#define PWM_MODE1 0
#define PWM_MODE2 1

/* PWM Output Mode Selection */
//#define PWM_MODE PWM_MODE1
#define PWM_MODE PWM_MODE2

const int indexWave[] = {
0,2,5,8,10,12,14,16,19,22,24,26,28,30,33,36,38,
40,42,44,47,50,52,54,56,58,61,64,66,68,70,72,74,
77,80,82,84,86,88,91,94,96,98,100,102,104,106,109,112,
114,116,118,120,122,124,126,129,132,134,136,138,140,142,144,146,
……………………………………………………………………
-90,-88,-86,-84,-82,-79,-76,-74,-72,-70,-68,-66,-63,-60,-58,-56,
-54,-52,-49,-46,-44,-42,-40,-38,-35,-32,-30,-28,-26,-24,-21,-18,
-16,-14,-12,-10,-7,-4,-2
};  //中间的数据可以自己生成,这里省略掉!

//控制输出波形的频率
__IO uint16_t period_class = 24;  正弦频率为24HZ

#define POINT_NUM 1000   // 每个正弦周期对应1000个点

/**
* @brief 配置嵌套向量中断控制器NVIC
* @param 无
* @retval 无
*/
static void NVIC_Config_PWM(void)
{
NVIC_InitTypeDef NVIC_InitStructure;

/* Configure one bit for preemption priority */
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);

/* 配置TIM3_IRQ中断为中断源 */
NVIC_InitStructure.NVIC_IRQChannel = TIM1_UP_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}

/*********************************************************************
* @fn TIM1_OutCompare_Init
*
* @brief Initializes TIM1 output compare.
*
* @param arr - the period value.
* psc - the prescaler value.
* ccp - the pulse value.
*
* @return none
*/
void TIM1_PWMOut_Init( u16 arr, u16 psc, u16 ccp )
{
GPIO_InitTypeDef GPIO_InitStructure={0};

RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOA | RCC_APB2Periph_TIM1, ENABLE );

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init( GPIOA, &GPIO_InitStructure );

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;


/* 基本定时器配置 ,配合PWM表点数、中断服务函数中的period_cnt循环次数设置*/
/* 设置使得整个呼吸过程为3秒左右即可达到很好的效果 */

/* 基本定时器配置 */
//当定时器从0计数到 TIM_Period+1 ,为一个定时周期
TIM_TimeBaseStructure.TIM_Period = arr;
//设置预分频
TIM_TimeBaseStructure.TIM_Prescaler = psc;
//设置时钟分频系数:不分频(这里用不到)
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1 ;
//向上计数模式
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseStructure.TIM_RepetitionCounter = 0;
TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure);

 

/* PWM模式配置 */
//配置为PWM模式1
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
//使能输出
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_OutputNState = TIM_OutputNState_Enable;
//设置初始PWM脉冲宽度为0
TIM_OCInitStructure.TIM_Pulse = ccp;
//当定时器计数值小于CCR1_Val时为低电平
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;

TIM_OC1Init ( TIM1, &TIM_OCInitStructure ); //使能通道

TIM_OC1PreloadConfig ( TIM1, TIM_OCPreload_Enable ); //使能预装载

TIM_ARRPreloadConfig(TIM1, ENABLE); //使能TIM重载寄存器ARR


TIM_ITConfig(TIM1, TIM_IT_Update, ENABLE); //使能update中断
NVIC_Config_PWM();
/* TIM enable counter */
TIM_Cmd(TIM1, ENABLE); //使能定时器

TIM_CtrlPWMOutputs(TIM1, ENABLE );

}

/**
* timer1 IRQHandler
*/
void TIM1_UP_IRQHandler(void) __attribute__((interrupt("WCH-Interrupt-fast")));

void TIM1_UP_IRQHandler(){
static uint16_t pwm_index = 0; //用于PWM查表
if (TIM_GetITStatus(TIM1, TIM_IT_Update) != RESET){
TIM_SetCompare1(TIM1, POINT_NUM / 2 + indexWave[+ pwm_index++]);

if(pwm_index >= POINT_NUM){
pwm_index = 0;
}
TIM_ClearITPendingBit (TIM1, TIM_IT_Update); //必须要清除中断标志位
}

}

/*********************************************************************
* @fn main
*
* @brief Main program.
*
* @return none
*/
int main(void)
{
USART_Printf_Init(115200);
SystemCoreClockUpdate();
printf("SystemClk:%d\r\n",SystemCoreClock);
printf( "ChipID:%08x\r\n", DBGMCU_GetCHIPID() );
TIM1_PWMOut_Init( 1000, 3, 10 );  // 设置24KHz的波形

while(1);
}

posted @ 2024-08-27 17:48  毛豆*_*  阅读(9)  评论(1编辑  收藏  举报