Проект Комментария к "Win32 API Tutorial" by Iczelion

Тема в разделе "WASM.PROJECTS", создана пользователем kero, 20 июн 2008.

  1. ALLeX

    ALLeX Member

    Публикаций:
    0
    Регистрация:
    21 окт 2004
    Сообщения:
    141
    Адрес:
    Ukraine
    kero
    "Недостающий" вариант можно было бы написать более лаконично (DlgProc+WndProc), если бы знать кому приходит очередной msg...
     
  2. kero

    kero Модератор SOURCES & 2LZ Команда форума

    Публикаций:
    0
    Регистрация:
    4 апр 2006
    Сообщения:
    1.074
    Адрес:
    Москва
    ALLeX
    О чем вы ??
     
  3. ALLeX

    ALLeX Member

    Публикаций:
    0
    Регистрация:
    21 окт 2004
    Сообщения:
    141
    Адрес:
    Ukraine
    kero
    Про объединение DlgProc и WndProc.
     
  4. kero

    kero Модератор SOURCES & 2LZ Команда форума

    Публикаций:
    0
    Регистрация:
    4 апр 2006
    Сообщения:
    1.074
    Адрес:
    Москва
    ALLeX
    А кто мешал узнать самостоятельно ?
    Всмотрелись бы в примеры из main_variants повнимательнее да покомпилировали чуток, варьируя обработчики в WndProc и DlgProc...

    Короче.
    Не смешивайте WndProc и DlgProc, это не одно и то же.
    wc.lpfnWndProc - именно для WndProc, не для DlgProc.

    "Очередной msg" - приходит именно в WndProc,
    и если там не обрабатывается - передается DefDlgProc,
    а оттуда - пользовательской DlgProc, если оная имеется.

    При этом "очередной msg" можно обрабатывать хоть в WndProc, хоть в DlgProc.

    Но только не в случае системных (первых и обычно единственных) WM_CREATE и WM_INITDIALOG.

    Я тащусь от этой фразы.
    При вашем желании поиметь сразу и WM_CREATE, и WM_INITDIALOG, - таки придется потерпеть связку WndProc+DlgProc.
    Ибо системное WM_CREATE приходит в WndProc еще до начала работы DlgProc (так что без WndProc - ни-ни).
    Ну, а в отсутствие DlgProc система WM_INITDIALOG в WndProc вообще не отправит.
    Т.е. CreateDialogParam(hInst,DlgId,0,0,0) - не годится, и необходима хотя бы "вырожденная" DlgProc:

    .asm
    Код (Text):
    1. .const
    2.   id   equ 100
    3. .data
    4.   _dlg  db "#32770",0  ; (WC_DIALOG)
    5.   _wnd  db "DlgClass",0
    6.   _1    db "WM_CREATE",0
    7.   _2    db "WM_INITDIALOG",0
    8. .data?
    9. .code
    10.  
    11. DlgProc proc hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
    12.   mov eax,FALSE
    13.   ret
    14. DlgProc endp
    15.  
    16. WndProc proc hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
    17.  
    18.   .if uMsg==WM_CREATE
    19.     invoke SetWindowText,hWnd,addr _1
    20.     invoke SetDlgItemText,hWnd,id+3,addr _1
    21.     mov eax,FALSE
    22.  
    23.   .elseif uMsg==WM_INITDIALOG
    24.     invoke SetDlgItemText,hWnd,id+3,addr _2
    25.     invoke GetDlgItem,hWnd,id+4
    26.     invoke SetFocus,eax
    27.     mov eax,FALSE
    28.  
    29.   .elseif uMsg==WM_CLOSE
    30.     invoke DestroyWindow,hWnd
    31.     mov eax,FALSE
    32.  
    33.   .elseif uMsg==WM_DESTROY
    34.     invoke PostQuitMessage,0
    35.     mov eax,FALSE
    36.  
    37.   .elseif uMsg==WM_COMMAND
    38.     .if wParam==id+1
    39.       mov eax,WM_CREATE
    40.       jmp @f
    41.     .elseif wParam==id+2
    42.       mov eax,WM_INITDIALOG
    43. @@:
    44.       invoke SendMessage,hWnd,eax,0,0
    45.     .endif
    46.     mov eax,wParam
    47.     and eax,0ffffh
    48.     invoke SetDlgItemInt,hWnd,id+5,eax,0
    49.     mov eax,FALSE
    50.  
    51.   .else
    52.     invoke DefDlgProc,hWnd,uMsg,wParam,lParam    
    53.   .endif
    54.   ret
    55. WndProc endp
    56.  
    57. RegisterWndClass proc hInst:HINSTANCE,lpproc:WNDPROC,lpclass:LPCTSTR
    58.  local  wc:WNDCLASSEX
    59.   mov   wc.cbSize,sizeof wc
    60.   invoke GetClassInfoEx,0,addr _dlg,addr wc
    61.   mov   eax,hInst
    62.   mov   wc.hInstance,eax  
    63.   mov eax,lpproc
    64.   mov   wc.lpfnWndProc,eax
    65.   mov eax,lpclass
    66.   mov   wc.lpszClassName,eax
    67.   invoke RegisterClassEx,addr wc
    68.   mov ecx,eax
    69.   mov eax,hInst
    70.   ret
    71. RegisterWndClass endp
    72.  
    73. DialogMessageLoop proc hWnd:HWND
    74.  local msg:MSG
    75.   .while TRUE
    76.     invoke GetMessage,addr msg,0,0,0
    77.     .break .if (!eax)
    78.     invoke IsDialogMessage,hWnd,addr msg
    79.     .if eax==FALSE
    80.       invoke TranslateMessage,addr msg
    81.       invoke DispatchMessage,addr msg
    82.     .endif
    83.   .endw
    84.   mov   eax,msg.wParam
    85.   ret
    86. DialogMessageLoop endp
    87.  
    88. start:
    89.   invoke GetModuleHandle,0
    90.   invoke RegisterWndClass,eax,addr WndProc,addr _wnd
    91.   invoke CreateDialogParam,eax,id,0,offset DlgProc,0
    92.   invoke DialogMessageLoop,eax
    93.   invoke ExitProcess,eax
    94.   invoke InitCommonControls
    95. end start
    .rc
    Код (Text):
    1. #include "\masm32\include\resource.h"
    2. #define  id  100
    3. #define  bp  BUTTON, WS_TABSTOP | BS_DEFPUSHBUTTON
    4. #define  bt  BUTTON, WS_TABSTOP
    5. #define  ed  EDIT,   WS_TABSTOP | WS_BORDER
    6. #define  em  EDIT,   WS_TABSTOP | WS_BORDER | WS_VSCROLL | WS_HSCROLL | ES_MULTILINE | ES_WANTRETURN
    7. #define  st  STATIC, SS_NOTIFY  | WS_BORDER
    8.  
    9. id DIALOGEX 20,20,300,150
    10. STYLE WS_POPUP | WS_SYSMENU | WS_VISIBLE | DS_CENTER
    11. EXSTYLE WS_EX_TOPMOST | WS_EX_CLIENTEDGE
    12. CAPTION ""
    13. CLASS "DlgClass"
    14. FONT 8,"Tahoma"
    15. {
    16.  CONTROL "WM_CREATE",       id+1, bp, 10,  10, 100, 15
    17.  CONTROL "WM_INITDIALOG",   id+2, bt, 10,  30, 100, 15
    18.  CONTROL "EDIT",            id+3, ed, 10,  50, 100, 15
    19.  CONTROL "MULTILINE  EDIT", id+4, em, 10,  70, 100, 35
    20.  CONTROL "STATIC",          id+5, st, 10, 115, 100, 15
    21. }
     
  5. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    С DefWindowProc и DefDlgProc в примере Iczelion'а разобрался, но меняя в своём примере эту функцию вылазит ошибка . Если не трудно , глянь как будет время, что не так. Прикрепляю файлы ниже . Зарание спасибо!
     
  6. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    ещё файл
     
  7. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    и последний...
    p.s. Сейчас понял, что надо было все три в рар запихать. Только сообщения не удаляются , поэтому исправлять не имеет смысла...
     
  8. kero

    kero Модератор SOURCES & 2LZ Команда форума

    Публикаций:
    0
    Регистрация:
    4 апр 2006
    Сообщения:
    1.074
    Адрес:
    Москва
    Об очевидных ошибках вроде обработки WM_CREATE "по Iczelion-у" говорить не буду, это разобрано выше, сам найди и поправь.

    Фигня же с нажатием "X"-кнопки заголовка - именно из-за того, что после замены DefWindowProc на DefDlgProc окно стало действительно диалоговым:
    "IDC_MESS equ 2" конфликтует со стандартной диалоговой константой "IDCANCEL equ 2".

    Поэтому или аккуратно поменять значение IDC_MESS, или добавить обработчик WM_CLOSE с DestroyWindow, а лучше сделать и то, и то.
     
  9. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    kero - Спасибо! Всё просто, исправил. Вчера мельком просмотрел ошибки Iczelion-а , сегодня ознакомлюсь повнимательней, что бы исправить остальное.
    з.ы. кстати, если сделать только WM_CLOSE с DestroyWindow, без изменения значения IDM_MESS, то точно такой же косяк получается , но уже с кнопкой Esc...
     
  10. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    kero - Ну, а строчки в WinMain -
    Код:

    invoke GetDlgItem,hDlg,IDC_EDIT
    invoke SetFocus,eax

    - зачем они?

    в поддержку Iczelion-а - что бы не имело значения в какой строчке стоит EDITTEXT в .rc, хотя, для экономии и оптимизации, конечно, проще поставить строчку EDITTEXT первой...
    Остальное всё понятно. Ценная информация для усвоения материала, спасибо!
     
  11. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    kero - tut11-1-k.rar , main_variants.rar, layoutrtl.rar,NonDialog - битые или уменя rar не работает? во всех архивах, при открытии пишет, что неожиданный конец архива. Из архива вынимает только exe , а asm, хоть и видно, но вытащить не получается...
    mb_ghost.rar - не вытаскивается mb_ghost.exe.manifest
    main_variants.rar - архив повреждён или имеет неизвестный формат
    wintreesnap_070520.rar - не вытаскивается asm
    cbt_hook.rar - повреждён
    дальше не проверял...
    интересного много, а скачать не получается...
     
  12. kero

    kero Модератор SOURCES & 2LZ Команда форума

    Публикаций:
    0
    Регистрация:
    4 апр 2006
    Сообщения:
    1.074
    Адрес:
    Москва
    Plis, не волнуйся, рары не битые, просто ты напоролся на аномальную зону васма :)
    Читай в форуме WASM.SITE ветку "Аттач".
    Вкратце: скачивай местные архивы качалками (ReGet и куча других).
     
  13. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    Доброго времени!
    kero Спасибо за подсказку. С аномальными зонами Wasma разобрался.
    Теперь не могу найти ответа , вот на это:
    "но зато фрагмент кода
    Код:

    .ELSE
    invoke DestroyWindow,hWnd

    - настолько ошибочен, что даже преодолевает ошибочное несовпадение значений IDM_EXIT в .asm и в .rc !)"

    А как здесь правильно?

    Единственное упоминание о выходе с DestroyWindow, это - "завершать немодальный CreateDialog* "по Iczelion-у" (т.е. EndDialog вместо DestroyWindow) - ошибка.", но это, вроде, вообще не то.
     
  14. kero

    kero Модератор SOURCES & 2LZ Команда форума

    Публикаций:
    0
    Регистрация:
    4 апр 2006
    Сообщения:
    1.074
    Адрес:
    Москва
    >А как здесь правильно?

    А как в tut10.asm WndProc обрабатывает WM_COMMAND ?

    Код (Text):
    1.     .ELSEIF uMsg==WM_COMMAND
    2.         mov eax,wParam
    3.         .IF lParam==0
    4.             .IF ax==IDM_GETTEXT
    5.                 invoke GetDlgItemText,hWnd,IDC_EDIT,ADDR buffer,512
    6.                 invoke MessageBox,NULL,ADDR buffer,ADDR AppName,MB_OK
    7.             .ELSEIF ax==IDM_CLEAR
    8.                 invoke SetDlgItemText,hWnd,IDC_EDIT,NULL
    9.             .ELSE
    10.                 invoke DestroyWindow,hWnd
    11.             .ENDIF
    12.         .ELSE
    13.             mov edx,wParam
    14.             shr edx,16
    15.             .IF dx==BN_CLICKED
    16.                 .IF ax==IDC_BUTTON
    17.                     invoke SetDlgItemText,hWnd,IDC_EDIT,ADDR TestString
    18.                         .ELSEIF ax==IDC_EXIT
    19.                     invoke SendMessage,hWnd,WM_COMMAND,IDM_EXIT,0
    20.                 .ENDIF
    21.             .ENDIF
    22.         .ENDIF
    Т.е. любое (ведь .ELSE!) WM_COMMAND с lParam=0 и wParam(low-order word)!=(IDM_GETTEXT либо IDM_CLEAR) вызовет DestroyWindow! Даже WM_COMMAND(0,0) :)
    А правильно - да хоть так:
    вместо
    Код (Text):
    1. .ELSE
    2.  invoke DestroyWindow,hWnd
    -
    Код (Text):
    1. .ELSEIF ax==IDM_EXIT
    2.  invoke DestroyWindow,hWnd
    но конечно - предварительно выбрав для IDM_EXIT что-то одно из 32002 (см. .asm) и 32003 (см. .rc) :)

    Если же охота, чтоб закрывалось и по ESC - добавь
    Код (Text):
    1. .ELSEIF ax==IDCANCEL
    2.  invoke DestroyWindow,hWnd
    Кстати, WM_COMMAND c wParam = IDCANCEL (и IDOK) приходит от IsDialogMessage как при DefWindowProc, так и при DefDlgProc,
    тогда как глюк с X-кнопкой (см. выше сообщение #28) связан с тем, что DefWindowProc и DefDlgProc по-разному обрабатывают WM_CLOSE.
     
  15. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    kero Спасибо за ответ!
     
  16. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    kero Привет!
    Воткнулся в проблему у Iczelion'а с progressbar : http://www.wasm.ru/article.php?article=1001018 ( 18 урок - контролы )
    Как работает пример в уроке с SetTimer я разобрался, но как привязывать к коду в программе не могу.
    Пример:

    ThreadProc PROC USES ecx Param:lol: WORD

    mov edx, 6000000
    mov ecx, 60000000

    cikl:

    add eax,eax
    dec ecx
    cmp ecx,0
    je vikh
    cmp edx,ecx
    jne cikl
    invoke SendMessage, hwndProgres, PBM_STEPIT, 0, 0
    shr edx,16
    jmp cikl

    vikh:

    invoke SendMessage,hwndProgres, PBM_SETPOS,0,0

    ret

    ThreadProc endp

    в трейде просто складываю eax c eax и хочу что бы этот процесс сопровождался заполнением процесс бара.
    Суть идеи: когда уменьшающаяся ecx догоняет edx, то происходит сообщение на PBM_SETPOS, которое сдвигает прогресс бар на какое-то количество пунктов. Потом edx делится, что бы ecx опять его догоняла, ну и так далее...

    В основном коде установки прогресс бара такие:

    S_VISIBLE+WS_CHILD, 0, 243, 400, 15, hWnd, IDC_PROGRES, hInstance, NULL
    mov hwndProgres,eax
    mov eax,1000
    mov CurrentStep, eax
    shl eax,16
    invoke SendMessage, hwndProgres,PBM_SETRANGE,0,eax
    invoke SendMessage, hwndProgres,PBM_SETSTEP,1,0

    Прогресс бар зацикливается и всё...
    PBM_SETSTEP и PBM_SETRANGE пробовал менять на разные значения, результат тот же.

    p.s. Извени, что не по теме поста задаю вопрос. Гугл прошарил , везде PBM_SETSTEP и PBM_SETRANGE применяется только с SetTimer, но к своему примеру не знаю как это прикрутить. Если не сложно объясни...
    Заранее спасибо!
     
  17. Rockphorr

    Rockphorr Well-Known Member

    Публикаций:
    0
    Регистрация:
    9 июн 2004
    Сообщения:
    2.622
    Адрес:
    Russia
    kero
    я двумя руками за чтоб вы это сделали и статью здесь опубликовали
     
  18. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    Rockphorr А что я таким трудным, или неразрешимым вопросом задался и kero озадачил, что по решению его можно статью писать?
    Если глупость написал по коду, так по этому и спрашиваю, что бы разъяснили...
    Вообще, я просто хотел понять принцип работы progressbar...
     
  19. Rockphorr

    Rockphorr Well-Known Member

    Публикаций:
    0
    Регистрация:
    9 июн 2004
    Сообщения:
    2.622
    Адрес:
    Russia
    Plis

    я про сабж топика - чтоб коментарии которые тут обсуждаются стали статьей или циклом статей
     
  20. Plis

    Plis New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2008
    Сообщения:
    26
    понятно