TJ-WW03-H03/APP_smoke_N_V1.3/HARDWARE/HEATER/heater.c

249 lines
5.7 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "heater.h"
#include <stdio.h>
#include "public.h"
#include "adc_anychannel_continuousscan_interrupt.h"
#include "sim_eeprom.h"
volatile u32 heat_on_delay = 0;
volatile u32 keep_temp_time = 0;
volatile u32 temp_time_clok = 0;
void TIM2_GPIO_Init(void)
{
GPIO_InitTypeDef GPIO_InitStruct;
RCC_AHBPeriphClockCmd(RCC_AHBENR_GPIOA, ENABLE);
GPIO_PinAFConfig(GPIOA, GPIO_PinSource2, GPIO_AF_2);
GPIO_InitStruct.GPIO_Pin = GPIO_Pin_2;
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStruct);
}
void TIM2_PWM_Init(u16 arr, u16 psc)
{
TIM_TimeBaseInitTypeDef TIM_TimeBaseStruct;
TIM_OCInitTypeDef TIM_OCInitStruct;
NVIC_InitTypeDef NVIC_StructInit;
RCC_APB1PeriphClockCmd(RCC_APB1ENR_TIM2, ENABLE);
TIM_TimeBaseStructInit(&TIM_TimeBaseStruct);
TIM_TimeBaseStruct.TIM_Period = arr;
TIM_TimeBaseStruct.TIM_Prescaler = psc;
TIM_TimeBaseStruct.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimeBaseStruct.TIM_RepetitionCounter = 0;
TIM_TimeBaseStruct.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStruct);
//使能TIM2 NVIC中断优先级通道
NVIC_StructInit.NVIC_IRQChannel = TIM2_IRQn;
//配置TIM2 NVIC中断优先级
NVIC_StructInit.NVIC_IRQChannelPriority = 2;
//使能NVIC中断优先级
NVIC_StructInit.NVIC_IRQChannelCmd = ENABLE;
//根据配置的中断优先级参数初始化TIM2中断优先级
NVIC_Init(&NVIC_StructInit);
TIM_ClearFlag(TIM2, TIM_FLAG_CC3);
//使能TIM2向上计时中断
TIM_ITConfig(TIM2, TIM_IT_CC3, ENABLE);
TIM_OCStructInit(&TIM_OCInitStruct);
TIM_OCInitStruct.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStruct.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStruct.TIM_Pulse = 0;
TIM_OCInitStruct.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OC3Init(TIM2, &TIM_OCInitStruct);
TIM_OC3PreloadConfig(TIM2, TIM_OCPreload_Enable);
TIM_ForcedOC3Config(TIM2, TIM_ForcedAction_InActive);
TIM_ARRPreloadConfig(TIM2, ENABLE);
TIM_CtrlPWMOutputs(TIM2, ENABLE);
TIM_Cmd(TIM2, ENABLE);
}
void Heater_Init(void)
{
TIM2_GPIO_Init();
TIM2_PWM_Init(999,359); //20KHZ 防止异响 200hz 占空比可以调节到999
}
void TIM2_IRQHandler(void)
{
if(TIM_GetITStatus(TIM2, TIM_IT_CC3) != RESET)
{
TIM_ClearITPendingBit(TIM2, TIM_IT_CC3);
}
}
void duty(u8 mode, u16 pwm) // mode : 0 关断 1 开 pwm :占空比0-1000
{
static unsigned char PWM_1 = 0;
if(pwm>999)
pwm = 999;
switch( mode )
{
case 0: // 全关断
TIM_ForcedOC3Config(TIM2, TIM_OCMode_PWM1);
TIM_SetCompare3(TIM2, 0);
PWM_1 = pwm;
break;
case 1:
if( PWM_1 != pwm)
{
TIM_ForcedOC3Config(TIM2, TIM_OCMode_PWM1);
TIM_SetCompare3(TIM2, pwm);
}
PWM_1 = pwm;
break;
}
}
/****************************************
根据时间找出设定温度 work_temp_up(u32 sleep_time)
参数sleep_time 运行时间
*****************************************/
u16 work_temp_up(u32 sleep_time) // ms
{
int i = 0;
int time_s = sleep_time/1000;
u8 find_tmep_flag = 0;
u16 temp = 0;
//0 350 20 350
for( i = 0; i < g_work.m_set_other_hot.set_up_num; i ++ )
{
if( time_s >= g_work.m_set_other_hot.m_set_up[i]._time)
{
temp = g_work.m_set_other_hot.m_set_up[i]._temp;
find_tmep_flag = 1;
}
}
if( find_tmep_flag == 0 )
{
temp = g_work.m_set_other_hot.m_set_up[0]._temp;
}
#ifdef _debug_
//printf(" temp target = %d \n",temp);
#endif
return temp;
}
void temp_control_new(u16 temp,u8 mod)
{
static u32 pwm_buffer = 0;
static u8 over_heat =0;
static float last_temp = 0.0;
if( mod == 0)
{
over_heat = 0;
pwm_buffer = 0;
last_temp = 0.0;
duty(0,0);
temp_time_clok = 0;
}
else
{
bat_v_delay = 50;
////////////////////////调试动画使用
// if(heat_on_delay == 0 && heat_stage == 1)
// {
// heat_stage = 2;
// keep_temp_time = 20000; //抽吸时间二十秒
// }
// else if(keep_temp_time==0 && heat_stage == 2 )
// {
// heat_stage = 3;
// }
// printf("CCR3 = %d \n",TIM_GetCapture3(TIM2));
if(temp_all<temp && over_heat == 0)
{
last_temp = temp_all;
pwm_buffer = (temp-temp_all)/temp*690+300;//第一次升温需要高PWM采用pid中比例调整pwm,避免过热
duty(1,pwm_buffer);
}
else if(temp_all<temp && over_heat == 1)
{
if(temp_all<= last_temp)
{
pwm_buffer = TIM_GetCapture3(TIM2);
if(pwm_buffer<990)
{
duty(1,++pwm_buffer);
}
last_temp = temp_all;
}
}
else if(temp_all == temp)
{
last_temp = temp_all;
pwm_buffer = TIM_GetCapture3(TIM2);
over_heat =1;
}
else if(temp_all>temp )
{
if(temp_all>=last_temp)
{
pwm_buffer = TIM_GetCapture3(TIM2);
over_heat =1;
if(pwm_buffer > 50 )
{
duty(1,--pwm_buffer);
}
last_temp = temp_all;
}
}
if(heat_on_delay == 0 && heat_stage == 1)
{
heat_stage = 2;
keep_temp_time =(g_work.m_set_other_hot.set_all_time - g_work.m_set_other_hot.set_order_time)*1000;
}
}
}
void heat_control(void)
{
u16 temp_buffer;
if(heat_stage == 0)//没开始升温前初始化需要用到的参数
{
heat_on_delay = g_work.m_set_other_hot.set_order_time*1000;//预加热时间设置
temp_time_clok = 0;
heat_stage = 1;
}
else if(heat_stage == 1)
{
temp_buffer = work_temp_up(temp_time_clok);
temp_control_new(temp_buffer,1);
}
else if(heat_stage == 2)
{
if(keep_temp_time>10000)//最后十秒进呼吸效果
{
temp_buffer = work_temp_up(temp_time_clok);
temp_control_new(temp_buffer,1);
}
else
{
heat_stage = 3;
}
}
else if(heat_stage ==3)
{
if(keep_temp_time>0)//最后十秒进呼吸效果
{
temp_buffer = work_temp_up(temp_time_clok);
temp_control_new(temp_buffer,1);
}
else
{
temp_control_new(0,0);
}
}
}