Assembler & Win32 - Пример 3
Оконное приложение

Файл dmenu.asm

Ideal
P586
Radix 16
Model flat
 
struc WndClassEx
cbSize dd 0
style dd 0
lpfnWndProc dd 0
cbClsExtra dd 0
cbWndExtra dd 0
hInstance dd 0
hIcon dd 0
hCursor dd 0
hbrBackground dd 0
lpszMenuName dd 0
lpszClassName dd 0
hIconSm dd 0
ends WndClassEx
 
struct Point
left dd 0
top dd 0
right dd 0
bottom dd 0
ends Point
 
struct msgStruc dd 0
hwnd dd 0
message dd 0
wParam dd 0
lParam dd 0
time dd 0
pt dd 0
ends msgStruc Point <>
MyMenu = 0065
ID_OPEN = 9C41
ID_SAVE = 9C42
ID_EXIT = 9C43
 
CS_VREDRAW = 0001
CS_HREDRAW = 0002
IDI_APPLICATION = 7F00
IDC_ARROW = 7F00
COLOR_WINDOW = 5
WS_EX_WINDOWEDGE = 00000100
WS_EX_CLIENTEDGE = 00000200
WS_EX_OVERLAPPEDWINDOW = WS_EX_WINDOWEDGE OR WS_EX_CLIENTEDGE
WS_OVERLAPPED = 00000000
WS_CAPTION = 00C00000
WS_SYSMENU = 00080000
WS_THICKFRAME = 00040000
WS_MINIMIZEBOX = 00020000
WS_MAXIMIZEBOX = 00010000
WS_OVERLAPPEDWINDOW = WS_OVERLAPPED OR \
WS_CAPTION OR \
WS_SYSMENU OR \
WS_THICKFRAME OR \
WS_MINIMIZEBOX OR \
WS_MAXIMIZEBOX
CW_USEDEFAULT = 80000000
SW_SHOW = 5
WM_COMMAND = 0111
WM_DESTROY = 0002
WM_CLOSE = 0010
MB_OK = 0
 
PROCTYPE ptGetModuleHandle  stdcall \
lpModuleName :dword
 
PROCTYPE ptLoadIcon stdcall \
hInstance :dword, \
lpIconName :dword
 
PROCTYPE ptLoadCursor stdcall \
hInstance :dword, \
lpCursorName :dword
 
PROCTYPE ptLoadMenu stdcall \
hInstance :dword, \
lpMenuName :dword
 
PROCTYPE ptRegisterClassEx stdcall \
lpwcx :dword
  
PROCTYPE ptCreateWindowEx stdcall \
dwExStyle :dword, \
LpClassName :dword, \
lpWindowName :dword, \
dwStyle :dword, \
x :dword, \
y :dword, \
nWidth :dword, \
nHeight :dword, \
hWndParent :dword, \
hMenu :dword, \
hInstance :dword, \
lpParam :dword
 
PROCTYPE ptShowWindow stdcall \
nWnd :dword, \
nCmdShow :dword
 
PROCTYPE ptUpdateWindow stdcall\
hWnd :dword
  
PROCTYPE ptGetMessage stdcall\
pMsg :dword, \
hWnd :dword, \
wMsgFilterMin :dword, \
wMsgFilterMax :dword
 
PROCTYPE ptTranslateMessage stdcall \
lpMsg :dword
 
PROCTYPE ptDispatchMessage stdcall \
pmsg :dword
 
PROCTYPE ptSetMenu stdcall \
hWnd :dword,\
hMenu :dword
 
PROCTYPE ptPostQuitMessage stdcall \
nExitCode :dword
 
PROCTYPE ptDefWindowProc stdcall \
hWnd :dword,\
Msg :dword,\
wParam :dword,\
lParam :dword
 
PROCTYPE ptSendMessage stdcall \
hWnd :dword,\
Msg :dword,\
wParam :dword,\
lParam :dword
 
PROCTYPE ptMessageBox stdcall \
hWnd :dword,\
lpText :dword,\
lpCaption :dword,\
uType :dword
   
PROCTYPE ptExitProcess stdcall \
exitCode :dword
  
extrn GetModuleHandleA :pt:GetModuleHandle
extrn LoadIconA :ptLoadIconA
extrn LoadCursorA :ptLoadCursorA
extrn RegisterClassExA :ptRegisterClassExA
extrn LoadMenuA :ptLoadMenuA
extrn CreateWindowExA :ptCreateWindowExA
extrn ShowWindow :ptShowWindow
extrn UpdateWindow :ptUpdateWindow
extrn GetMessageA :ptGetMessageA
extrn TranslateMessage :ptTranslateMessage
extrn DispatchMessageA :ptDispatchMessageA
extrn SetMenu :ptSetMenu
extrn PostQuitMessage :ptPostQuitMessage
extrn DefWindowProcA :ptDefWindowProcA
extrn SendMessageA :ptSendMessageA
extrn MessageBoxA :ptMessageBoxA
extrn ExitProcess :ptExitProcess
extrn
 
