Графика в TASM: текстовая строка, которая двигается стрелками клавиатуры, и меняет цвет при каждом нажатии клавиши - Assembler
Формулировка задачи:
Нужно реализовать текстовую строку которая двигается стрелками клавиатуры, и меняет цвет при каждом нажатии клавиши, совсем не понимаю как можно реализовать, подскажите
Решение задачи: «Графика в TASM: текстовая строка, которая двигается стрелками клавиатуры, и меняет цвет при каждом нажатии клавиши»
textual
Листинг программы
.model small .stack 100h .data ;коды, возвращаемые int 16h ah=00h kbArrowUp equ 4800h kbArrowDown equ 5000h kbArrowLeft equ 4B00h kbArrowRight equ 4D00h kbEsc equ 011Bh CrLf db 0Dh, 0Ah, '$' azMsg db 'My Little String!', 0 MsgLen equ $-azMsg-1 Mode0D_W equ 320 ;ширина экрана в пикселях для видеорежима 0Dh Mode0D_H equ 200 ;высота экрана в пикселях для видеорежима 0Dh Mode0D_C equ 16 ;количество цветов для видеорежима 0Dh Mode0D_A equ 0A000h ;начальный адрес видеопамяти для видеорежима 0Dh VideoPage db ? ;номер видеостраницы lpFontTable8x14 dw 2 dup(?);указатель на таблицу символов 8x14 FontH equ 14 ;количество строк в описании глифа FontW equ 8 ;количество столбцов в описании глифа Xstart dw 100 ;координаты начала надписи Ystart dw 70 Xcurr dw ? ;текущие координаты левого верхнего угла строки Ycurr dw ? Color db 1 ;цвет выводимого текста PointsPerMsg equ MsgLen*FontW ;длина изображения строки в точках .code main proc mov ax, @data mov ds, ax ; установка графического видео режима mov ax, 000Dh int 10h ;возьмём какую-нибудь таблицу знакогенератора ;например, 8x14 mov ax, 1130h ;Get EGA information mov bh, 2 ;2 = return ES:BP => ROM 8x14 font table addr int 10h mov [lpFontTable8x14 ], bp mov [lpFontTable8x14+2], es mov ah, 0Fh ;уточнение параметров видеорежима int 10h mov [VideoPage], bh call ShowString mov ah, 00h int 16h inc [Color] call ShowString @@GetCmd: ;ожидание нажатия любой клавиши mov ah, 00h int 16h ;обработка команды @@TestCmd1: cmp ax, kbArrowUp jne @@TestCmd2 mov dx, [Ystart] cmp dx, 0 je @@GetCmd dec dx mov cx, [Xstart] jmp @@Redraw @@TestCmd2: cmp ax, kbArrowDown jne @@TestCmd3 mov dx, [Ystart] add dx, FontH cmp dx, Mode0D_H jae @@GetCmd sub dx, FontH inc dx mov cx, [Xstart] jmp @@Redraw @@TestCmd3: cmp ax, kbArrowLeft jne @@TestCmd4 mov cx, [Xstart] cmp cx, 0 je @@GetCmd dec cx mov dx, [Ystart] jmp @@Redraw @@TestCmd4: cmp ax, kbArrowRight jne @@TestCmd5 mov cx, [Xstart] add cx, PointsPerMsg cmp cx, Mode0D_W jae @@GetCmd sub cx, PointsPerMsg inc cx mov dx, [Ystart] jmp @@Redraw @@TestCmd5: cmp ax, kbEsc jne @@GetCmd jmp @@StopCmdLoop @@Redraw: mov al, [Color] mov [Color], 0 call ShowString inc al ;Color++ cmp al, Mode0D_C ;if (Color>MaxColor) sbb ah, ah ; Color=1 and al, ah cmp al, 1 adc al, 0 mov [Color], al mov [Xstart], cx mov [Ystart], dx call ShowString jmp @@GetCmd @@StopCmdLoop: ;переключение в текстовый режим mov ax, 0003h int 10h ;завершение программы mov ax, 4C00h int 21h main endp ShowString proc push ax push bx push cx push dx push si push di mov ax, [Xstart] mov [Xcurr], ax mov ax, [Ystart] mov [Ycurr], ax lea si, [azMsg] cld ForByChar: lodsb ;al - очередной символ строки or al, al ;конец строки? - прервать цикл jz Break mov cx, FontH ;цикл по строкам глифа mul cl ;di=(код символа)*(размер глифа) - смещение строки текущего глифа mov di, ax ForByLines: push ax push cx mov ah, es:[bp+di] ;считываем очередную строку глифа mov cx, 8 ForByBits: mov al, 0 ;сдвигаем биты влево, и выбираем цвет точки shl ah, 1 sbb al, 0 ;если бит был равен 0 - то al:=0 and al, [Color] ;если бит был равен 1 - то al:=Color push ax push bx push cx push dx ;установка графической точки mov ah, 0Ch mov bh, [VideoPage] ;номер видеостраницы mov dx, [Ycurr] ;строка mov cx, [Xcurr] ;колонка ;mov al, 1 ;цвет (+80h означает XOR с точкой на экране) int 10h pop dx pop cx pop bx pop ax inc word ptr [Xcurr] ;следующую точку выводить правее loop ForByBits ;сместиться на одну строку вниз при выводе следующей линии глифа inc word ptr [Ycurr] ;вернуться на начальную колонку при выводе след. линии глифа sub [Xcurr],word ptr 8 pop cx pop ax add di, 1 ;переходим к рассмотрению следующей строки глифа loop ForByLines ;для вывода глифа следующего символа ; - уменьшить строку на высоту глифа sub [Ycurr],word ptr FontH ; - сдвинуть колонку на ширину глифа add [Xcurr],word ptr 8 jmp ForByChar Break: pop di pop si pop dx pop cx pop bx pop ax ret ShowString endp end main
ИИ поможет Вам:
- решить любую задачу по программированию
- объяснить код
- расставить комментарии в коде
- и т.д