With the project STM32: microSD Wav audio player with touchscreen I use microcontroller's PWM as 10 bit DAC but in first version of firmware I have found an annoying glitch during playback.
(coming soon video with glitch problem)
This problem is typical when you use TIM_OC1Init(TIM1,&TIM1_OCInitStructure) function to obtain PWM with costant frequency and variable duty cycle.
To solve this problem you can follow these steps:
First step: The initialization code
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
TIM_DeInit(TIM1);
/* Time Base configuration */
TIM1_TimeBaseStructure.TIM_Prescaler = 0x0;
TIM1_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Down;
TIM1_TimeBaseStructure.TIM_ClockDivision = 0x0;
TIM1_TimeBaseStructure.TIM_Period = 1020;
/* Channel 1,3 Configuration in PWM mode */
TIM1_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM1_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM1_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_Low;
TIM1_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Set;
TIM1_OCInitStructure.TIM_Pulse = 1024/2;
TIM_TimeBaseInit(TIM1,&TIM1_TimeBaseStructure);
TIM_OC1Init(TIM1,&TIM1_OCInitStructure);
TIM_OC3Init(TIM1, &TIM1_OCInitStructure);
/* TIM1 counter enable */
TIM_Cmd(TIM1,ENABLE);
TIM_CtrlPWMOutputs(TIM1,ENABLE);
Second step: Update Duty cycle periodically
After initialization, if you want to update duty cycle periodically, you don't use a TIM_OC1Init(TIM1,&TIM1_OCInitStructure) function because you load all field of TIM1_OCInitStructure struct losing firmware efficiency inevitably and causing a glitch during playback but you must update the PWM writing the registers directly as follows:
TIM2->CCR2 = duty1;
TIM2->CCR3 = duty2;
TIM2->CCR3 = duty2;