В настоящее время я работаю над проектом сборки и столкнулся с проблемой: у меня есть процедура под названием «mouse_click», которую мне нужно вызвать пару раз в проекте. в первый раз, когда процесс вызывается, он работает так, как должен, но во второй раз, когда он вызывается после строки «int 33h», bx всегда равен единице, и он пропускает ту часть, где я проверяю, нажата ли мышь. вот код:
proc mouse_click
mov ax,0h
int 33h ;resets the mouse
mov ax,1h
int 33h ;shows the mouse
not_pressed:
mov bx,0
mov ax,3h
int 33h
cmp bx, 01h ;checks if left mouse is pressed
jne not_pressed
;if left mouse is not pressed, it jumps to not_pressed and checks again if left mouse is pressed
shr cx, 1 ;devide the x coordinates in 2 to get correct x coordinates
mov [left_pressed_x], cx
;moves the x cordinates of the mouse to left_pressed_x when left button is pressed
mov [left_pressed_y], dx
;moves the y cordinates of the mouse to left_pressed_y when left button is pressed
mov ax, 2h
int 33h
;hides the mouse because if not the coordinates of the color will be the one on the outline of the mouse so the color would never change
mov bh, 0 ;sets page to zero
mov ah, 0Dh ; checks pixel color in mouse coordinates(left_pressed_x, left_pressed_y)
int 010h
;al = color
mov [left_pressed_color], al
; moves the color to left_pressed_color
add [left_pressed_color], '0'
;turns left_pressed_color from unicode into ascii
mov ax, 1
int 33h ;shows the mouse agaim
ret
endp mouse_click
Я пробовал сбросить bx перед строкой «int 33h» и перед строкой «ret», но каждый раз, когда он доходит до строки «int 33h», bx равен единице.
Как мне «отпустить» ЛКМ? Потому что я нажимаю ее только на короткое время, а затем отпускаю, и только после того, как снова вызову процесс (когда я не нажимаю мышь)
int 33h AX=3 возвращает текущее состояние кнопок в регистре BX. Само собой разумеется, что вы получаете там 1, потому что ЛКМ на самом деле нажата во время вашего второго вызова (иначе мы попадаем в область паранойи сломанных драйверов). Вы уверены, что не делаете этого? Как узнать, что ЛКМ нажата до второго вызова mouse_click? Когда он на самом деле называется?
Я почти уверен, что не делаю этого, потому что, как я уже сказал, я нажимаю ее только на короткое время, но я попытаюсь добавить фрагмент кода в процесс mouse_click, который проверяет, нажата ли мышь, хотя Я правда не думаю, что это сработает..
Я добавил фрагмент кода, который проверяет, отпущена ли мышь, и он все еще не работает.
Как ты это делаешь? Я предполагаю, что вы использовали тот же вызов int33h AX=3 в цикле, чтобы дождаться, пока BX станет равным 0, верно? Предполагая, что вы это сделали и этот цикл работает нормально, мы приходим к выводу, что один и тот же системный вызов работает в одном месте, а не в другом. Чего не может быть, если только не происходит что-то чрезвычайно странное.





Каждый раз, когда вы вызываете mouse_click, мышь сбрасывается, потому что процесс начинается с mov ah,0 / int 33h, внутри bx указано количество кнопок. Я добавил код, который печатает это.
Далее у нас есть цикл not_pressed. То есть, если ничего не нажималось, Вы увидите 0, если была нажата ПКМ, Вы увидите 2. Если вы нажмете ЛКМ, вы увидите 1, и код остановится, потому что я добавил ожидание службы ключа, и после этого остальная часть кода будет выполнена, bx = 1, процедура завершится. Каждый раз, когда Вы позвоните mouse_click, это будет происходить.
Если вы решите переместить mov ah,0 / int 33h за пределы процесса, мышь будет инициализирована только один раз. Сначала код будет напечатан number of buttons, потому что это то, что внутри bx, позже bx будет содержать только 1.
IDEAL
MODEL small
STACK 100h
assume ds:data, cs:code
segment data
left_pressed_x dw ?
left_pressed_y dw ?
left_pressed_color db ?
pos_x dw ?
pos_y dw ?
status_text db "Number of buttons: ",13,10
db " Pressed:$"
ends
segment code
Start:
proc main
mov ax, data
mov ds,ax
mov ax,13h ; mode 13h, 320x200x256
int 10h
mov ax,0a000h ; es = video mem address
mov es,ax
;-----------------------
mov ah,02h ; move cursor
mov dh,0
mov dl,2
int 10h
mov ah,09h ; show status text
lea dx, status_text
int 21h
; mov ax,0h
;int 33h ; resets the mouse
main_loop:
call mouse_click
mov ah,01h ; check keyboard buffer
int 16h
jz no_keys
mov ah,00h
int 16h
cmp al,27 ; if ESC pressed, exit app
je quit
no_keys:
jmp main_loop
quit:
MOV AX, 3h
int 10h
mov ax, 4c00h
int 21h
endp main
proc mouse_click
mov ax,0h
int 33h ; resets the mouse
; bx = number of buttons
mov ah,02h ; position
mov dh,0
mov dl,21
int 10h
mov ah,02h ; print number of buttons
mov dl,bl
add dl,30h
int 21h
mov ax,1h
int 33h ;shows the mouse
not_pressed:
;mov bx,0
mov ax,3h ; mouse status
int 33h ; bx = button number
mov ah,02h ; position of button number
mov dh,1
mov dl,13
int 10h
mov ah,02h ; inside loop: 0 - nothing was pressed
mov dl,bl ; 2 - RMB
add dl,30h ; 3 - LMB + RMB
int 21h ; 4 - CMB
cmp bx, 01h ; we go outside if bx = 1, checks if left mouse is pressed
jne not_pressed
;if left mouse is not pressed, it jumps to not_pressed and checks again if left mouse is pressed
mov ah,02h ; position
mov dh,1
mov dl,13
int 10h
mov ah,02h ; print 1 and stop (wait for key press)
mov dl,bl ; just to see that LMB was pressed
add dl,30h ; after that bx is changed on enter to mouse_click
int 21h ; bx = number of mouse buttons
mov ah,08h
int 21h
shr cx, 1 ;devide the x coordinates in 2 to get correct x coordinates
mov [left_pressed_x], cx
;moves the x cordinates of the mouse to left_pressed_x when left button is pressed
mov [left_pressed_y], dx
;moves the y cordinates of the mouse to left_pressed_y when left button is pressed
mov ax, 2h
int 33h
;hides the mouse because if not the coordinates of the color will be the one on the outline of the mouse so the color would never change
mov bh, 0 ;sets page to zero
mov ah, 0Dh ; checks pixel color in mouse coordinates(left_pressed_x, left_pressed_y)
int 010h
;al = color
mov [left_pressed_color], al
; moves the color to left_pressed_color
add [left_pressed_color], '0'
;turns left_pressed_color from unicode into ascii
mov ax, 1
int 33h ;shows the mouse agaim
ret
endp mouse_click
ends ;code
end Start
Простой вероятный ответ - вы дождались нажатия ЛКМ, что-то сделали, а потом снова проверяете, а она ВСЕ ЕЩЕ нажата.