汇编(三)-窗口切换与字符输入

问题描述及要求

在屏幕上开出三个窗口

<-->键选择左窗口或右窗口为当前活动窗口,从键盘输入字符, 字符就会从当前活动窗口的最下行开始显示,同时也在下窗口显示。当一行字符显示满后(左右窗口一行显示20个字符,下窗口显示50个字符),窗口自动向上卷动一行,输入的字符仍显示于最低一行,窗口最高一行向上卷动后消失,ESC键程序运行结束

二 设计思想论述

程序启动时初始化三个窗口,窗口的属性用一个变量property保存起来,方便改变窗口的属性。属性为一个字节的变量,变量每位的意义如下:

  7

  6

   5

  4


  2

  1

  0

 

  闪烁(7)        背景(**)              亮度(3)     前景(2-0)

 0=正常显示                           0=正常显示

 1=闪烁显示                           1=加强亮度

 

初始化窗口后接受用户的输入,根据用户输入的字符执行相应的操作,用户输入ESC时退出程序,输入<-切换到左窗口,输入->切换到右窗口,输入Backspace在活动窗口和底部窗口删除一个字符,输入Enter在活动窗口和底部窗口中换行,输入一个字符时在活动窗口和底部窗口显示,显示满一行时自动向上卷动一行。

 

三  程序清单

