• 一个简单的汇编报时小闹钟


    有些简陋,但是可以变色+滴答,却做了将近8天,还有1个下午6点-早上7点的小通宵。熬得头大,但是每当解决完一个问题或者发现一处自己没有想到的地方时,心情确实格外的高兴,总体的收获就是-磨刀不误砍柴工啊,很多中断只是看了提示或者例题就开做,出错的时候迷惑的一塌糊涂,也许开始就仔细的看完中断会给后来带来很大的节省。

    1.在自定义1ch中断时,要注意定义的中断尽量不要调用过于复杂的过程,甚至不调用过程,我在这上面吃亏吃了很惨。调试了整整一晚上。。。改用为倒数18次后,在主函数中通过查看标志变量来达到一秒更新钟表的效果。

    2.表盘数字,参考他人的程序,直接按照定位光标+输出字符来硬编码出我们的表盘。

    3.指针,没有用taylor展开式求正弦值,而是简单的使用正弦表,产生正弦表很简单O,比算正弦简单。

    正弦
    import sys
    import math
    file
    =open("c:\sin.txt","w")
    for i in range(0,360):
    result
    =int(math.sin(i*2*math.pi/360)*100)
    str
    = " db %s\n" %result
    file.write(str)
    file.close()

    4.我们开始根据时间算出来的角度是针对12点的,所以要回退90度,但是这样计算需要判断情况比较多才能保证角度为正值,所以我们可以直接+270,超过360再进行缩减。

    5.每秒重绘指针,关键是保存旧的三个指针角度,然后绘制新的指针,比较复杂,我倾向于直接重绘屏幕。

    6.滴答声,简单的用扬声器的中断,不停的0101就行了。

    汇编代码好长,删掉那个正弦表发上来O

    之前写的时候,可以实现按任意键退出,但是后来迷失了。。。

    clock
    pusha macro
    push ax
    push bx
    push cx
    push dx
    push si
    push di
    endm
    POPA macro
    pop di
    pop si
    pop dx
    pop cx
    pop bx
    pop ax
    endm
    clear macro
    pusha
    mov ah,6
    mov al,0
    mov ch,0
    mov cl,0
    mov dh,24
    mov dl,79
    mov bh,0
    int 10h
    popa
    endm
    data segment
    time_up db
    0
    count db
    18
    R2 dw
    13000
    flag db
    0
    window_width dw
    640
    window_height dw
    480
    color db
    10
    R dw
    120
    D dw
    180
    mid_line dw
    320 ;cx x-
    mid_row dw 246 ;dx y-
    edge_line dw 600
    edge_row dw
    400
    round_r db
    30
    round_m db
    6
    len_of_sin dw ?
    _cos dw ?
    _sin dw ?
    _thi dw ?
    check_sin dw
    0
    dw .....
    DATA ENDS
    STACK SEGMENT
    LENG DW
    120 DUP(?)
    TOP EQU $-LENG
    STACK ENDS
    CODE SEGMENT
    MAIN PROC FAR
    ASSUME
    CS:CODE,DS:DATA,ES:data,SS:STACK
    ;; INIT
    START: PUSH DS
    SUB AX,AX
    PUSH AX
    MOV AX,DATA
    MOV DS,AX
    MOV ES,AX
    MOV AH,2CH
    INT 21H
    ;;SET WINDOW_WIDTH X WINDOW_HEIGHT
    MOV AL,12H
    MOV AH,00H
    int 10h
    mov ax,window_width
    mov cx,window_height
    mov count,18
    ;; 保存原位置中断
    mov al,1ch
    mov ah,35h
    int 21h
    push es
    push bx
    ;; 设定中断号
    push ds
    mov dx,offset ring
    mov ax,seg ring
    mov ds,ax
    mov al,1ch
    mov ah,25h
    int 21h
    pop ds
    mov al,11111100b ;for keybord & timer
    out 21h,al
    draw_clock:
    call draw_all
    input:
    sti
    cmp time_up,1
    jz draw_clock
    in al,60h
    jmp input
    next_input:
    jmp input
    quit:
    cli
    mov cx,ds
    pop dx
    pop ds
    mov ds,cx
    sti
    ret
    main endp

    ring proc near
    push ds
    push ax
    push cx
    push dx
    mov ax,data
    mov ds,ax
    mov time_up,0
    dec count
    jnz exit
    mov time_up,1
    mov count,18
    exit:
    cli
    pop dx
    pop cx
    pop ax
    pop ds
    iret
    ring endp

    draw_noodle proc near
    pusha
    mov ah,2ch
    int 21h
    cmp ch,0ch ;; hour
    jle no_dec_12
    sub ch,0ch
    no_dec_12:
    mov al,ch
    mul round_r
    mov ch,cl
    shr ch,1
    add al,ch
    adc ah,0
    push ax
    ;; minute:minute*6+second/8(10)
    mov al,cl
    mul round_m
    mov bl,cl
    mov cl,3
    mov dl,dh
    shr al,cl
    add al,bl
    adc ah,0
    push ax
    ;; second:second*6
    mov al,dh
    mul round_m
    push ax
    mov bx,100
    mov cx,3
    draw_line:
    mov len_of_sin,bx
    pop ax
    add ax,270
    cmp ax,360
    jle no_add
    sub ax,360
    no_add:
    call sin
    sub bx,20
    loop draw_line
    popa
    ret
    draw_noodle endp

    draw_number PROC NEAR
    pusha
    MOV AL,10h
    MOV BX,R
    ;; 12 ; 12
    MOV DH,7 ; 11 1
    MOV DL,39 ; 10 2
    CALL draw_point ; 9 3
    MOV DL,'1' ; 8 4
    MOV AH,2 ; 7 5
    INT 21h ; 6
    MOV DH,7
    MOV DL,40
    CALL draw_point
    MOV DL,'2'
    MOV AH,2
    INT 21h
    ;; 11
    MOV DH,8
    MOV DL,30
    CALL draw_point
    MOV DL,'1'
    MOV AH,2
    INT 21h
    MOV DH,8
    MOV DL,31
    CALL draw_point
    MOV DL,'1'
    MOV AH,2
    INT 21h
    ;; 1
    MOV DH,8
    MOV DL,47
    CALL draw_point
    MOV DL,'1'
    MOV AH,2
    INT 21h
    ;; 10
    MOV DH,11
    MOV DL,25
    CALL draw_point
    MOV DL,'1'
    MOV AH,2
    INT 21h
    MOV DH,11
    MOV DL,26
    CALL draw_point
    MOV DL,'0'
    MOV AH,2
    INT 21h
    ;; 2
    MOV DH,11
    MOV DL,53
    CALL draw_point
    MOV DL,'2'
    MOV AH,2
    INT 21h
    ;; 9
    MOV DH,15
    MOV DL,24
    CALL draw_point
    MOV DL,'9'
    MOV AH,2
    INT 21h
    ;; 3
    MOV DH,15
    MOV DL,55
    CALL draw_point
    MOV DL,'3'
    MOV AH,2
    INT 21h
    ;; 8
    MOV DH,19
    MOV DL,26
    CALL draw_point
    MOV DL,'8'
    MOV AH,2
    INT 21h
    ;; 4
    MOV DH,19
    MOV DL,53
    CALL draw_point
    MOV DL,'4'
    MOV AH,2
    INT 21h
    ;; 5
    MOV DH,22
    MOV DL,47
    CALL draw_point ;
    MOV DL,'5'
    MOV AH,2
    INT 21h
    ;; 7
    MOV DH,22
    MOV DL,32
    CALL draw_point
    MOV DL,'7'
    MOV AH,2
    INT 21h
    ;; 6
    MOV DH,23
    MOV DL,40
    CALL draw_point
    MOV DL,'6'
    MOV AH,2
    INT 21h
    popa
    RET
    draw_number ENDP

    draw_point PROC NEAR
    MOV BH,0
    MOV AH,02h
    INT 10h
    RET
    draw_point ENDP

    draw_cloth proc near
    pusha
    ;; heart of the circle
    mov bh,0h
    mov cx,mid_line
    mov dx,mid_row
    mov al,color
    mov ah,0ch
    int 10h
    ;; draw the surface
    sub cx,R ;cx:line-R=x_mix
    jns out_next
    neg cx
    out_next:
    mov dx,mid_row ;dx:row-R=y_mix
    sub dx,R
    jns in_next
    neg dx
    in_next:
    call calculate_R
    mov al,flag
    cmp al,1
    jnz test_D
    mov bh,0h
    mov al,color
    mov ah,0ch
    int 10h
    test_D: inc dx
    cmp dx,edge_row
    jl in_next
    inc cx
    cmp cx,edge_line
    jl out_next
    popa
    ret
    draw_cloth endp
    ; Test.make.flag 1-------------------------------------------------
    calculate_TestR proc near
    mov si,dx
    mov di,cx
    mov cx,di
    mov dx,si
    mov flag,1
    ret
    calculate_TestR endp
    ;
    ;
    Judge is the R distance--------------
    calculate_R proc near
    pusha
    mov si,cx
    mov di,dx
    mov flag,0
    ;; cx:bx=(x1-x2)*(x1-x2)
    mov ax,cx
    sub ax,mid_line
    imul ax
    ; jc fail_equal
    mov cx,dx
    mov bx,ax
    ;; (y1-y2)2
    mov ax,mid_row
    sub ax,di
    imul ax
    ; jc fail_equal
    ;;dx:ax=(x1-x2)*(x1-x2)+(y1-y2)*(y1-y2)
    add ax,bx
    adc dx,cx
    cmp dx,0
    jnz fail_equal
    mov bx,R2
    sub bx,120
    mov cx,R2
    add cx,120
    cmp ax,bx
    jb fail_equal
    cmp ax,cx
    ja fail_equal
    mov flag,1
    fail_equal:
    mov dx,di
    mov cx,si
    popa
    ret
    calculate_R endp

    sin proc near
    pusha
    ;; ax-角度,di-半径,bx-sin扩张倍数
    mov _thi,ax
    mov di,len_of_sin
    mov bx,100
    ;; ax=cos(x)
    mov si,90
    sub si,ax
    cmp si,0
    jge no_add_360
    add si,360
    no_add_360:
    shl si,1
    mov ax,check_sin[si]
    mov _cos,ax
    mov si,_thi
    shl si,1
    mov ax,check_sin[si] ;sin(x)
    mov _sin,ax
    draw_one:
    mov ax,_cos
    imul di
    idiv bx
    add ax,mid_line
    mov cx,ax
    mov ax,_sin
    imul di
    idiv bx
    add ax,mid_row
    mov dx,ax
    mov bh,0
    mov al,color
    mov ah,0ch
    int 10h
    mov bx,100
    dec di
    jnz draw_one
    popa
    ret
    sin endp

    draw_all proc near
    cli
    clear
    mov ah,2ch
    int 21h
    and dh,0fh
    mov color,dh
    call draw_number
    call draw_cloth
    call draw_noodle
    mov bx,2000
    mov cx,400
    call sound
    ret
    draw_all endp

    ;; SOUND-sound in frequency bx,delay cx
    sound proc near
    pusha
    mov dx,cx
    in al,61h ;port 61 mask-1 connect to producter
    and al,11111100b ;turn off 0、1
    trig:
    xor al,2 ;00000010 1->0 0->
    out 61h,al
    mov cx,bx
    delay:
    loop delay
    ;wait for cx time
    dec dx
    jne trig
    popa
    ret
    sound endp

    code ends
    end start

  • 相关阅读:
    字符串匹配之BF算法
    python里的反射(自学习)
    python的super()以及父类继承
    @staticmethod
    @classmethod
    scrapy
    mongodb
    js注入提取伪元素选择器
    execjs
    base64解密
  • 原文地址:https://www.cnblogs.com/amaoxiaozhu/p/1933030.html
Copyright © 2020-2023  润新知