Assembler & Win32

Усов Александр

Пример 1. Программа работы с диалогом

 

 

Файл, содержащий текст приложения, dlg.asm

IDEAL

P586

RADIX  16

MODEL  FLAT

%NOINCL

%NOLIST

include      "winconst.inc"             ; API Win32 consts

include      "winptype.inc"             ; API Win32 functions prototype

include      "winprocs.inc"             ; API Win32 function

include      "resource.inc"             ; resource consts

MAX_USER_NAME =      20

DataSeg

szAppName    db     'Demo 1', 0

szHello             db     'Hello, '

szUser       db     MAX_USER_NAME dup (0)

CodeSeg

Start:       call   GetModuleHandleA,   0

             call   DialogBoxParamA,    eax, IDD_DIALOG, 0, offset DlgProc, 0

             cmp    eax,IDOK

             jne    bye

             call   MessageBoxA,        0, offset szHello,  \

                                        offset szAppName,   \

                                        MB_OK or MB_ICONINFORMATION

bye:         call   ExitProcess,        0

public stdcall      DlgProc

proc   DlgProc      stdcall

arg    @@hDlg :dword,      @@iMsg :dword,      @@wPar :dword,      @@lPar :dword

             mov    eax,[@@iMsg]

             cmp    eax,WM_INITDIALOG

             je     @@init

             cmp    eax,WM_COMMAND

             jne    @@ret_false

             mov    eax,[@@wPar]

             cmp    eax,IDCANCEL

             je     @@cancel

             cmp    eax,IDOK

             jne    @@ret_false

             call   GetDlgItemTextA,    @@hDlg, IDR_NAME,   \

                                        offset szUser, MAX_USER_NAME

             mov    eax,IDOK

@@cancel:    call   EndDialog,          @@hDlg, eax

@@ret_false: xor    eax,eax

             ret

@@init:             call   GetDlgItem,         @@hDlg, IDR_NAME

             call   SetFocus,           eax

             jmp    @@ret_false

endp   DlgProc

end    Start

Файл ресурсов dlg.rc

#include "resource.h"

IDD_DIALOG DIALOGEX 0, 0, 187, 95

STYLE DS_MODALFRAME | DS_3DLOOK | WS_POPUP | WS_CAPTION | WS_SYSMENU

EXSTYLE WS_EX_CLIENTEDGE

CAPTION "Dialog"

FONT 8, "MS Sans Serif"

BEGIN

    DEFPUSHBUTTON   "OK",IDOK,134,76,50,14

    PUSHBUTTON      "Cancel",IDCANCEL,73,76,50,14

    LTEXT           "Type your name",IDC_STATIC,4,36,52,8

    EDITTEXT        IDR_NAME,72,32,112,14,ES_AUTOHSCROLL

END

Остальные файлы из данного примера, приведены в приложении 1.

 

Краткие комментарии к программе

Сразу после метки Start, программа обращается к функции API Win32 GetModuleHandle для получения handle данного модуля (данный параметр чаще именуют как handle of instance). Получив handle, мы вызываем диалог, созданный либо вручную, либо с помощью какой-либо программы построителя ресурсов. Далее программа проверяет результат работы диалогового окна. Если пользователь вышел из диалога посредством нажатия клавиши OK, то приложение запускает MessageBox с текстом приветствия.

Диалоговая процедура обрабатывает следующие сообщения. При инициализации диалога  (WM_INITDIALOG) она просит Windows установить фокус на поле ввода имени пользователя. Сообщение WM_COMMAND обрабатывается в таком порядке: делается проверка на код нажатия клавиши. Если была нажата клавиша OK, то пользовательский ввод копируется в переменную szValue, если же была нажата клавиша Cancel, то копирования не производится. Но и в том и другом случае вызывается функция окончания диалога: EndDialog. Остальные сообщения в группе WM_COMMAND просто игнорируются, предоставляя Windows действовать по умолчанию.

Вы можете сравнить приведённую программу с аналогичной программой, написанной на ЯВУ, разница в написании будет незначительна. Очевидно те, кто писал приложения на ассемблере под Windows 3.x, отметят тот факт, что исчезла необходимость в сложном и громоздком startup коде. Теперь приложение выглядит более просто и естественно.