Code:
  1. ;--------------------------------------------------------  
  2. ;在屏幕上开出三个窗口  
  3. ;--------------------------------------------------------  
  4. ;********************************************************  
  5. data segment  
  6.     property    db    01100101B ;字符的属性  
  7.     lminrow     db    5    ;左窗口最小行号  
  8.     lmaxrow     db    14   ;左窗口最大行号  
  9.     lmincol     db    10   ;左窗口最小列号  
  10.     lmaxcol     db    29   ;左窗口最大列号  
  11.     rminrow     db    5  
  12.     rmaxrow     db    14  
  13.     rmincol     db    50  
  14.     rmaxcol     db    69  
  15.     bminrow     db    18   ;底部窗口最小行号  
  16.     bmaxrow     db    21  
  17.     bmincol     db    15  
  18.     bmaxcol     db    64  
  19.     lrow        db    14   ;左窗口阻塞时行坐标  
  20.     lcol        db    10   ;左窗口阻塞时列坐标  
  21.     rrow        db    14   ;右窗口阻塞时行坐标  
  22.     rcol        db    50   ;右窗口阻塞时列坐标  
  23.     activewin   db    1    ;当前活动窗口(1=左窗口,2=右窗口)  
  24.   
  25. data ends  
  26. ;********************************************************  
  27. code segment  
  28. ;--------------------------------------------------------  
  29. ;主程序  
  30. main   proc   far  
  31.         assume cs:code,ds:data  
  32. start:  
  33.     push ds  
  34.     xor ax,ax  
  35.     push ax  
  36.   
  37.     mov ax,data  
  38.     mov ds,ax  
  39.   
  40.     mov ax,0B800h  
  41.     mov es,ax  
  42.   
  43.     call init  
  44.     call input  
  45.     call cls  
  46. mainret:     
  47.     ret  
  48. main   endp  
  49. ;--------------------------------------------------------  
  50. ;程序初始化  
  51. init    proc   near  
  52.     push ax  
  53.     push bx  
  54.     push cx  
  55.     push dx  
  56.   
  57.     mov bh,property  
  58.     mov al,0  
  59.   
  60.     ;初始化左窗口  
  61.     mov ch,lminrow  
  62.     mov cl,lmincol  
  63.     mov dh,lmaxrow  
  64.     mov dl,lmaxcol  
  65.     mov bh,property  
  66.     mov ah,6  
  67.     int 10h  
  68.       
  69.     ;初始化右窗口  
  70.     mov ch,rminrow  
  71.     mov cl,rmincol  
  72.     mov dh,rmaxrow  
  73.     mov dl,rmaxcol  
  74.     mov ah,6  
  75.     int 10h  
  76.   
  77.     ;初始化底部窗口  
  78.     mov ch,bminrow  
  79.     mov cl,bmincol  
  80.     mov dh,bmaxrow  
  81.     mov dl,bmaxcol  
  82.     mov ah,6  
  83.     int 10h  
  84.   
  85.     ;将光标置于左窗口底部开始处  
  86.     mov bh,0  
  87.     mov dh,lmaxrow  
  88.     mov dl,lmincol  
  89.     mov ah,2  
  90.     int 10h  
  91.   
  92. initret:  
  93.     pop dx  
  94.     pop cx  
  95.     pop bx  
  96.     pop ax  
  97.     ret  
  98. init   endp  
  99. ;--------------------------------------------------------  
  100. ;循环输入字符,在活动窗口和底部窗口显示  
  101. input   proc   near  
  102.     push ax  
  103.     push bx  
  104.     push cx  
  105.     push dx  
  106.     push di  
  107.   
  108.     ;将di设置到底部窗口最下行开始  
  109.     mov ax,0  
  110.     mov bx,0  
  111.     mov al,bmaxrow  
  112.     mov bl,80  
  113.     mul bl  
  114.     mov bl,bmincol  
  115.     add ax,bx  
  116.     shl ax,1  
  117.     mov di,ax  
  118.       
  119.     ;循环输入  
  120.     mov ax,0  
  121.     mov bx,0  
  122.     mov cx,0  
  123. inputlop1:  
  124.     mov ah,0  
  125.     int 16h  
  126.       
  127.     ;判断是否是ESC  
  128.     cmp ah,01  
  129.     je inputret ;是ESC则退出  
  130.       
  131.     ;判断是否是<-  
  132.     cmp ah,4bh  
  133.     je toleftwin  
  134.   
  135.     ;判断是否是->  
  136.     cmp ah,4dh  
  137.     je torightwin  
  138.   
  139.     ;判断是否是Backspace  
  140.     cmp ah,0eh  
  141.     je backspace  
  142.   
  143.     ;判断是否是  
  144.     cmp ah,1ch  
  145.     je enter  
  146.   
  147.     ;输出字符  
  148.     mov bh,0  
  149.     mov bl,property  
  150.     mov ah,0eh  
  151.     int 10h  
  152.     mov byte ptr es:[di],al  
  153.     inc cx  
  154.     add di,2  
  155.     call actscroll  
  156.     call botscroll  
  157.     jmp inputlop1  
  158.   
  159. toleftwin:  
  160.     mov bl,activewin  
  161.     cmp bl,1  
  162.     je inputlop1 ;当前活动窗口已是左窗口  
  163.     mov dh,lrow  
  164.     mov dl,lcol  
  165.     call switchwin  
  166.     jmp inputlop1  
  167.   
  168. torightwin:  
  169.     mov bl,activewin  
  170.     cmp bl,2  
  171.     je inputlop1 ;当前活动窗口已是右窗口  
  172.     mov dh,rrow  
  173.     mov dl,rcol  
  174.     call switchwin  
  175.     jmp inputlop1  
  176.   
  177. backspace:  
  178.     call deletech  
  179.     jmp inputlop1  
  180.   
  181. enter:  
  182.     call crlf  
  183.     jmp inputlop1  
  184.   
  185. inputret:  
  186.     pop di  
  187.     pop dx  
  188.     pop cx  
  189.     pop bx  
  190.     pop ax  
  191.     ret  
  192. input   endp  
  193. ;--------------------------------------------------------  
  194. ;转换窗口  
  195. ;参数:  
  196. ;*   dh/dl=新窗口的行/列  
  197. switchwin    proc   near  
  198.     push ax  
  199.     push bx  
  200.     push cx  
  201.     ;保存当前活动窗口光标的坐标  
  202.     push dx  
  203.     mov ah,3  
  204.     mov bh,0  
  205.     int 10h  
  206.     mov cl,activewin  
  207.     cmp cl,1  
  208.     je lactive  
  209.     jmp ractive   
  210.   
  211. lactive:  
  212.     mov lrow,dh  
  213.     mov lcol,dl  
  214.     mov activewin,2 ;新窗口为右窗口  
  215.     jmp switch  
  216. ractive:  
  217.     mov rrow,dh  
  218.     mov rcol,dl  
  219.     mov activewin,1 ;新窗口为左窗口  
  220.     ;切换窗口  
  221. switch:  
  222.     ;置光标  
  223.     pop dx  
  224.     mov ah,2  
  225.     mov bh,0  
  226.     int 10h  
  227.       
  228. switchwinret:  
  229.     pop cx  
  230.     pop bx  
  231.     pop ax  
  232.     ret  
  233. switchwin    endp  
  234. ;--------------------------------------------------------  
  235. ;判断活动窗口是否需要向上滚屏,如果需要则滚屏  
  236. actscroll  proc  near  
  237.     push ax  
  238.     push bx  
  239.     push cx  
  240.     push dx  
  241.   
  242.     ;获取当前光标位置  
  243.     mov ah,3  
  244.     mov bh,0  
  245.     int 10h  
  246.   
  247.     mov bl,activewin  
  248.     cmp bl,1  
  249.     je islactive  
  250.     jmp isractive  
  251.   
  252. islactive:  ;当前活动窗口为左窗口  
  253.     cmp dl,lmaxcol  
  254.     ja lscroll  
  255.     jmp actscrollret  
  256.   
  257. isractive:  ;当前活动窗口为右窗口  
  258.     cmp dl,rmaxcol  
  259.     jbe actscrollret  
  260.   
  261. rscroll:  ;右窗口上卷  
  262.     mov al,1  
  263.     mov bh,property  
  264.     mov ch,rminrow  
  265.     mov cl,rmincol  
  266.     mov dh,rmaxrow  
  267.     mov dl,rmaxcol  
  268.     mov ah,6  
  269.     int 10h  
  270.   
  271.     ;置光标  
  272.     mov bh,0  
  273.     mov dh,rmaxrow  
  274.     mov dl,rmincol  
  275.     mov ah,2  
  276.     int 10h  
  277.     jmp actscrollret  
  278.   
  279. lscroll: ;左窗口上卷  
  280.     mov al,1  
  281.     mov bh,property  
  282.     mov ch,lminrow  
  283.     mov cl,lmincol  
  284.     mov dh,lmaxrow  
  285.     mov dl,lmaxcol  
  286.     mov ah,6  
  287.     int 10h  
  288.   
  289.     ;置光标  
  290.     mov bh,0  
  291.     mov dh,lmaxrow  
  292.     mov dl,lmincol  
  293.     mov ah,2  
  294.     int 10h  
  295.   
  296. actscrollret:  
  297.     pop dx  
  298.     pop cx  
  299.     pop bx  
  300.     pop ax  
  301.     ret  
  302. actscroll endp  
  303. ;--------------------------------------------------------  
  304. ;判断底部窗口是否需要滚动,如需要则滚动底部窗口  
  305. ;参数:  
  306. ;*  cx=最后一行的字符数  
  307. ;*  di=指向下一字符的指针  
  308. botscroll   proc  near  
  309.     push ax  
  310.     push bx  
  311.     push dx  
  312.   
  313.     mov ax,0  
  314.     mov bx,0  
  315.     ;计算底部窗口每行能容纳的字符数  
  316.     mov al,bmaxcol  
  317.     mov bl,bmincol  
  318.     sub al,bl  
  319.     inc al  
  320.   
  321.     cmp cx,ax  
  322.     jb botscrollret  
  323. bscroll: ;底部窗口滚动  
  324.     mov al,1  
  325.     mov bh,property  
  326.     mov ch,bminrow  
  327.     mov cl,bmincol  
  328.     mov dh,bmaxrow  
  329.     mov dl,bmaxcol  
  330.     mov ah,6  
  331.     int 10h  
  332.       
  333.     mov cx,0 ;cx清零  
  334.   
  335.     ;将di设置到底部窗口最下行开始  
  336.     mov ax,0  
  337.     mov bx,0  
  338.     mov al,bmaxrow  
  339.     mov bl,80  
  340.     mul bl  
  341.     mov bl,bmincol  
  342.     add ax,bx  
  343.     shl ax,1  
  344.     mov di,ax  
  345.   
  346. botscrollret:  
  347.     pop dx  
  348.     pop bx  
  349.     pop ax  
  350.     ret  
  351. botscroll   endp  
  352. ;--------------------------------------------------------  
  353. ;删除一个字符  
  354. deletech   proc  near  
  355.     push ax  
  356.     push bx  
  357.     push dx  
  358.     push cx  
  359.   
  360.     ;取得光标位置  
  361.     mov ah,3  
  362.     mov bh,0  
  363.     int 10h  
  364.   
  365.     ;判断活动窗口  
  366.     mov al,activewin  
  367.     cmp al,1  
  368.     je  isleft  
  369.   
  370. isright:  
  371.     cmp dl,rmincol  
  372.     jne delch  
  373.   
  374. delr: ;屏幕下卷,并删除一个字符  
  375.     mov al,1  
  376.     mov bh,property  
  377.     mov ch,rminrow  
  378.     mov cl,rmincol  
  379.     mov dh,rmaxrow  
  380.     mov dl,rmaxcol  
  381.     mov ah,7  
  382.     int 10h  
  383.   
  384.     ;置光标  
  385.     mov bh,0  
  386.     mov ah,2  
  387.     int 10h  
  388.       
  389.     ;删除字符  
  390.     mov al,0  
  391.     mov cx,1  
  392.     mov ah,0ah  
  393.     int 10h  
  394.     jmp delb  
  395.   
  396. isleft:  
  397.     cmp dl,lmincol  
  398.     jne delch  
  399.   
  400. dell:  
  401.     mov al,1  
  402.     mov bh,property  
  403.     mov ch,lminrow  
  404.     mov cl,lmincol  
  405.     mov dh,lmaxrow  
  406.     mov dl,lmaxcol  
  407.     mov ah,7  
  408.     int 10h  
  409.   
  410.     ;置光标  
  411.     mov bh,0  
  412.     mov ah,2  
  413.     int 10h  
  414.       
  415.     ;删除字符  
  416.     mov al,0  
  417.     mov cx,1  
  418.     mov ah,0ah  
  419.     int 10h  
  420.     jmp delb  
  421.   
  422. delch:  
  423.     dec dl  
  424.     mov ah,2  
  425.     int 10h  
  426.   
  427.     mov bh,0  
  428.     mov al,0  
  429.     mov cx,1  
  430.     mov ah,0ah  
  431.     int 10h  
  432.   
  433. delb:  
  434.     pop cx  
  435.     cmp cx,0  
  436.     je delbch  
  437.   
  438.     sub di,2  
  439.     mov byte ptr es:[di],0  
  440.     dec cx  
  441.     jmp deletechret  
  442.   
  443. delbch:  
  444.     ;窗口下移  
  445.     mov al,1  
  446.     mov bh,property  
  447.     mov ch,bminrow  
  448.     mov cl,bmincol  
  449.     mov dh,bmaxrow  
  450.     mov dl,bmaxcol  
  451.     mov ah,7  
  452.     int 10h  
  453.   
  454.     ;改变di和cx  
  455.     mov ax,0  
  456.     mov al,bmaxcol  
  457.     sub al,bmincol  
  458.     mov cx,ax  
  459.   
  460.     shl ax,1  
  461.     add di,ax  
  462.   
  463.     ;删除字符  
  464.     mov byte ptr es:[di],0  
  465.   
  466. deletechret:  
  467.     pop dx  
  468.     pop bx  
  469.     pop ax  
  470.     ret  
  471. deletech  endp  
  472. ;--------------------------------------------------------  
  473. ;当前活动窗口和底部窗口回车换行  
  474. crlf   proc  near  
  475.     push ax  
  476.     push bx  
  477.     push dx  
  478.     push cx  
  479.   
  480.     ;底部窗口回车换行  
  481.     ;向上卷动  
  482.     mov al,1  
  483.     mov bh,property  
  484.     mov ch,bminrow  
  485.     mov cl,bmincol  
  486.     mov dh,bmaxrow  
  487.     mov dl,bmaxcol  
  488.     mov ah,6  
  489.     int 10h  
  490.       
  491.     pop cx  
  492.     ;重置di和cx  
  493.     shl cx,1  
  494.     sub di,cx  
  495.   
  496.     ;活动窗口回车换行  
  497.     mov bl,activewin  
  498.     cmp bl,1  
  499.     jne rightact  
  500. leftact:  
  501.     ;卷动窗口  
  502.     mov al,1  
  503.     mov bh,property  
  504.     mov ch,lminrow  
  505.     mov cl,lmincol  
  506.     mov dh,lmaxrow  
  507.     mov dl,lmaxcol  
  508.     mov ah,6  
  509.     int 10h  
  510.   
  511.     ;重置光标  
  512.     mov dl,lmincol  
  513.     mov bh,0  
  514.     mov ah,2  
  515.     int 10h  
  516.     jmp crlfret  
  517.   
  518. rightact:  
  519.     ;卷动窗口  
  520.     mov al,1  
  521.     mov bh,property  
  522.     mov ch,rminrow  
  523.     mov cl,rmincol  
  524.     mov dh,rmaxrow  
  525.     mov dl,rmaxcol  
  526.     mov ah,6  
  527.     int 10h  
  528.   
  529.     ;重置光标  
  530.     mov dl,rmincol  
  531.     mov bh,0  
  532.     mov ah,2  
  533.     int 10h  
  534.   
  535. crlfret:  
  536.     mov cx,0  
  537.     pop dx  
  538.     pop bx  
  539.     pop ax  
  540.     ret  
  541. crlf   endp  
  542. ;--------------------------------------------------------  
  543. ;清屏  
  544. cls  proc near  
  545.     push ax  
  546.     push bx  
  547.     push cx  
  548.     push dx  
  549.   
  550.     mov al,0  
  551.     mov bh,0  
  552.     mov ch,0  
  553.     mov cl,0  
  554.     mov dh,24  
  555.     mov dl,79  
  556.     mov ah,6  
  557.     int 10h  
  558. clsret:  
  559.     pop dx  
  560.     pop cx  
  561.     pop bx  
  562.     pop ax  
  563.     ret  
  564. cls  endp  
  565. ;--------------------------------------------------------  
  566. code ends  
  567. ;********************************************************  
  568.      end start  

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值