久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 1674|回復: 1
收起左側

想利用單片機制作一個遙控器,問題求解

[復制鏈接]
ID:968724 發表于 2021-11-5 18:34 | 顯示全部樓層 |閱讀模式
/************* 發送脈沖函數 **************/
void        IR_TxPulse(u16 pulse)
{
        tx_cnt = pulse;
        B_Space = 0;        //發脈沖
        CCAPM2 = 0x48 | 0x04 | 0x01;        //工作模式 0x00: PCA_Mode_Capture,  0x42: PCA_Mode_PWM,  0x48: PCA_Mode_SoftTimer
        CR = 1;                //啟動
        while(CR);
        P_IR_TX = IR_TX_OFF;
}

代碼中 CCAPM2   有什么用求解   在代碼中也沒看見CCAP2L 和CCAP2H 附值  搞不懂這段有什么用   求大神指點



以下是下載的代碼
/*---------------------------------------------------------------------*/
/* --- STC MCU International Limited ----------------------------------*/
/* --- STC 1T Series MCU Demo Programme -------------------------------*/
/* 如果要在程序中使用此代碼,請在程序中注明使用了宏晶科技的資料及程序   */
/*---------------------------------------------------------------------*/



/*************        本程序功能說明        **************


用戶可以在宏定義中改變MCU主時鐘頻率. 范圍 8MHZ ~ 33MHZ.

紅外接收程序。模擬市場上用量最大的NEC的編碼。

用戶可以在宏定義中指定用戶碼.

使用PCA0軟件定時產生38KHZ載波, 1/3占空比, 每個38KHZ周期發射管發射9us,關閉16.3us.

使用開發板上的16個IO掃描按鍵, MCU不睡眠, 連續掃描按鍵.

當鍵按下, 第一幀為數據, 后面的幀為重復爭,不帶數據, 具體定義請自行參考NEC的編碼資料.

鍵釋放后, 停止發送.

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

#define         MAIN_Fosc                22118400UL        //定義主時鐘

#include        "STC15Fxxxx.H"


/*************        紅外發送相關變量        **************/
#define        User_code        0xFF00                //定義紅外用戶碼

sbit        P_IR_TX   = P3^7;        //定義紅外發送端口
#define        IR_TX_ON        0
#define        IR_TX_OFF        1

u16                PCA_Timer0;        //PCA2軟件定時器變量
bit                B_Space;        //發送空閑(延時)標志
u16                tx_cnt;                //發送或空閑的脈沖計數(等于38KHZ的脈沖數,對應時間), 紅外頻率為38KHZ, 周期26.3us
u8                TxTime;                //發送時間


/*************        IO口定義        **************/
sbit        P_HC595_SER   = P4^0;        //pin 14        SER                data input
sbit        P_HC595_RCLK  = P5^4;        //pin 12        RCLk        store (latch) clock
sbit        P_HC595_SRCLK = P4^3;        //pin 11        SRCLK        Shift data clock

/*************        IO鍵盤變量聲明        **************/

u8        IO_KeyState, IO_KeyState1, IO_KeyHoldCnt;        //行列鍵盤變量
u8        KeyHoldCnt;        //鍵按下計時
u8        KeyCode;        //給用戶使用的鍵碼, 1~16有效


/*************        本地函數聲明        **************/
void        delay_ms(u8 ms);
void        DisableHC595(void);
void        IO_KeyScan(void);
void        PCA_config(void);
void        IR_TxPulse(u16 pulse);
void        IR_TxSpace(u16 pulse);
void        IR_TxByte(u8 dat);




