STM8S的按鍵PWM調光燈歷程

STM8SPWM應用

前幾天有個項目用到PWM,今天整理下,弄個氛圍燈;記錄下,以後忘記了返回來還能看看。

思路就是在硬件端設置個按鍵,按下全局變量Key_num的值+1,按鍵一開始我用輪詢法做的,後來覺得輪詢法延時可能導致未知的問題,現在用中斷法做;根據Key_num的值,用switch語句選擇要變換的模樣。
上代碼:

/*****************************************************************************
  * @function  : Tim2_Init
  * @brief     : TIM2初始化函數 CH1用作出LED——G的呼吸變化燈
  * @note      : STM8S005
  * @param     : null
  * @retval    : null
  * @author    : 2016.03.23 by Steam.Yang 
                2016.11.02  RPP 學習並增加註釋
******************************************************************************/
void Tim2_Init(void)                    //TIM2的初始化語句們
{
    //配置通道1
        TIM2_TimeBaseInit(TIM2_PRESCALER_8, 999);              //第一步配置時基單元,先設置預分頻PSCRH/L高低八位 寄存器,再設置自動裝載寄存器ARRH/L。
    TIM2_OC1Init(TIM2_OCMODE_PWM1,
                     TIM2_OUTPUTSTATE_ENABLE,
                     0, 
                     TIM2_OCPOLARITY_LOW);                      //然後配置通道的輸出模式爲PWM,啓用輸出比較,佔空比設置爲0,輸出爲低電平
    TIM2_OC1PreloadConfig(ENABLE);
        TIM2_Cmd(ENABLE); 


    //配置通道2
        TIM2_TimeBaseInit(TIM2_PRESCALER_8, 999);              //第一步配置時基單元,先設置預分頻PSCRH/L高低八位 寄存器,再設置自動裝載寄存器ARRH/L。
        TIM2_OC2Init(TIM2_OCMODE_PWM1,
                     TIM2_OUTPUTSTATE_ENABLE,
                     0, 
                     TIM2_OCPOLARITY_LOW);                      //然後配置通道的輸出模式爲PWM,啓用輸出比較,佔空比設置爲0,輸出爲(低電平).105s4是低電平點亮
        TIM2_OC2PreloadConfig(ENABLE);                          //開啓預裝載寄存器
        TIM2_Cmd(ENABLE);                                       //最後的開啓  啓用定時器



        //配置通道3
            TIM2_TimeBaseInit(TIM2_PRESCALER_8, 999);            //第一步配置時基單元,先設置預分頻PSCRH/L高低八位 寄存器,再設置自動裝載寄存器ARRH/L。
    TIM2_OC3Init(TIM2_OCMODE_PWM1,
                     TIM2_OUTPUTSTATE_ENABLE,
                     0, 
                     TIM2_OCPOLARITY_LOW);                      //然後配置通道的輸出模式爲PWM,啓用輸出比較,佔空比設置爲0,輸出爲低電平
    TIM2_OC3PreloadConfig(ENABLE);
    TIM2_Cmd(ENABLE); 



}



這段代碼爲PWM初始化代碼,被折騰了好幾天,手頭上的105S4跟別人就是不一樣,他非要低電平點亮小燈。。。。,心累這段代碼比較重要。

下面的是主函數


int main( void )
{


        CLK_HSICmd(ENABLE);     //配置個時鐘先
        GPIO_Init(GPIOC, GPIO_PIN_7, GPIO_MODE_IN_PU_NO_IT);//初始化按鍵的GPIO口 上拉輸入
        Tim2_Init();                        //再初始化TIM2 PWM1輸出模式



    while(1)
    {

    Key_Press();                        //再調用按鍵

                                    //再給PWM呼吸燈佔空比的值
        if((!sta) && (PWM<1000))    //比較好的循環

                {
                        PWM++;
            if(PWM == 1000) sta = 1;

        }
                if((sta) && (PWM>0))
                {
                  PWM--;
                  if(PWM == 0) sta = 0;
                }

        Delay_Us(500);               //延時調整呼吸的速度

                switch(Key_num){

                case 0:                         //沒有按下 或者按到第7下時 全滅,進行清零
                TIM2_SetCompare1(0);
                TIM2_SetCompare2(0);
                TIM2_SetCompare3(0);

                break;


                case 1:
                    TIM2_SetCompare1(1000);     //按第一下,計數1, W燈常亮1 (1000常亮 PWM呼吸  0關閉)
                                break;
                case 2:                         //按第二下,計數2,W燈呼吸2
                    //TIM2_Cmd(DISABLE);//本來想關掉PWM來進行關閉燈亮,結果不能關,關了後面就不執行了 要重新做初始化  要做其他處理
                    TIM2_SetCompare1(PWM);
                                break;
                case 3:
                    TIM2_SetCompare1(0);
                    TIM2_SetCompare2(1000);     //按三下,計數3,G燈常亮 ,同時要關掉前面亮着的
                break;

                 case 4:                        //按四下,計數4,G燈呼吸 
                    TIM2_SetCompare2(PWM);      //
                break;

                case 5: 
                    TIM2_SetCompare2(0);        //按第五下,計數5,B燈常亮 
                    TIM2_SetCompare3(1000);     //
                break;

                case 6:                         //按第六下,計數6,B燈呼吸 
                    TIM2_SetCompare3(PWM);      //
                break;

                case 7:                         //全呼吸
                    TIM2_SetCompare1(PWM);

                    TIM2_SetCompare2(PWM);
        `




                TIM2_SetCompare3(PWM);

                }


    }

}

PWM不能關 關了就要重新初始化,所以選變成0 他就不亮了。這個循環結構是非常好的循環結構,很多書上的循環結構都是從0-100 沒有100-0 燈呼吸很突兀,所以建議用這種。
中斷的按鍵函數
放在中斷裏面

if(GPIO_ReadInputPin(GPIOC, GPIO_PIN_7) == 0)
    {
        delay_us(5000);     //去抖延時
        if(GPIO_ReadInputPin(GPIOC, GPIO_PIN_7) == 0)
        {
            while(GPIO_ReadInputPin(GPIOC, GPIO_PIN_7) == 0);
            Key_num++;
            if(Key_num == 2)
            {
                Key_num=0;

            }
        }
    }

寫完了,有什麼再補充吧,
吐槽這鬼編譯器,噁心 好幾次都代碼上不去

補充:
我師父教我的 哈哈
首先該計數器,循環技術,例如從0到ARR,那麼這個ARR就決定了PWM的週期,
PWM週期=(ARR+1)*計數器時鐘的週期.
PWM頻率=計數器時鐘的頻率/(ARR+1)
在計數器模塊中還有一個比較器,比較器有兩個輸入,一個是計數器的當前值,另一個是可以設置的數,這個數來着一個比較寄存器.當計數器的值小於比較寄存器的值時,輸出爲1(也可以是0),當計數器的值大於或者等於比較器寄存器的值時,輸出爲0(也可以是1,與前面對應).

STM8–PWM初始化流程
1、時基初始化,得出PWM的頻率(週期)
2、初始化輸出比較通道,確定是哪個模式、通道、脈衝寬度(確定佔空比)、和電平。
3、輸出比較通預裝載使能
4、允許主輸出(TIM1)
5、使能定時器

隨時改變PWM頻率:
void TIM1_SetAutoreload(uint16_t Autoreload);//設置自動重裝寄存器的值
隨時改變佔空比:
TIM1_SetCompare1(0x0000);//設置捕獲比較寄存器的值

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章