K2 BIT P14 //+
K3 BIT P15 //-
K4 BIT P16 //CLR
K_OLD EQU 30H
K_NEW EQU 31H
K_COUNT EQU 32H
S_BUF EQU 33H
DISSTART EQU 40H ;显示单元首地址
LED_DATA EQU P0 ;数码管数据口定义
;---------------------------------------------------------
ORG 0000H
JMP MAIN
ORG 0080H
;---------------------------------------------------------
MAIN:
MOV SP,#60H
MOV P1,#0FFH
MOV P0,#0FFH
MOV K_OLD,#00H
MOV K_NEW,#00
MOV K_COUNT,#00H
MAIN1:
CALL CONVT
CALL PLAY
CALL KEY_PROG
JMP MAIN1
KEY_PROG:
CALL K_SCAN ;键扫描
MOV A,K_NEW
CJNE A,K_OLD,KEY_P1
JMP KEY_P_END
KEY_P1:
MOV K_OLD,A
CJNE A,#1, NEXT_K1
AJMP LOOP1
NEXT_K1:
CJNE A,#2, NEXT_K2
AJMP LOOP2
NEXT_K2:
CJNE A,#3, KEY_P_END
AJMP LOOP3
LOOP1:
INC K_COUNT ;键计数加1
JMP KEY_P_END
LOOP2:
DEC K_COUNT ;键计数减1
JMP KEY_P_END
LOOP3:
MOV K_COUNT,#00 ;键计数单元清零
JMP KEY_P_END
KEY_P_END:
CALL PLAY
JNB K2,KEY_P_END
JNB K3,KEY_P_END
JNB K4,KEY_P_END
RET
;---------------------------------------------------------
;代码变换 (HEX TO BCD)
;---------------------------------------------------------
CONVT:
MOV A,K_COUNT
MOV B,#100
DIV AB
MOV DISSTART+2,A ;百位存放在DISSTART+2
MOV A,#10
XCH A,B
DIV AB
MOV DISSTART+1,A ;十位存放在DISSTART+1
MOV DISSTART+0,B ;个位存放在DISSTART
RET
;---------------------------------------------------------
; 键扫描子程序
;---------------------------------------------------------
K_SCAN:
SETB K2
JB K2 ,NEXT_KEY1
AJMP KEY1_DOWN //加1
NEXT_KEY1:
SETB K3
JB K3 ,NEXT_KEY2
AJMP KEY2_DOWN //减1
NEXT_KEY2:
SETB K4
JB K4 ,END_KEY
AJMP CLEAR_KEY
CLEAR_KEY:
MOV A,#3
JMP END_KEY1
KEY1_DOWN: // 加1键按下
MOV A,#1
JMP END_KEY1
KEY2_DOWN: //
MOV A,#2
JMP END_KEY1
END_KEY1:
MOV K_NEW,A
AJMP EXIT_KET
END_KEY:
MOV K_NEW,#0
EXIT_KET:
RET
;---------------------------------------------------------
;延时子程序
;---------------------------------------------------------
DELAY:
MOV R6,#200
DEL:
MOV R7,#0FFH
DJNZ R7,$
DJNZ R6,DEL
RET
;---------------------------------------------------------
PLAY:
MOV R0,#DISSTART ;获得显示单元首地址
MOV R1,#0feH ;从第一个数码管开始
MOV R2,#04H ;共显示3位数码管
DISP1:
MOV A,@R0 ;获得当前位地址
MOV DPTR,#TAB_NU ;获得表头
MOVC A,@A+DPTR ;查表获得显示数据
//CPL A
MOV LED_DATA,A ;显示数据
MOV P2,R1 ;开始显示当前位
MOV A,R1 ;准备显示下一位
RL A
MOV R1,A ;下一位
INC R0 ;取下一个单元地址
LCALL DELAY2MS ;延时 2 MS
DJNZ R2,DISP1 ;重复显示下一个
MOV P2,#0FFH ;关闭显示
RET ;显示完成,返回
;---------------------------------------------------------
;延时子程序
;---------------------------------------------------------
DELAY2MS:
MOV R6,#10
DEL1:
MOV R7,#100
DJNZ R7,$
DJNZ R6,DEL1
RET
TAB_NU:
db 03fh,06h,05bh,04fh,066h,06dh,07dh,07h,07fh,06fh ;字形代码表
;
END
电脑上计算器的是没有快捷键的,可以通过以下方法打开:
1、在电脑底部的任务栏中找到开始菜单,并单击打开开始菜单。
2、在打开的开始菜单界面中,找到计算器功能栏,并单击进入。
3、之后即可跳转到计算机界面,使用计算机的相关功能。
这个很容易嘛,你先设置一个寄存器,然后一直扫描两个按键(假设K1按下为加,K2按下为减),假设检测到K1被按下,寄存器就加1,如果检测到K2被按下,寄存器就减1;然后再调用显示函数就OK了。、
不同的笔记本 *** 作不一样,一般是配合Fn键使用,比如我的笔记本,光标左右键上分别有绿色的音量加减图标,所以按Fn+左或右就是音量加减。也有的笔记本是单独的按钮控制音量,比如我GF的Sony
直接用按钮触发外部中断的,一个加速,一个减速。
用的光敏电阻和继电器做的光电开关。
电路我用proteus 8画和仿真的。你参考吧。
#include <reg52h>
#define uint unsigned int
void delay(uint time);
void flicker(uint led);//呼吸灯
void init();
uint t1=80;//闪烁频率
uint light=0;
sbit k1=P3^2;
sbit k2=P3^3;
sbit led1=P1^6;
sbit led2=P1^7;
void main()
{
uint led1=0xFE,led2=0xFD,led3=0xFB;
init();
while(1)
{
flicker(led1);
flicker(led2);
flicker(led3);
}
}
void init()
{
IT0=0;
IT1=0;
EX0=1;
EX1=1;
EA=1;
}
void delay(uint t)//延时程序
{
uint i,j;
for(i=t;i>0;i--)
for(j=110;j>0;j--);
}
void flicker(uint led)//呼吸灯 flag==1逐渐变亮 flag==0逐渐变暗
{
uint flag=1;
while(1)
{
P1=led;
delay(light);
P1=0xFF;
delay(t1-light);
if(flag==1)
light++;
else
light--;
if(light==t1 && flag==1)
flag=0;
else if(light==0 && flag==0)
break;
}
}
void click1()interrupt 0 //加速
{
delay(10);
if(k1==0)
{
while(k1==0);
if(t1-1>light)
t1--;
else
{
t1--;
light=t1-1;
}
}
}
void click2()interrupt 2 //减速
{
delay(10);
if(k2==0)
{
while(k2==0);
if(t1<80)
t1++;
}
}
#include<reg52>
#define uchar unsigned char
#define uint unsigned int
sbit K1 = P1^4;
sbit K2 = P1^5;
uchar data K1state;
uchar data K2state;
uint data num,ntmp;
uchar code table[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x06f,0x77,0x7c,0x39,0x5e,0x79,0x71} ;
uchar data showIndex,indexTmp;
uchar data W[8];
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);//能使之延时接近1毫秒就成 无需精确
}
void main()
{
K1state = 0xFF;
K2state = 0xFF;
num = 0;
while(1)
{
delay(1);//每毫秒轮询一回
//移位法,延时防抖
K1state = (K1state<<1);
K2state = (K2state<<1);
if(K1) K1state++;
if(K2) K2state++;
//检查开关状态
if(K1state==0x80) num++;
if(K2state==0x80) num--;
for(indexTmp=0,ntmp = num;indexTmp<=7;indexTmp++)
{
W[indexTmp] = num%10;
num /=10;
}
P0 = (0x01<<showIndex);//位选
P2 = table[W[showIndex]];//段选
showIndex++;
if(showIndex>=8)
showIndex=0;
}
}
看了你的全图,修改后了,用Keil uVision 3或4都可以,编译后可以查看对应的汇编代码
程序稍大一点的,不会有人用汇编来给你蘑菇,汇编设计写编码太慢了,开发代价不值得
以上就是关于51单片机按键加减清零汇编语言编程全部的内容,包括:51单片机按键加减清零汇编语言编程、电脑上计算器的快捷键是什么啊、怎样用单片机编程:独立按键两个键控制一个数码管的加减 一个键加 一个键减等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)