/********************** 主函數 ************************/
void main(void)
{
        P0M1 = 0;        P0M0 = 0;        //設置為準雙向口
        P1M1 = 0;        P1M0 = 0;        //設置為準雙向口
        P2M1 = 0;        P2M0 = 0;        //設置為準雙向口
        P3M1 = 0;        P3M0 = 0;        //設置為準雙向口
        P4M1 = 0;        P4M0 = 0;        //設置為準雙向口
        P5M1 = 0;        P5M0 = 0;        //設置為準雙向口
        P6M1 = 0;        P6M0 = 0;        //設置為準雙向口
        P7M1 = 0;        P7M0 = 0;        //設置為準雙向口
        
        PCA_config();
        P_IR_TX = IR_TX_OFF;
        
        EA = 1;                                                //打開總中斷
        
        DisableHC595();                //禁止掉學習板上的HC595顯示,省電

        while(1)
        {
                delay_ms(30);                //30ms
                IO_KeyScan();

                if(KeyCode != 0)                //檢測到鍵碼
                {
                        TxTime = 0;
                                                                //一幀數據最小長度 = 9 + 4.5 + 0.5625 + 24 * 1.125 + 8 * 2.25 = 59.0625 ms
                                                                //一幀數據最大長度 = 9 + 4.5 + 0.5625 + 8 * 1.125 + 24 * 2.25 = 77.0625 ms
                        IR_TxPulse(342);        //對應9ms,同步頭                9ms
                        IR_TxSpace(171);        //對應4.5ms,同步頭間隔        4.5ms
                        IR_TxPulse(21);                //開始發送數據                        0.5625ms

                        IR_TxByte(User_code%256);        //發用戶碼低字節
                        IR_TxByte(User_code/256);        //發用戶碼高字節
                        IR_TxByte(KeyCode);                        //發數據
                        IR_TxByte(~KeyCode);                //發數據反碼
                        
                        if(TxTime < 56)                //一幀按最大77ms發送, 不夠的話,補償時間                108ms
                        {
                                TxTime = 56 - TxTime;
                                TxTime = TxTime + TxTime / 8;
                                delay_ms(TxTime);
                        }
                        delay_ms(31);

                        while(IO_KeyState != 0)        //鍵未釋放
                        {
                                IR_TxPulse(342);        //對應9ms,   同步頭                9ms
                                IR_TxSpace(86);                //對應2.25ms,同步頭間隔        2.25ms
                                IR_TxPulse(21);                //開始發送數據                                 0.5625ms
                                delay_ms(96);
                                IO_KeyScan();
                        }
                        KeyCode = 0;
                }
        }
}
/**********************************************/

//========================================================================
// 函數: void  delay_ms(unsigned char ms)
// 描述: 延時函數。
// 參數: ms,要延時的ms數, 這里只支持1~255ms. 自動適應主時鐘.
// 返回: none.
// 版本: VER1.0
// 日期: 2013-4-1
// 備注:
//========================================================================
void  delay_ms(u8 ms)
{
     u16 i;
         do{
              i = MAIN_Fosc / 13000;
                  while(--i)        ;   //13T per loop
     }while(--ms);
}



void DisableHC595(void)
{               
        u8        i;
        P_HC595_SER   = 1;
        for(i=0; i<20; i++)
        {
                P_HC595_SRCLK = 1;
                P_HC595_SRCLK = 0;
        }
        P_HC595_RCLK = 1;
        P_HC595_RCLK = 0;                                                        //鎖存輸出數據
        P_HC595_RCLK = 1;
        P_HC595_RCLK = 0;                                                        //鎖存輸出數據
}


/*****************************************************
        行列鍵掃描程序
        使用XY查找4x4鍵的方法,只能單鍵,速度快

   Y     P04      P05      P06      P07
          |        |        |        |
X         |        |        |        |
P00 ---- K00 ---- K01 ---- K02 ---- K03 ----
          |        |        |        |
P01 ---- K04 ---- K05 ---- K06 ---- K07 ----
          |        |        |        |
P02 ---- K08 ---- K09 ---- K10 ---- K11 ----
          |        |        |        |
P03 ---- K12 ---- K13 ---- K14 ---- K15 ----
          |        |        |        |
******************************************************/


u8 code T_KeyTable[16] = {0,1,2,0,3,0,0,0,4,0,0,0,0,0,0,0};

