Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "WinAPI";
Текущий архив: 2005.07.18;
Скачать: [xml.tar.bz2];

Вниз

GUI на WinAPI   Найти похожие ветки 

 
Marser ©   (2005-05-25 17:30) [0]

При создании элементарного окна с кнопкой возникла следующая проблема - обработка нажатия левой кнопки мыши на кнопке происходит, однако визуально кнопка на это не реагирует.
Вот код:
program apipro;

uses
 Windows, Messages;
var
 MWND:TWndClassEx;
 mwin,mbut:HWND;
 Mesg:TMsg;
 l:Pointer;
function MWinProc(wnd:HWND;Msg:Integer;wParam:wParam;lParam:lParam):HResult;stdcall;
begin
 case msg of
   wm_destroy:Begin
     postquitmessage(0); exit;
     Result:=0;
   End
 else
    result:=DefWindowProc(wnd,msg,wparam,lparam);
 end
end;
function MButProc(wnd:HWND;Msg:Integer;wParam:wParam;lParam:lParam):HResult;stdcall;
begin
 result:=0;
 case msg of
   WM_LBUTTONDOWN:messagebox(0,"Меня нажали","My button",mb_iconexclamation);
 else
   Result:=CallWindowProc(l,wnd,msg,wparam,lparam);
 end;
end;
procedure createmainwin;
begin
 mwnd.cbSize:=sizeof(TWndClassEx);
 mwnd.style:=CS_HREDRAW or CS_VREDRAW;
 mwnd.lpfnWndProc:=@MWinProc;
 mwnd.cbClsExtra:=0;
 mwnd.cbWndExtra:=0;
 mwnd.hInstance:=HInstance;
 mwnd.hIcon:=LoadIcon(0,idi_application);
 mwnd.hCursor:=LoadCursor(0,IDC_ARROW);
 mwnd.hbrBackground:=COLOR_BTNFACE+1;
 mwnd.lpszMenuName:=nil;
 mwnd.lpszClassName:="WinMin : Main";
 mwnd.hIconSm:=0;
 RegisterClassEx(mwnd);
 mwin:=CreateWindowEx(0,"WinMin : Main","MyWin",WS_OVERLAPPEDWINDOW or WS_BORDER or WS_CAPTION,100,60,
                200,200,0,0,Hinstance,nil);
 ShowWindow(mwin,CmdShow);
end;
procedure createbutton;
begin
 mbut:=createwindow("BUTTON","My Button",WS_CHILDWINDOW or BS_PUSHBUTTON,10,10,80,20,
                      mwin,0,Hinstance,nil);
 ShowWindow(mbut,CmdShow);
 l:=pointer(GetWindowLong(mbut,gwl_wndproc));
 SetWindowLong(mbut,gwl_wndproc,integer(@MButProc))
end;
begin
 createmainwin;
 createbutton;
 While GetMessage(Mesg,0,0,0) do
 begin
  TranslateMessage(Mesg);
  DispatchMessage(Mesg);
 end;
end.

Вариант
function MButProc(wnd:HWND;Msg:Integer;wParam:wParam;lParam:lParam):HResult;stdcall;
begin
 if msg=WM_LBUTTONDOWN then
   messagebox(0,"Меня нажали","My button",mb_iconexclamation);
   Result:=CallWindowProc(l,wnd,msg,wparam,lparam);
 end;
end;

То бишь, полностью стандартная обработка вместе с нестандартной, приводит к непонятному мне зацикливанию.

Одним из вариантов решения был предложен Игорем Осовьяком - дополнительная отсылка собственного сообщения в postmessage с многоступенчатой обработкой, в принципе неплох. Но мне кажется, что всё несколько проще.


 
Polevi ©   (2005-05-25 17:38) [1]

BM_CLICK, BM_CLICKED


 
Marser ©   (2005-05-25 17:44) [2]


> Polevi ©   (25.05.05 17:38) [1] [Новое
>сообщение][Ответить]
> BM_CLICK, BM_CLICKED

BN_CLICKED
Это был первоначальный вариант. Но этого события не происходило, насколько я помню.


 
Игорь Шевченко ©   (2005-05-25 17:47) [3]

Для того, чтобы кнопка реагировала нужно вызывать старую оконную процедуру и не вызывать MessageBox, так как MessageBox меняет окно, захватывающее мышь


 
Marser ©   (2005-05-25 17:48) [4]


> Игорь Шевченко ©   (25.05.05 17:47) [3] [Новое
>сообщение][Ответить]
> Для того, чтобы кнопка реагировала нужно вызывать
> старую оконную процедуру и не вызывать MessageBox, так
> как MessageBox меняет окно, захватывающее мышь

Спасибо! А как же всё-таки запустить messagebox? После обработки старой процедурой?


 
Marser ©   (2005-05-25 17:51) [5]


> Polevi ©   (25.05.05 17:38) [1][Ответить]

