📄 mouse.asm
字号:
include ..\cwlib.inc
include ..\cw.inc
ME struc
ME_Flags dw ?
ME_XCoord dw ?
ME_YCoord dw ?
ME_Wide dw ?
ME_Depth dw ?
ME ends
MaxExcludes equ 16
MaxExcludeSplits equ 32
scode
;-------------------------------------------------------------------------------
;
;Initialise mouse stuff.
;
;On Entry:
;
;nothing.
;
;On Exit:
;
;EAX - mouse status.
;
;ALL other registers preserved.
;
_MouseInitialise:
public _MouseInitialise
MouseInitialise proc near
pushad
;
push ebp
mov ax,0
int 33h
cmp ax,0
jz @@0
mov MousePresent,1 ;flag mouse.
@@0: pop ebp
;
;Register pointer Bitmaps with Bitmap manager.
;
mov esi,offset MouseDetails ;point to table
@@1: cmp d[esi],-1
jz @@2
push esi
mov esi,[esi] ;point to the table.
add esi,4+4 ;skip animation and hot spot
@@3: cmp d[esi],-1 ;end of the list?
jz @@4
push esi
mov esi,[esi]
call RegisterSystemBitmap
pop esi
add esi,4
jmp @@3
@@4: pop esi
add esi,4
jmp @@1
;
@@2: ;Setup mouse event call back address.
;
push es
push cs
pop es
mov edx,offset MouseEvent
mov ecx,-1
mov ax,0ch
int 33h
pop es
;
;Patch timer interupt for animation module.
;
mov bl,8
sys GetVect
push ds
mov ds,CodeSegAlias
assume ds:@CurSeg
mov d[OldTimer],edx
mov w[OldTimer+4],cx
assume ds:DGROUP
pop ds
mov bl,8
mov cx,cs
mov edx,offset TimerInterupt
sys SetVect
;
mov MouseOffCall,offset MouseOff
mov MouseOnCall,offset MouseOn
mov MouseExcludeCall,offset MouseExclude
;
popad
movzx eax,MousePresent
ret
MouseInitialise endp
;-------------------------------------------------------------------------------
;
;Release mouse stuff.
;
;On Entry:
;
;Nothing.
;
;On Exit:
;
;Nothing.
;
;ALL registers preserved.
;
_MouseRemove:
public MouseRemove
MouseRemove proc near
pushad
;
cmp w[OldTimer+4],0 ;check timer was patched.
jz @@0
;
mov ax,0 ;reset mouse interupt mask/pointers.
int 33h
;
mov edx,d[OldTimer]
mov cx,w[OldTimer+4]
mov bl,8
sys SetVect
;
@@0: popad
ret
MouseRemove endp
;-------------------------------------------------------------------------------
TimerInterupt proc far
pushm ds,ax
mov ax,DGROUP
mov ds,ax
;
inc TimerCount
;
mov AnimWaiting,0 ;clear animation flag.
cmp InMouse,0
jnz @@0
cmp w[TimerStackStore+4],0
jnz @@0
pushad
pushm es,fs,gs,ds
pop es
;
mov d[TimerStackStore],esp
mov w[TimerStackStore+4],ss
mov ax,ds
mov ss,ax
mov esp,offset TimerStack
;
call MouseUpdate
;
cmp MouseLeftDnCnt,0
jz @@d0
dec MouseLeftDnCnt
jnz @@d0
and MouseBtDouble,not (1+8)
@@d0: ;
lss esp,f[TimerStackStore]
mov w[TimerStackStore+4],0
popm es,fs,gs
popad
@@0: ;
popm ds,ax
assume ds:nothing
jmp cs:f[OldTimer]
assume ds:DGROUP
OldTimer df ?
TimerInterupt endp
;-------------------------------------------------------------------------------
;
;Turn the mouse pointer ON. Will increment the mouse flag byte. The mouse
;pointer is only displayed when this flag is > 0.
;
;On Entry:
;
;nothing.
;
;On Exit:
;
;nothing.
;
;ALL registers preserved.
;
_MouseOn:
public _MouseOn
MouseOn proc near
inc InMouse
mov MouseAnmCount,0 ;reset animation offset
mov MouseAnmCount2,-1 ;reset animation offset
mov MousePointAn,0 ;/
inc MouseFlag ;update the counter.
cmp MouseFlag,1
jl @@1
jg @@1
pushad
call MousePOn ;put the mouse on.
popad
@@1: dec InMouse
ret
MouseOn endp
;-------------------------------------------------------------------------------
;
;Turn the mouse pointer OFF. Will decrement the mouse flag byte. The mouse
;pointer is only displayed when this flag is > 0.
;
;On Entry:
;
;nothing.
;
;On Exit:
;
;nothing.
;
;ALL registers preserved.
;
_MouseOff:
public _MouseOff
MouseOff proc near
inc InMouse
dec MouseFlag ;update the counter.
cmp MouseFlag,0
jl @@1
jg @@1
pushad
call MousePOFF ;Remove the mouse.
popad
@@1: dec InMouse
ret
MouseOff endp
;-------------------------------------------------------------------------
;
;Set the type of graphic used for the mouse pointer. Only 2 are currently
;supported but others can be added to the table.
;
;On Entry:
;
;AL - Pointer number.
;
;On Exit:
;
;AL - Previous type.
;
;ALL other registers preserved.
;
MouseSetType proc near
pushad
inc InMouse
mov ah,MousePointNm
mov OldPointNm,ah
cmp al,ah
jz @@9
;
pushad
call MouseOff
popad
;
mov MousePointNm,al
mov MousePointAn,0
mov MouseAnmCount,0 ;reset animation offset
mov MouseAnmCount2,-1 ;reset animation offset
;
;Now fiddle the mouse position so that the new hot spot is in
;the same position as the old hot spot!
;
;If this isn't done, changing the mouse pointer number will
;change the co-ordinates returned by GetMouse without the
;pointer having moved. This could cause great confusion for
;the main program!
;
;Get the old pointers offsets.
;
movzx ebx,OldPointNm
shl ebx,2
add ebx,offset MouseDetails
test VideoModeFlags,8
jz @@Grph0
sub ebx,offset MouseDetails
add ebx,offset MouseDetailsT
@@Grph0: mov ebx,[ebx] ;get real table.
add ebx,4 ;skip animation table.
mov cx,0[ebx]
mov dx,2[ebx] ;get x,y offsets
;
;Point to the new offsets
;
movzx ebx,MousePointNm
shl ebx,2
add ebx,offset MouseDetails
test VideoModeFlags,8
jz @@Grph1
sub ebx,offset MouseDetails
add ebx,offset MouseDetailsT
@@Grph1: mov ebx,[ebx]
add ebx,4 ;skip animation pointer.
sub cx,0[ebx]
sub dx,2[ebx] ;get x,y differance.
;
;Add offsets to REAL mouse co-ordinates.
;
add cx,MousePointX1
add dx,MousePointY1
mov MousePointX1,cx
mov MousePointY1,dx
;
call MouseOn
;
@@9: dec InMouse
popad
mov al,OldPointNm
ret
MouseSetType endp
;-------------------------------------------------------------------------
MouseEvent proc far
pushm ds,es,fs,gs
pushad
push ax
mov ax,DGROUP
mov ds,ax
mov es,ax
pop ax
;
cmp w[EventStackStore+4],0
jnz @@9
cmp InMouse,0
jnz @@9
inc InMouse
;
mov d[EventStackStore],esp
mov w[EventStackStore+4],ss
mov ax,ds
mov ss,ax
mov esp,offset EventStack
;
call MouseUpdate
lss esp,f[EventStackStore]
mov w[EventStackStore+4],0
dec InMouse
@@9: ;
@@10: popad
popm ds,es,fs,gs
retf
MouseEvent endp
;-------------------------------------------------------------------------
;
;Get the current position & button state for the mouse.
;
;On Entry:
;
;nothing.
;
;On Exit:
;
;EBX - button state.
;ECX - X coord.
;EDX - Y coord.
;
;ALL other registers preserved.
;
MouseGet proc near
mov cx,MousePointX1
mov dx,MousePointY1
movzx ebx,MousePointNm
shl ebx,2
add ebx,offset MouseDetails
test VideoModeFlags,8
jz @@Grph0
sub ebx,offset MouseDetails
add ebx,offset MouseDetailsT
@@Grph0: mov ebx,[ebx] ;get real type.
add ebx,4 ;skip animation pointer.
add cx,0[ebx]
add dx,2[ebx]
mov bx,MousePointBt
movzx ebx,bx
movzx ecx,cx
movzx edx,dx
ret
MouseGet endp
;-------------------------------------------------------------------------
;
;Update the mouse pointer position visually. Put it in its new position and
;display the new graphic.
;
MouseUpdate proc near
inc InMouse
call MouseAnimate ;Animate the pointer.
call MouseHandler
cmp MousePointOff,0 ;Forced removal?
jnz @@0
mov al,MouseAnmCount ;update counter.
cmp al,MouseAnmCount2
mov MouseAnmCount2,al
jnz @@0
mov ax,MousePointX1 ;Current position
cmp ax,MousePointX2 ;Last position.
jnz @@0
mov ax,MousePointY1 ;Current position.
cmp ax,MousePointY2 ;Last position.
jz @@1
@@0: mov MousePointOff,0 ;Clear forced removal flag.
call MousePOff ;Remove last pointer.
call MousePOn ;Put a new pointer on.
@@1: dec InMouse
ret
MouseUpdate endp
;-------------------------------------------------------------------------
;
;This gets called every time there is mouse motion or a timer interupt. Fetches
;mouse status from the mouse driver and updates the co-ordinates acordingly.
;
MouseHandler proc near
mov ax,3
mov bx,0
int 33h
mov MousePointBt,bx
;
;Update left button double click status.
;
test MousePointBt,1 ;Left button press?
jz @@l1
cmp MouseLeftDnCnt,0 ;Second press?
jnz @@l0
;
;Hasn't been pressed within timeout period.
;
mov eax,MouseDoubleTime
mov MouseLeftDnCnt,eax
or MouseBtDouble,1
jmp @@l9
@@l0: ;
;Has been pressed within timeout period.
;
test MouseBtDouble,1 ;Was it released?
jnz @@l9
or MouseBtDouble,8 ;Signal double click.
jmp @@l9
;
@@l1: test MouseBtDouble,8
jz @@l2
;
;After effect of a double click.
;
and MouseBtDouble,not (1+8)
mov MouseLeftDnCnt,0
jmp @@l9
@@l2: ;
;Just reset the button press toggle incase it's the first
;stage of a double press.
;
and MouseBtDouble,not 1
@@l9: ;
mov ax,MouseBtDouble
and ax,8+16+32
or MousePointBt,ax
;
;Update X/Y stuff.
;
mov ax,0bh
mov cx,0
mov dx,0
int 33h
mov si,cx
mov di,dx
;
;Calculate X displacement
;
mov cx,MouseScaleX
cmp VideoXResolution,320+1
jc @@5
sub cx,2
cmp VideoXResolution,640+1
jc @@5
; dec cx
cmp VideoXResolution,800+1
jc @@5
; dec cx
@@5: mov ax,si
add ax,ax
add ax,MouseMickeyX ;add remainder from last time.
cwd
idiv cx
mov MouseMickeyX,dx ;Reset displacement
mov si,ax
add si,MousePointX1
;
movzx ebx,MousePointNm
shl ebx,2
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -