精华区代码Revision-C版本[系列六]
程序代码:
五子棋游戏原作者链接: http://bbs.bccn.net/viewthread.php?tid=146783&extra=page%3D1%26amp%3Bfilter%3Ddigest ;Revision Declare Modified by zaixuexi ;*/ -------------------------------------------------------------------------------------- ;*/ source:http://www. ;*/ author:zaixuexi ;*/ date: 2011-11-30 ;*/ email: asmedu@ ;*/ revision declare: ;*/ 1.add self-estimated c source code. ;*/ 2.adjust all asm source code lower-case style. ;*/ 3.keep all original code designment. ;*/ 4.using tab alignment source code text. ;*/ -------------------------------------------------------------------------------------- ;typedef unsigned char uint8_t; ;typedef unsigned short uint16_t; ;typedef uint8_t bool; ;typedef uint8_t color_t; ;#define false (0) ;#define true (!false) ;#define SCAN_KEY_ESC (0x01) ;#define SCAN_KEY_UP (0x48) ;#define SCAN_KEY_DOWN (0x50) ;#define SCAN_KEY_LEFT (0x4b) ;#define SCAN_KEY_RIGHT (0x4d) ;#define SCAN_KEY_ENTER (0x1c) ;#define SCAN_KEY_SPACE (0X39) ;struct point { ; uint8_t x; ; uint8_t y; ;}; ;struct ch_object { ; uint8_t ch; ; uint8_t attr; ;}; .model small ;---------------------------------------------------------------------- ;数据段 .data ; x db 0 y db 0 ;struct point g_xy = {0, 0}; ; win_time equ 5 ;#define win_time (5) chess_state dw ? ;uint16_t chess_state; chess_x db ? chess_y db ? ;struct point chess_xy; help_x db ? help_y db ? ;struct point help_xy; nothing1 db ? nothing2 db ? nothing3 db ? ;uint8_t nothing[3]; chess_t db ? ;uint8_t chess_t; person1 db ? person2 db ? ;uint8_t person_t[2]; person db ? ;uint8_t person; person_first db ? ;uint8_t person_first; jud db ? ;bool jud; ; person1_x equ 6 ;#define person1_x (6) person1_y equ 3 ;#define person1_y (3) person1_x1 equ 0 ;#define person1_x1 (0) person1_y1 equ 0 ;#define person1_y1 (0) person1_x2 equ 49 ;#define person1_x2 (49) person1_y2 equ 14 ;#define person1_y2 (14) ; person2_x equ 6 ;#define person2_x (6) person2_y equ 68 ;#define person2_y (68) person2_x1 equ 0 ;#define person2_x1 (0) person2_y1 equ 64 ;#define person2_y1 (64) person2_x2 equ 49 ;#define person2_x2 (49) person2_y2 equ 79 ;#define person2_y2 (79) ; map_x equ 6 ;#define map_x (6) map_y equ 20 ;#define map_y (20) map_x_end equ 44 ;#define map_x_end (44) map_y_end equ 58 ;#define map_y_end (58) map_x1 equ 6 ;#define map_x1 (6) map_y1 equ 15 ;#define map_y1 (15) map_x2 equ 44 ;#define map_x2 (44) map_y2 equ 63 ;#define map_y2 (63) ; answer_x equ 2 ;#define answer_x (2) answer_y equ 28 ;#define answer_y (28) answer_x1 equ 0 ;#define answer_x1 (0) answer_y1 equ 15 ;#define answer_y1 (15) answer_x2 equ 5 ;#define answer_x2 (5) answer_y2 equ 63 ;#define answer_y2 (63) ; end_x equ 47 ;#define end_x (47) end_y equ 26 ;#define end_y (26) end_x1 equ 45 ;#define end_x1 (45) end_y1 equ 15 ;#define end_y1 (15) end_x2 equ 49 ;#define end_x2 (49) end_y2 equ 63 ;#define end_y2 (63) ; map_size equ 19 ;#define map_size (19) map_over db ? ;uint8_t map_over; map db 400 dup(0) ;uint8_t map[400]; ; string_doing db ' Want To Peace ! ','$' ;const char * string_doing = " Want To Peace ! "; string_person1 db ' P 1 : ','$' ;const char * string_person1 = " P 1 : "; string_person2 db ' P 2 : ','$' ;const char * string_person2 = " P 2 : "; string_p1 db ' Person 1 first . ','$' ;const char * string_p1 = " Person 1 first . "; string_p2 db ' Person 2 first . ','$' ;const char * string_p2 = " Person 2 first . "; string_win1 db ' Person 1 win. ','$' ;const char * string_win1 = " Person 1 win. "; string_win2 db ' Person 2 win. ','$' ;const char * string_win2 = " Person 2 win. "; string_peace db ' PEACE !!! ','$' ;const char * string_peace = " PEACE !!! "; string_wrong db ' You can`t put here.','$' ;const char * string_wrong = " You can`t put here."; string_end db ' I Want To End The Game ! ','$' ;const char * string_end = " I Want To End The Game ! "; string_lose1 db ' P1 want to lose? ','$' ;const char * string_lose1 = " P1 want to lose? "; string_lose2 db ' P2 want to lose? ','$' ;const char * string_lose2 = " P2 want to lose? "; string_final1 db ' P1 win the final ! ','$' ;const char * string_final1 = " P1 win the final ! "; string_final2 db ' P2 win the final ! ','$' ;const char * string_final2 = " P2 win the final ! "; string_thank db ' Thank You Very Much !','$' ;const char * string_thank = " Thank You Very Much !"; ; heart db 0,1,1,0,0,0,1,1,0 db 1,0,0,1,0,1,0,0,1 db 1,0,0,0,1,0,0,0,1 db 0,1,0,0,0,0,0,1,0 db 0,0,1,0,0,0,1,0,0 db 0,0,0,1,0,1,0,0,0 db 0,0,0,0,1,0,0,0,0 heart_size1 db 7 heart_size2 db 9 ;uint8_t heart[7][9] = {...}; ; ;---------------------------------------------------------------------- ;清屏程序,gao_color为颜色,x1,y1,x2,y2为坐标 gao_clear_screen macro gao_color,x1,y1,x2,y2 ;static inline gao_clear_screen(color_t gao_color, struct point xy1, struct point xy2); push ax push bx push cx push dx ; mov ah,6 ;bios syscall vector nr; mov al,0 mov bh,gao_color mov ch,x1 mov cl,y1 mov dh,x2 mov dl,y2 int 10h ;textbackground(gao_color); ; pop dx pop cx pop bx pop ax endm ;---------------------------------------------------------------------- ;画出当前状态 ;辅助函数 1 , 判断x,y坐标在那个区域 gao_judge macro jud,x,y,x1,y1,x2,y2 ;static inline gao_judge(bool jud, struct point xy, struct point xy1, struct point xy2); local gao_judge_exit ; mov jud,0 ;jud = false; cmp x,x1 jl gao_judge_exit cmp x,x2 jg gao_judge_exit ;if ((xy.x < xy1.x) || (xy.x > xy2.x)) goto gao_judge_exit; cmp y,y1 jl gao_judge_exit cmp y,y2 jg gao_judge_exit ;if ((xy.y < xy1.y) || (xy.y > xy2.y)) goto gao_judge_exit; ; mov jud,1 ;jud = true; ; gao_judge_exit: ; endm ;辅助函数 2 , 输出相应语句的位置 gao_print_string macro string,x,y,gao_color ;static inline gao_print_string(const char *string, struct point xy, color_t gao_color); push ax push bx push cx push dx ; mov dh,x mov dl,y ;struct point _xy = xy; mov bx,offset string ;uint16_t *p = string; mov al,[bx] ;uint8_t ch = *p; .while al!='$' ;while (ch != '\0') ; push bx ; mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov bl,gao_color mov bh,0 mov cx,1 mov ah,9 int 10h ;putchar_attr(ch, gao_color); /*Pseudo-code*/ ; pop bx inc bx ;p++; inc dl ;_xy.y++; mov al,[bx] ;ch = *p; .endw ; pop dx pop cx pop bx pop ax endm ;辅助函数 3 - 1 , 打印当前棋盘一奇数行 gao_print_map_line1 macro x,y,gao_color ;static inline gao_print_map_line1(struct point xy, color_t gao_color); local gao_print_map_line1_repeat push ax push bx push cx push dx ; mov dh,x mov dl,y ;struct point _xy = xy; mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov bh,0 mov ah,9 mov al,2bh mov bl,gao_color mov cx,1 int 10h ;putchar_attr('+', gao_color); /*Pseudo-code*/ inc dl ;_xy.y++; mov cl,map_size mov ch,0 ;uint8_t count = map_size; ; gao_print_map_line1_repeat: push cx mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov al,2dh mov bh,0 mov ah,9 mov cx,1 mov bl,gao_color int 10h ;putchar_attr('+', gao_color); /*Pseudo-code*/ inc dl ;_xy.y++; ; mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov al,2bh mov bh,0 mov ah,9 mov bl,gao_color int 10h ;putchar_attr('+', gao_color); /*Pseudo-code*/ inc dl ;_xy.y++; pop cx ; loop gao_print_map_line1_repeat ;while(count--); ; pop dx pop cx pop bx pop ax endm ;辅助函数 3 - 2 , 打印当前棋盘一偶数行 gao_print_map_line2 macro p,x,y,gao_color ;static gao_print_map_line2(uint16_t p, struct xy, color_t gao_color); local gao_print_map_line2_repeat ; push ax push bx push cx push dx push ax ;uint16_t p; ; mov dh,x mov dl,y ;struct point _xy = xy; mov ah,2 mov bh,0 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov ah,9 mov al,7ch mov bh,0h mov bl,gao_color mov cx,1 int 10h ;putchar_attr('|', gao_color); /*Pseudo-code*/ ; pop ax mov ah,0 ;p &= 0x0ff; mov bx,map_size push dx mul bx ;uint32_t q = p * map_size; pop dx mov cx,map_size ;uint16_t size = map_size; ; gao_print_map_line2_repeat: push cx inc dl ;_xy.y++; mov bx,offset map ;uint8_t *p_map = map; add bx,ax ;p_map += LOWORD(q); ; push ax push bx mov ah,2 mov bh,0 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; pop bx mov bl,[bx] .if bl==0 ;switch ((uint8_t)*p_map) { mov al,20h ;case 0: p = (p & 0xff00) | 0x20; break; .elseif bl==1 mov al,1h ;case 1: p = (p & 0xff00) | 0x01; break; .else mov al,2h ;default: p = (p & 0xff00) | 0x02; .endif ;} ; mov ah,9 mov bh,0 mov bl,gao_color mov cx,1 int 10h ;putchar_attr(LOBYTE(p), gao_color); /*Pseudo-code*/ ; inc dl ;_xy.y++; mov ah,2 mov bh,0 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov ah,9 mov al,7ch mov bh,0 mov bl,gao_color mov cx,1 int 10h ;putchar_attr('|', gao_color); /*Pseudo-code*/ ; pop ax ;uint16_t j = LOWORD(q); inc ax ;j++; pop cx loop gao_print_map_line2_repeat ;while (--size); ; pop dx pop cx pop bx pop ax endm ;辅助函数 3 , 打印当前棋盘状态 gao_print_map macro gao_color,x,y ;static inline gao_print_map(color_t gao_color, struct point xy); push ax push bx push cx push dx ; gao_print_map_line1 x,y,gao_color ;gao_print_map_line1(xy, gao_color); mov al,0h ;uint8_t i = 0; ;struct point _xy; ;_xy.y = xy.y; .while al!=map_size ;while(i != map_size) { mov bl,al ;_xy.x = i; add bl,al ;_xy.x += i; add bl,x ;_xy.x += xy.x; add bl,1 ;_xy.y++; gao_print_map_line2 al,bl,y,gao_color;gao_print_map_line2(i, _xy, gao_color) add bl,1 ;_xy.x++; gao_print_map_line1 bl,y,gao_color ;gao_print_map_line(_xy, gao_color); inc al ;i++; .endw ;} ; pop dx pop cx pop bx pop ax endm ;辅助函数 4 - 1 , 将现在字符改变底色 gao_print_map_point_change macro x,y,gao_color ;static inline gao_print_map_point_change(struct point xy, color_t gao_color); push ax push bx push cx push dx ; mov dh,x mov dl,y ;struct point _xy = xy; ; mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov bh,0 mov ah,8h ;struct ch_object cho; int 10h ;getchar_attr(&cho); /*Pseudo-code*/ ; mov bh,0 mov bl,gao_color mov ah,9 mov cx,1 int 10h ;putchar_attr(cho.ch, gao_color); /*Pseudo-code*/ ; pop dx pop cx pop bx pop ax endm ;辅助函数 4 , 如果当前操作的是棋盘 , 将棋盘相应位置的颜色变化为 0e7H 方式 gao_print_map_point macro x,y,gao_color ;static inline gao_print_map_point(struct point xy, color_t gao_color); push ax push bx push cx push dx ; mov dh,x mov dl,y ;struct point _xy; ; dec dh dec dl ;_xy.x--; _xy.y--; gao_print_map_point_change dh,dl,gao_color ;gao_print_map_point_change(_xy, gao_color); ; inc dl ;_xy.y++; gao_print_map_point_change dh,dl,gao_color ;gao_print_map_point_change(_xy, gao_color); ; inc dl ;_xy.y++; gao_print_map_point_change dh,dl,gao_color ;gao_print_map_point_change(_xy, gao_color); ; inc dh ;_xy.x++; mov dl,y dec dl ;_xy.y = xy.y + 1; gao_print_map_point_change dh,dl,gao_color ;ignore same c source code ; inc dl gao_print_map_point_change dh,dl,gao_color ; inc dl gao_print_map_point_change dh,dl,gao_color ; inc dh mov dl,y dec dl gao_print_map_point_change dh,dl,gao_color ; inc dl gao_print_map_point_change dh,dl,gao_color ; inc dl gao_print_map_point_change dh,dl,gao_color ; pop dx pop cx pop bx pop ax endm ;打印当前比分 gao_printf_num macro x,y,gao_color,num ;static inline gao_printf_num(struct point xy, color_t gao_color, uint8_t num); push ax push bx push cx push dx ; mov dh,x mov dl,y ;struct point _xy = xy; add dl,7 ;_xy.y += 7; mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ mov al,num ;uint8_t ch = num; ; add al,30h ;ch += 0x30; mov ah,9h mov bl,gao_color mov cx,1 int 10h ;putchar_attr(ch, gao_color); /*Pseudo-code*/ ; pop dx pop cx pop bx pop ax endm ;辅助函数都不知道多少号了 gao_print_heart macro x,y,gao_color,num,word ;static inline gao_print_heart(struct point xy, color_t gao_color, uint8_t num, uint8_t word); push ax push bx push cx push dx ; mov dh,x mov dl,y ;struct point _xy = xy; inc dh inc dh ;_xy.x += 2; mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ ; mov bl,num ;uint8_t num = num; mov ch,0 ;uint8_t i=0 mov cl,0 ;uint8_t j=0; ; .while bl>0 ;while (num > 0) { dec bl ;num--; push bx ;uint16 pos; ;uint8_t h_ch; .while ch<heart_size1 ;while (i < heart_size1) { .while cl<heart_size2 ; while(j < heart_size2) { push ax push cx mov bh,0 mov ah,2 int 10h ;setcursor(_xy); /*Pseudo-code*/ mov al,ch mov ah,0 mov bl,heart_size2 mul bl ;pos = i * heart_size2; mov ch,0 ;i = 0; add ax,cx ;pos += MAKEWORD(j, i); mov bx,offset heart ;h = heart; add bx,ax ;h += pos; mov bl,[bx] ;h_ch = *h; .if bl==1 mov al,word ;if (h_ch == 1) h_ch = word; .else mov al,20h ;else h_ch = ' '; .endif mov ah,9h mov bl,gao_color mov bh,0 mov cx,1 int 10h ;putchar_attr(h_ch, gao_color); pop cx pop ax inc cl ;j++; inc dl ;_xy.y++; .endw ;} inc dh ;_xy.x++; mov dl,y ;_xy.y = xy.y; inc ch ;i++; mov cl,0 ;j = 0; .endw ;} inc dh ;_xy.x++; mov dl,y ;_xy.y = xy.y; mov ch,0 mov cl,0 ;i = 0; j = 0; pop bx .endw ;} ; pop dx pop cx pop bx pop ax endm ;打印函数 gao_print macro ;ignore c source code push ax push bx push cx push dx ; gao_judge [jud],[x],[y],person1_x1,person1_y1,person1_x2,person1_y2 .if [jud]==1 gao_clear_screen 90h,person1_x1,person1_y1,person1_x2,person1_y2 gao_print_string string_person1,person1_x,person1_y,90h gao_printf_num person1_x,person1_y,90h,[person1] gao_print_heart person1_x,person1_y,9ch,[person1],3h .elseif [person]==1 gao_clear_screen 90h,person1_x1,person1_y1,person1_x2,person1_y2 gao_print_string string_person1,person1_x,person1_y,90h gao_printf_num person1_x,person1_y,90h,[person1] gao_print_heart person1_x,person1_y,9ch,[person1],3h .else gao_clear_screen 10h,person1_x1,person1_y1,person1_x2,person1_y2 gao_print_string string_person1,person1_x,person1_y,10h gao_printf_num person1_x,person1_y,10h,[person1] gao_print_heart person1_x,person1_y,14h,[person1],3h .endif ; gao_judge [jud],[x],[y],person2_x1,person2_y1,person2_x2,person2_y2 .if [jud]==1 gao_clear_screen 0b0h,person2_x1,person2_y1,person2_x2,person2_y2 gao_print_string string_person2,person2_x,person2_y,0b0h gao_printf_num person2_x,person2_y,0b0h,[person2] gao_print_heart person2_x,person2_y,0bch,[person2],5h .elseif [person]==2 gao_clear_screen 0b0h,person2_x1,person2_y1,person2_x2,person2_y2 gao_print_string string_person2,person2_x,person2_y,0b0h gao_printf_num person2_x,person2_y,0b0h,[person2] gao_print_heart person2_x,person2_y,0bch,[person2],5h .else gao_clear_screen 30h,person2_x1,person2_y1,person2_x2,person2_y2 gao_print_string string_person2,person2_x,person2_y,30h gao_printf_num person2_x,person2_y,30h,[person2] gao_print_heart person2_x,person2_y,34h,[person2],5h .endif ; gao_judge [jud],[x],[y],map_x1,map_y1,map_x2,map_y2 .if [jud]==1 gao_clear_screen 0d0h,map_x1,map_y1,map_x2,map_y2 gao_print_map 0d0h,map_x,map_y .else gao_clear_screen 050h,map_x1,map_y1,map_x2,map_y2 gao_print_map 050h,map_x,map_y .endif ; gao_judge [jud],[x],[y],answer_x1,answer_y1,answer_x2,answer_y2 .if [jud]==1 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_doing,answer_x,answer_y,0c0h .else .if [map_over]==5 gao_clear_screen 40h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_doing,answer_x,answer_y,40h .elseif [map_over]==1 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_win1,answer_x,answer_y,0c0h .elseif [map_over]==2 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_win2,answer_x,answer_y,0c0h .elseif [map_over]==3 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_peace,answer_x,answer_y,0c0h .elseif [map_over]==4 gao_clear_screen 40h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_wrong,answer_x,answer_y,40h .elseif [map_over]==6 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_p1,answer_x,answer_y,0c0h .elseif [map_over]==7 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_p2,answer_x,answer_y,0c0h .endif ; .if [y]<=person1_y2 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_lose1,answer_x,answer_y,0c0h .elseif [y]>=person2_y1 gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_lose2,answer_x,answer_y,0c0h .endif .endif ; gao_judge [jud],[x],[y],end_x1,end_y1,end_x2,end_y2 .if [jud]==1 gao_clear_screen 0a0h,end_x1,end_y1,end_x2,end_y2 gao_print_string string_end,end_x,end_y,0a0h .else gao_clear_screen 20h,end_x1,end_y1,end_x2,end_y2 gao_print_string string_end,end_x,end_y,20h .endif ; gao_print_map_point [x],[y],0e0h ; .if [person1]==win_time gao_clear_screen 90h,person1_x1,person1_y1,person1_x2,person1_y2 gao_print_string string_person1,person1_x,person1_y,90h gao_printf_num person1_x,person1_y,90h,[person1] gao_print_heart person1_x,person1_y,9ch,[person1],3h ; gao_clear_screen 0b0h,person2_x1,person2_y1,person2_x2,person2_y2 gao_print_string string_person2,person2_x,person2_y,0b0h gao_printf_num person2_x,person2_y,0b0h,[person2] gao_print_heart person2_x,person2_y,0b4h,[person2],5h ; gao_clear_screen 0d0h,map_x1,map_y1,map_x2,map_y2 gao_print_map 0d0h,map_x,map_y ; gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_final1,answer_x,answer_y,0c0h ; gao_clear_screen 0a0h,end_x1,end_y1,end_x2,end_y2 gao_print_string string_thank,end_x,end_y,0a0h ; mov bh,0 mov ah,0h int 16h gao_exit ; .elseif [person2]==win_time gao_clear_screen 90h,person1_x1,person1_y1,person1_x2,person1_y2 gao_print_string string_person1,person1_x,person1_y,90h gao_printf_num person1_x,person1_y,90h,[person1] gao_print_heart person1_x,person1_y,94h,[person1],3h ; gao_clear_screen 0b0h,person2_x1,person2_y1,person2_x2,person2_y2 gao_print_string string_person2,person2_x,person2_y,0b0h gao_printf_num person2_x,person2_y,0b0h,[person2] gao_print_heart person2_x,person2_y,0bch,[person2],5h ; gao_clear_screen 0d0h,map_x1,map_y1,map_x2,map_y2 gao_print_map 0d0h,map_x,map_y ; gao_clear_screen 0c0h,answer_x1,answer_y1,answer_x2,answer_y2 gao_print_string string_final2,answer_x,answer_y,0c0h ; gao_clear_screen 0a0h,end_x1,end_y1,end_x2,end_y2 gao_print_string string_thank,end_x,end_y,0a0h ; mov bh,0 mov ah,0h int 16h ;uint8_t ch = getchar(); gao_exit ; .endif pop dx pop cx pop bx pop ax endm简单评论:代码复用性很差,感觉像凑行数的,游戏的坐标用hard code,这样的可维护性很差,原作者大量用宏,避免了参数传递和函数的调用规约的使用,虽然写代码是方便了,但造成了code rom会很大,最后原作者利用了编译器相关的特性来变量的值([imm]),这样不太好。
特别声明: revision-c系列元旦前不再做更新,所有的c代码,是本人主观判断,并非标准答案,有兴趣的童鞋,可以再摸索摸索研究研究,能写出更好的代码抽象度。有任何问题,欢迎大家积极参与讨论。(说帖子太长了,只能分2次发了。。。。。。。)