void IO_KeyDelay(void)
{
        u8 i;
        i = 60;
        while(--i)        ;
}

void        IO_KeyScan(void)        //50ms call
{
        u8        j;

        j = IO_KeyState1;        //保存上一次狀態

        P0 = 0xf0;        //X低,讀Y
        IO_KeyDelay();
        IO_KeyState1 = P0 & 0xf0;

        P0 = 0x0f;        //Y低,讀X
        IO_KeyDelay();
        IO_KeyState1 |= (P0 & 0x0f);
        IO_KeyState1 ^= 0xff;        //取反
        
        if(j == IO_KeyState1)        //連續兩次讀相等
        {
                j = IO_KeyState;
                IO_KeyState = IO_KeyState1;
                if(IO_KeyState != 0)        //有鍵按下
                {
                        F0 = 0;
                        if(j == 0)        F0 = 1;        //第一次按下
                        else if(j == IO_KeyState)
                        {
                                if(++IO_KeyHoldCnt >= 20)        //1秒后重鍵
                                {
                                        IO_KeyHoldCnt = 18;
                                        F0 = 1;
                                }
                        }
                        if(F0)
                        {
                                j = T_KeyTable[IO_KeyState >> 4];
                                if((j != 0) && (T_KeyTable[IO_KeyState& 0x0f] != 0))
                                        KeyCode = (j - 1) * 4 + T_KeyTable[IO_KeyState & 0x0f] + 16;        //計算鍵碼,17~32
                        }
                }
                else        IO_KeyHoldCnt = 0;
        }
        P0 = 0xff;
}



/************* 發送脈沖函數 **************/
void        IR_TxPulse(u16 pulse)
{
        tx_cnt = pulse;
        B_Space = 0;        //發脈沖
        CCAPM2 = 0x48 | 0x04 | 0x01;        //工作模式 0x00: PCA_Mode_Capture,  0x42: PCA_Mode_PWM,  0x48: PCA_Mode_SoftTimer
        CR = 1;                //啟動
        while(CR);
        P_IR_TX = IR_TX_OFF;
}

/************* 發送空閑函數 **************/
void        IR_TxSpace(u16 pulse)
{
        tx_cnt = pulse;
        B_Space = 1;        //空閑
        CCAPM2 = 0x48 | 0x01;        //工作模式 0x00: PCA_Mode_Capture,  0x42: PCA_Mode_PWM,  0x48: PCA_Mode_SoftTimer
        CR = 1;                //啟動
        while(CR);
        P_IR_TX = IR_TX_OFF;
}


/************* 發送一個字節函數 **************/
void        IR_TxByte(u8 dat)
{
        u8 i;
        for(i=0; i<8; i++)
        {
                if(dat & 1)                IR_TxSpace(63),        TxTime += 2;        //數據1對應 1.6875 + 0.5625 ms
                else                        IR_TxSpace(21),        TxTime++;                //數據0對應 0.5625 + 0.5625 ms
                IR_TxPulse(21);                        //脈沖都是0.5625ms
                dat >>= 1;                                //下一個位
        }
}

//========================================================================
// 函數: void        PCA_config(void)
// 描述: PCA配置函數.
// 參數: None
// 返回: none.
// 版本: V1.0, 2012-11-22
//========================================================================
void        PCA_config(void)
{
        //  PCA0初始化
        CCON = 0x00;        //清除所有中斷標志
        CCAPM0  = 0x48 | 0x01;        //工作模式 + 中斷允許 0x00: PCA_Mode_Capture,  0x42: PCA_Mode_PWM,  0x48: PCA_Mode_SoftTimer
        PCA_Timer0 = 100;                //隨便給一個小的初值
        CCAP0L = (u8)PCA_Timer0;        //將影射寄存器寫入捕獲寄存器,先寫CCAP0L
        CCAP0H = (u8)(PCA_Timer0 >> 8);        //后寫CCAP0H

        PPCA = 1;        //高優先級中斷
        CMOD  = (CMOD  & ~0xe0) | 0x08;        //選擇時鐘源, 0x00: 12T, 0x02: 2T, 0x04: Timer0溢出, 0x06: ECI, 0x08: 1T, 0x0A: 4T, 0x0C: 6T, 0x0E: 8T
        CH = 0;
        CL = 0;
        CR = 0;
        tx_cnt = 2;
}

//========================================================================
// 函數: void        PCA_Handler (void) interrupt PCA_VECTOR
// 描述: PCA中斷處理程序.
// 參數: None
// 返回: none.
// 版本: V1.0, 2012-11-22
//========================================================================

#define        D_38K_DUTY        ((MAIN_Fosc * 26) / 1000000UL + MAIN_Fosc / 3000000UL)        /*         38KHZ周期時間        26.3us */
#define        D_38K_OFF        ((MAIN_Fosc * 17) / 1000000UL + MAIN_Fosc / 3000000UL)        /* 發射管關閉時間        17.3us */
#define        D_38K_ON        ((MAIN_Fosc * 9) / 1000000UL)                                                        /* 發射管導通時間        9us */

void        PCA_Handler (void) interrupt PCA_VECTOR
{
        CCON = 0x40;        //清除所有中斷標志,但不關CR
        if(!B_Space)        //發送載波
        {                                                                //發送脈沖,交替裝載TH0值,溢出時自動重裝
                P_IR_TX = ~P_IR_TX;
                if(P_IR_TX)
                {
                        PCA_Timer0 += D_38K_OFF;        //裝載高電平時間        17.3us
                        if(--tx_cnt == 0)        CR = 0;        //pulse has sent,        stop
                }
                else        PCA_Timer0 += D_38K_ON;        //裝載低電平時間        9us
        }
        else        //發送暫停時間
        {
                PCA_Timer0 += D_38K_DUTY;        //裝載周期時間        26.3us
                if(--tx_cnt == 0)        CR = 0;        //空閑時間
        }
        CCAP0L = (u8)PCA_Timer0;                        //將影射寄存器寫入捕獲寄存器,先寫CCAP0L
        CCAP0H = (u8)(PCA_Timer0 >> 8);        //后寫CCAP0H
}


回復

使用道具 舉報

ID:624769 發表于 2021-11-5 20:51 | 顯示全部樓層
代碼中的注釋不是注明了么?

0x48 : 當定時器用。

至于,沒有看到 CCAP2L 和CCAP2H  的賦值兩個可能,可能1,只需要0就可以了。可能2,CCAP2的設置,因為種種原因放棄了。但是代碼沒有刪除干凈。

最后,遙控器,那么簡單的一個功能,有必要搞CCAP么? 不做學習型的話,連定時器都可以不用。
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 我要看黄色录像一级片 | 91社区视频| 中文字幕亚洲一区 | 国产在线精品一区二区三区 | 二区在线观看 | 欧美成人精品在线 | 国产精品一区二区三区四区五区 | 午夜影晥| 伊人免费在线 | 久久久www | 久久久久久天堂 | 欧美不卡网站 | 91色综合 | 日韩一区二区三区在线 | 99热视| 国产精品视频网 | 国产一区二区三区四区在线观看 | 精品久久久久久久久久久久 | 亚洲精品中文在线 | av网址在线 | 中文字幕亚洲欧美 | 国产精品一区在线播放 | 一区二区福利视频 | 精品99久久 | 成人三区四区 | 国产精品永久 | 欧美亚洲视频 | 天天色影视综合 | 久久精品久久久久久 | 欧美精品欧美精品系列 | 亚洲综合二区 | 国产欧美在线观看 | 特a毛片 | 欧美视频一区二区三区 | 欧美高清性xxxxhdvideosex | 欧美日韩在线视频一区 | 懂色中文一区二区在线播放 | 久久久成人精品 | 懂色中文一区二区在线播放 | 亚洲成人毛片 | 欧美一区二区三区在线视频 |