BM_CLICK
This message is sent by an application to simulate the user clicking a button. This message causes the button to receive a WM_LBUTTONDOWN and a WM_LBUTTONUP message, and the button"s parent window to receive a BN_CLICKED notification message.

(С)MSDN


 
DVM ©   (2005-05-25 17:53) [6]


> Спасибо! А как же всё-таки запустить messagebox? После обработки
> старой процедурой?

у кнопок есть уведомляющие сообщения (кнопка нажалась и т.д.) именно в них надо вызывать разные messagebox-ы


 
Игорь Шевченко ©   (2005-05-25 17:55) [7]

Marser ©   (25.05.05 17:48) [4]


> А как же всё-таки запустить messagebox? После обработки
> старой процедурой?


Можно попробовать и после, но лучше отправить (PostMessage) сообщение основному окну, пусть оно реагирует.


 
Marser ©   (2005-05-25 17:57) [8]


> DVM ©   (25.05.05 17:53) [6]

bn_clicked уже опробовался. Неудачно.


> Игорь Шевченко ©   (25.05.05 17:55) [7]

То есть, без своего оообщения тут не обойдется?
Мне несложно, конечно, но как-то казалось, что можно обойтись без этого...


 
DVM ©   (2005-05-25 18:00) [9]


> bn_clicked уже опробовался. Неудачно.

ты где это сообщение пытался ловить - в оконной процедуре кнопки или родительском окне?


 
Marser ©   (2005-05-25 18:04) [10]


> DVM ©   (25.05.05 18:00) [9]

Везде ловил.


 
Marser ©   (2005-05-25 18:07) [11]

Частное решение найдено!
Отловил wm_lbuttonUp и делоф!
Спасибо всем, кто пробовал помочь!


 
Marser ©   (2005-05-25 18:08) [12]

Конечно, оно именно частное(возможно нажатие за пределами кнопки). Однако уже выглядит нормально :-)


 
alpet ©   (2005-05-25 18:12) [13]

Зачем вообще подменять у кнопки ее процедуру? Имхо проще обрабатывать в процедуре основного окна сообщение WM_COMMAND.


 
Игорь Шевченко ©   (2005-05-25 18:13) [14]

alpet ©   (25.05.05 18:12) [13]


> Зачем вообще подменять у кнопки ее процедуру?


Обычно для собственной отрисовки


 
Marser ©   (2005-05-25 18:13) [15]


> alpet ©   (25.05.05 18:12) [13] [Новое
>сообщение][Ответить]
> Зачем вообще подменять у кнопки ее процедуру? Имхо
> проще обрабатывать в процедуре основного окна
> сообщение WM_COMMAND.

Уже учтено. Но спасибо!


 
alpet ©   (2005-05-25 18:20) [16]

>Обычно для собственной отрисовки

Хм, понятно. Я что-то привык к WM_DRAWITEM + BS_OWNERDRAW, но так вроде хитрее...


 
alpet ©   (2005-05-25 18:22) [17]

Вернее NM_CUSTOMDRAW, WM_DRAWITEM здесь не причем.


 
Marser ©   (2005-05-25 18:25) [18]

прошу прощения у DVM за проявленное ламерство. С notification и wm_command у меня ещё не было никакого опыта работы.


 
alpet ©   (2005-05-25 18:29) [19]

Вообще все перепутал, NM_CUSTOMDRAW у меня используется для рисования в ListView контроле, а здесь рулят WM_DRAWITEM, WM_CTLCOLORBTN.


 
alpet ©   (2005-05-25 18:31) [20]

По отношению к кнопкам NM_CUSTOMDRAW можно использовать только в Windows XP.


 
Игорь Шевченко ©   (2005-05-26 00:55) [21]

alpet ©   (25.05.05 18:20) [16]


> Хм, понятно. Я что-то привык к WM_DRAWITEM + BS_OWNERDRAW,
> но так вроде хитрее...


Не то, что хитрее, но гибче. Можно обрабатывать сообщения WM_ERASEBKGND (видел в первом таком примере, еще для Windows 3.1), можно обрабатывать сообщения WM_NCPAINT (сам писал такие обработчики для стандартных контролов) и т.д. и т.п., можно менять картинку при наведении мыши, кстати. Customdraw эту проблему не решит.



Страницы: 1 вся ветка

Форум: "WinAPI";
Текущий архив: 2005.07.18;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.5 MB
Время: 0.036 c
1-1119818085
Green_Templar
2005-06-27 00:34
2005.07.18
Internal Error L1333


3-1118217498
Юра
2005-06-08 11:58
2005.07.18
InterBase, 100тыс записей клиенту


4-1116386312
Владимир_К
2005-05-18 07:18
2005.07.18
как вызвать окно выбора папки?


1-1119854437
AlexG
2005-06-27 10:40
2005.07.18
Как создать экземпляр TOleStream?


10-1096498814
Ivan K
2004-09-30 03:00
2005.07.18
Тупой вопрос. Как вытащить данные из xml?





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский