学习资料
XBYTE[0x7f01]=i; } } }
17. 用汇编语言编写出定时扫描方式下矩阵键盘的处理程序。
答:该程序放于定时器的中断服务程序中。定时器每10ms中断一次,执行一次中断服务程序。F1和F2标志位用片内RAM的50H和51H单元。 ACALL KS1 JNZ LK1 MOV 50H,#0 ;无键按下,F1的F0标志清0结束 MOV 51H,#0 SJMP OUT
LK1: CJNE 50H,#1,OUT1 ;有键按下检查F1标志是否为1,不为1置1结束。 CJNE 51H,#01,OUT ;再检查F2标志是否为1,为1说明已处理按键则结束。 LK2: MOV R2,#0FEH ;扫描查询键码 MOV R4,#00H LK4: MOV DPTR,#7F00H MOV A,R2 MOVX @DPTR,A INC DPTR INC DPTR
MOVX A,@DPTR JB ACC.0,LONE MOV A,#00H AJMP LKP LONE: JB ACC.1,LTWO MOV A,#08H AJMP LKP LTWO:JB ACC.2,LTHR MOV A,#10H AJMP LKP LTHR: JB ACC.3,NEXT MOV A,#18H LKP: ADD A,R4 ;求键码放累加大器A, MOV 51H,#1 ;F2标志置1,结束 SJMP OUT
NEXT: INC R4 MOV A,R2 JNB ACC.7,KEND RL A MOV R2,A SJMP LK4
KEND:SJMP OUT ;扫描完结束 KS1: MOV DPTR,#7F00H ;检查有无按键 MOV A,#00H MOVX @DPTR,A INC DPTR INC DPTR
仅供学习与参考
学习资料
MOVX A,@DPTR CPL A ANL A,#0FH RET OUT1:MOV 50H,#1 OUT:
18. 用C语言编写出定时扫描方式下矩阵键盘的处理程序。
答:该程序放于定时器的中断服务程序中。定时器每10ms中断一次,执行一次中断服务程序。F1和F2标志已在主函数前定义。
//************检测有无键按下函数************
uchar checkkey() //检测有无键按下函数,有返回0xff,无返回0 {uchar i;
XBYTE[0x7f00]=0x00; i=XBYTE[0x7f02]; i=i&0x0f;
if (i= =0x0f) return(0); else return(0xff); }
//************键盘扫描函数************
uchar keyscan()//键盘扫描函数,如果有键按下,则返回该键的编码,如果无键按下,则返回0xff {uchar scancode; //定义列扫描码变量 uchar codevalue; //定义返回的编码变量 uchar m; //定义行首编码变量 uchar k; //定义行检测码 uchar i,j;
if (checkkey()= =0) return(0xff); //检测有无键按下,无返回0xff else
{delay(200); //延时
if(checkkey()= =0) return(0xff); //检测有无键按下,无返回0xff else {
scancode=0xfe;m=0x00; //列扫描码,行首码赋初值 for (i=0;i<8;i++) {k=0x01;
XBYTE[0x7f00]=scancode; //送列扫描码 for (j=0;j<4;j++)
{if ((XBYTE[0x7f02]&k)= =0) //检测当前行是否有键按下 {codevalue=m+j; //按下,求编码 while(checkkey()! =0); //等待键位释放 return(codevalue); //返回编码 m=m+8; //计算下一行的行首编码 }
else k=k<<1; //行检测码左移一位 }
scancode=scancode<<1; //列扫描码左移一位,扫描下一列 }
} } }
仅供学习与参考
学习资料
19. 试编制4?4的键盘扫描程序。
答:设P0口低4位接行线,P2口低4位接列线。有键按下,R2中放键代码0~F,有无键按下,R2中放无键代码FFH。
KEYSUB: ACALL KS1 JNZ LK1 AJMP NOKEY LK1:ACALL TM6 ACALL KS1 JNZ LK2 NOKEY:MOV R2,#0FFH AJMP KEYOUT LK2:MOV R3,#0FEH MOV R4,#00H LK3:MOV A,R3 MOV P0,A MOV A,P2 JB ACC.0,LONE MOV A,#00H AJMP LKP LONE: JB ACC.1, LTWO MOV A,#04H AJMP LKP LTWO: JB ACC.2,LTHREE MOV A,#08H AJMP LKP LTHREE: JB ACC.3,KNEXT MOV A,#0CH LKP:ADD A,R4 MOV R2,A LK4:ACALL KS1 JNZ LK4 KEYOUT: RET ;KNEXT:INC R4 MOV A,R3 JNB ACC.3,NOKEY RL A MOV R3,A AJMP LK3 KS1:MOV A,#00H MOV P0,A MOV A,P2 CPL A ANL A,#0FH RET
TM12ms: MOV R7,#14H TM: MOV R6,#0FFH TM6: DJNZ R6,TM6
仅供学习与参考
;调用判断有无键按下子程序 ;有键按下时,(A)≠0转消抖延时 ;无键按下返回 ;调用10ms延时子程序 ;查有无键按下,若真有键按下 ;键(A)≠ 0逐行扫描
;不是真有键按下,R2中放无键代码FFH ;返回 ;初始行扫描字(0行)送入R3 ;初始行(0行)号送入R4 ;行扫描字送至P0口 ;从P2口读入列状态 ;查第0列无键按下,转查第1列 ;第0列有键按下, 列首键码#00H→A ;转求键码 ;查第1列无键按下,转查第2列 ;第1列有键按下, 列首键码#04H→A ;转求键码 ;查第2列无键按下,转查第3列 ;第2列有键按下, 列首键码#08H→A ;转求键码 ;查第3列无键按下,转查下一行 ;第3列有键按下, 列首键码#0CH→A ;求键码,键码=列首键码+行号 ;键码放入R2中 ;等待键释放 ;键未释放,等待
键扫描结束,出口状态R2:无键按下为FFH,有键按下为键码 ;准备扫描下一行, 行号加1 ;取行扫描字送累加器A ;判断4行扫描完否? ;扫描字左移一位,变为下一行扫描字 ;扫描字送入R3中保存 ;转下一行扫描 ;全扫描字→A ;全扫描字送往P0口 ;读入P2口行状态 ;变正逻辑,以高电平表示有键按下 ;屏蔽高4位,只保留低4位列线值
;出口状态:(A)≠0时有键按下 ;延时10 ms子程序 学习资料
DJNZ R7,TM RET
20. 根据图5.26,编制一个在两个数码管上显示1和2的显示程序。 答:图见书 程序:
MOV P1,#11100001B ;在第一个数码管显示1 MOV P1,#11010010B ;在第二个数码管显示2
21. 根据图5.27,用汇编语言或C语言编制一个在8个数码管上滚动显示1~8的程序。
答:程序如下:显示子程序DISPLAY见书,在字段码表最后放不显示的编码00H,显示缓冲区50H~57H;显示效果:在第一个数码管上显示1后,第一个数码管不显示,然后在第二个数码管上显示2,依此类推,直到在第八个上显示8。然后重复。
MOV R1,#50H MOV R4,#08H MOV A,#10H LOOP: MOV @R1,A ;初始化为全部不显示。
INC R1 DJNZ R4,LOOP START:
MOV R2,#01H MOV R4,#08H MOV R1,#50H LOOP2:
MOV A,R2 MOV @R1,A MOV R5,#0FFH LOOP1:
LCALL DISPLAY DJNZ R5,LOOP1 INC R1 INC R2
DJNZ R4,LOOP2 SJMP START END
22 根据图5.34,用汇编语言或C语言编制程序,要求按键从左边入右边出。
仅供学习与参考
学习资料 答:参考书上。
仅供学习与参考