UDataSeg
hInst dd ?
hWnd dd ?
  
IFNDEF VER1
hMenu dd ?
ENDIF
  
DataSeg
msg msgStruc <>
classTitle db 'Menu demo' ,0
wndTitle db 'Demo program' ,0
msg_open_txt db 'You selected open' ,0
msg_open_tlt db 'Open box' ,0
msg_save_txt db 'You selected save' ,0
msg_save_tlt db 'Save box' ,0
CodeSeg
Start: call GetModuleHandleA, 0 ; не обязательно, но желательно
mov [hInst],eax
sub esp,SIZE WndClassEx  ; отведём место в стеке под структуру
mov [(WndClassEx esp).cbSize],SIZE WndClassEx
mov [(WndClassEx esp).style],CS_HREDRAW or CS_VREDRAW
mov [(WndClassEx esp).lpfnWndProc],offset WndProc
mov [(WndClassEx esp).cbWndExtra],0
mov [(WndClassEx esp).cbClsExtra],0
mov [(WndClassEx esp).hInstance],eax
call LoadIconA, 0, IDI_APPLICATION
mov [(WndClassEx esp).hIcon],eax
call LoadCursorA, 0, IDC_ARROW
mov [(WndClassEx esp).hCursor],eax
mov [(WndClassEx esp).hbrBackground],COLOR_WINDOW
IFDEF VER1
mov [(WndClassEx esp).lpszMenuName],MyMenu
ELSE
mov [(WndClassEx esp).lpszMenuName],0
ENDIF
mov [(WndClassEx esp).lpszClassName],offset classTitle
mov [(WndClassEx esp).hIconSm],0
call RegisterClassExA, esp  ; зарегистрируем класс окна
add esp,SIZE WndClassEx ; восстановим стек
; и создадим окно
IFNDEF VER2
call
CreateWindowExA, WS_EX_OVERLAPPEDWINDOW, \ extended window style
offset classTitle, \ pointer to registered class name
offset wndTitle, \ pointer to window name
WS_OVERLAPPEDWINDOW, \ window style
CW_USEDEFAULT, \ horizontal position of window
CW_USEDEFAULT, \ vertical position of window
CW_USEDEFAULT, \ window width
CW_USEDEFAULT, \ window height
0, \ handle to parent or owner window
0, \ handle to menu, or child-window identifier
[hInst], \ handle to application instance
0 ; pointer to window-creation data
ELSE
call LoadMenu, hInst MyMenu
mov [hMenu],eax
call
CreateWindowExA WS_EX_OVERLAPPEDWINDOW, \ extended window style
offset classTitle, \ pointer to registered class name 
offset wndTitle, \ pointer to window name
WS_OVERLAPPEDWINDOW, \ window style
CW_USEDEFAULT, \ horizontal position of window
CW_USEDEFAULT, \ vertical position of window
CW_USEDEFAULT, \ window width
CW_USEDEFAULT, \ window height
0, \ handle to parent or owner window
eax, \ handle to menu, or child-window identifier
[hInst], \ handle to application instance
0 ; pointer to window-creation data
ENDIF
 
mov [hMenu],eax
call ShowWindow, eax, SW_SHOW ; show window
UpdateWindow, [hWnd] ; redraw window
 
IFDEF VER3
call LoadMenuA, [hInst], MyMenu
mov [hMenu],eax
call SetMenu [hWnd], eax
ENDIF
 
msg loop:
call GetMessageA, offset msg,  0, 0, 0
or ax,ax
jz exit
call TranslateMessage, offset msg, 
call DispatchMessageA, offset msg, 
jmp msg loop
exit:
call ExitProcess, 0
   
public stdcall     WndProc
proc WndProc  stdcall
arg @@hwnd: dword, @@msg: dword, @@wPar: dword, @@lPar: dword
mov eax,[@@msg]
cmp eax,WM_COMMAND
je @@command
cmp eax,WM_DESTROY
jne @@default
call PostQuitMessage, 0
xor eax,eax
jmp @@ret
@@default
call DefWindowProcA, [@@hwnd], [@@msg], [@@wPar], [@@lPar]
@@ret ret
@@command:
mov eax,[@@wPar]
cmp eax, ID_OPEN
je @@open
cmp eax, ID_SAVE
je @@save
call SendMessageA, [@@hwnd], WM_CLOSE, 0, 0
xor eax, eax
jmp @@ret
@@open:
mov eax, offset msg_open_txt
mov edx, offset msg_open_tlt
jmp @@mess
@@save:
mov eax, offset msg_save_txt
mov edx, offset msg_save_tlt
@@mess:
call MessageBoxA, 0, eax, edx, MB_OK
xor eax,eax
jmp @@ret
endp WndProc
endStart
Сайт Alexus Software Development