![]() |
發布時間: 2017-12-27 15:40
正文摘要:通過4*4鍵盤矩陣按鍵在LCD12864中顯示1~16,原理圖如下: 輸出結果為亂碼,按鍵狀態是否有掃描到? 請問我的程序該怎么改呢? 單片機源程序如下: /*----------------------------------------------- ... |
我也在做這個題的實訓,總是出現問題,開始我又找不到哪里有問題 |
xdn 發表于 2017-12-28 09:09 用STC12系列芯片P0~P4加電復位后都是高電平準雙向口,不必設置,給你這個例程主要是介紹不同組別端口組成的4*4矩陣鍵盤讀寫方法。 |
wulin 發表于 2017-12-27 20:43 //新一代 1T 8051系列,單片機i/o口的特殊功能寄存器 // 7 6 5 4 3 2 1 0 Reset Value sfr P0 = 0x80; //8 bitPort0 P0.7 P0.6 P0.5 P0.4 P0.3 P0.2 P0.1 P0.0 1111,1111 sfr P0M0 = 0x94; // 0000,0000 sfr P0M1 = 0x93; // 0000,0000 sfr P1 = 0x90; //8 bitPort1 P1.7 P1.6 P1.5 P1.4 P1.3 P1.2 P1.1 P1.0 1111,1111 sfr P1M0 = 0x92; // 0000,0000 sfr P1M1 = 0x91; // 0000,0000 sfr P1ASF = 0x9D; //P1 analog special function sfr P2 = 0xA0; //8 bitPort2 P2.7 P2.6 P2.5 P2.4 P2.3 P2.2 P2.1 P2.0 1111,1111 sfr P2M0 = 0x96; // 0000,0000 sfr P2M1 = 0x95; // 0000,0000 sfr P3 = 0xB0; //8 bitPort3 P3.7 P3.6 P3.5 P3.4 P3.3 P3.2 P3.1 P3.0 1111,1111 sfr P3M0 = 0xB2; // 0000,0000 sfr P3M1 = 0xB1; // 0000,0000 sfr P4 = 0xC0; //8 bitPort4 P4.7 P4.6 P4.5 P4.4 P4.3 P4.2 P4.1 P4.0 1111,1111 sfr P4M0 = 0xB4; // 0000,0000 sfr P4M1 = 0xB3; // 0000,0000 // 7 6 5 4 3 2 1 0 Reset Value sfr P4SW = 0xBB; //Port-4 switch - LVD_P4.6 ALE_P4.5 NA_P4.4 - - - - x000,xxxx sfr P5 = 0xC8; //8 bitPort5 - - - - P5.3 P5.2 P5.1 P5.0 xxxx,1111 sfr P5M0 = 0xCA; // 0000,0000 sfr P5M1 = 0xC9; // 0000,0000 這是STC12C5A60S2頭文件里面的定義,你的main函數所指的初始化為標準的雙向端口是要修改這個地方嗎?還是直接在主程序中重新定義修改? |
xdn 發表于 2017-12-27 19:06 main函數里面很簡單,所有端口初始化為準雙向口是因為使用可以仿真的IAP15W4K58S4單片機,其很多端口默認狀態是強推挽或高阻,需要改為準雙向口。主循環里就是調用鍵盤掃描程序和用LED顯示鍵值語句。 |
wulin 發表于 2017-12-27 17:47 沒能理解你的main函數里面的意思?能解釋一下嗎? |
異組端口組成的4*4矩陣鍵盤讀寫方法 #include <STC15F2K60S2.H> #define uint unsigned int //宏定義數據類型uint #define uchar unsigned char //宏定義數據類型uchar sbit code0=P3^0; //定義4*4鍵盤端口 sbit code1=P3^1; sbit code2=P3^2; sbit code3=P3^3; sbit code4=P3^4; sbit code5=P3^5; sbit code6=P4^2; sbit code7=P4^4; uchar key=0xff; //鍵值變量初始值 void PX(uchar i) //寫入8位數據 { code0=i&0x01;i>>=1; code1=i&0x01;i>>=1; code2=i&0x01;i>>=1; code3=i&0x01;i>>=1; code4=i&0x01;i>>=1; code5=i&0x01;i>>=1; code6=i&0x01;i>>=1; code7=i&0x01; } uchar PD() //讀取8位數據 { uchar i; i=code7; i=(i<<1)|code6; i=(i<<1)|code5; i=(i<<1)|code4; i=(i<<1)|code3; i=(i<<1)|code2; i=(i<<1)|code1; i=(i<<1)|code0; return i; } void key_scan() //矩陣鍵盤掃描函數 { uchar temp1,temp2,temp3; //臨時變量 static bit sign=0; //按鍵自鎖標志 static uint count=0; //消抖計數變量 PX(0xf0); //先給矩陣端口賦一個初值0xf0 if(PD()!=0xf0) //判斷矩陣端口不等于所賦初值,說明有健按下 { if(sign==0) //如果按鍵自鎖標志為0 { count++; //消抖計數 if(count>=1000) //消抖計數>=1000,估算主循環周期調整 { //摒棄Delay延時方式, count=1000; //防止溢出 sign=1; //按鍵自鎖標志置1,鍵不抬起,按其他鍵無效 temp1=PD(); //temp1保存矩陣端口高4位變化 PX(0x0f); //再給矩陣端口賦值0x0f temp2=PD(); //temp2保存矩陣端口低4位變化 temp3=temp2|temp1; //temp3=高4位+低4位 key=temp3; //保存鍵值 } } } else //按鍵抬起 { sign=0; //按鍵自鎖標志清0 count=0; //消抖計數清0 } } void main() { P0M0 = 0x00; //初始化端口準雙向 P0M1 = 0x00; P1M0 = 0x00; P1M1 = 0x00; P2M0 = 0x00; P2M1 = 0x00; P3M0 = 0x00; P3M1 = 0x00; P4M0 = 0x00; P4M1 = 0x00; P5M0 = 0x00; P5M1 = 0x00; P6M0 = 0x00; P6M1 = 0x00; P7M0 = 0x00; P7M1 = 0x00; while(1) { key_scan(); //鍵盤掃描 P1=key; //LED低電平亮顯示鍵值 } } |
zzzxxxccc 發表于 2017-12-27 17:36 這兩句已經單獨測試過了,LCD_PutString(0+i,1+j,TAB[num])不能顯示TAB[num]的具體值。這個問題我改怎么改呢? 還有按鍵掃描的函數不正確嗎?按下按鍵它會彈出亂碼,而且是一直循環著,按下復位鍵也沒反應,這是為什么呢? |
檢查 修改 顯示的計算 一定要 讓顯示的參數 和 函數能夠對應 比如0-f 是否是 你想要的 0-15 unsigned char code TAB[]={1,2,3,15,4,5,6,14,7,8,9,13,10,0,11,12}; LCD_PutString(0+i,1+j,TAB[num]); 這倆個好好檢查 掃描的 按鍵 先單個測試 多個的話 你的代碼暫時不能實現 |
求大神幫幫忙, |