Top.Mail.Ru
Мастера DELPHI, Delphi programming community Титульная страница Поиск, карта сайта Написать письмо 
| Новости | Поиск | FAQ | Статьи | Книги | Новости VCL |
| Форумы ЧАТ | Орешник | KOL и MCK |
Форумы -» Основная («Начинающим»)/ Базы / WinAPI / Компоненты / Сети / Media / Игры / Corba и COM / KOL / FreePascal / .Net / Прочее / RSDN.ORG

« предыдущая ветвь | форум | следующая ветвь »

Перехват клавиши мыши, когда курсор над любым элементом окна [D6]


EthernalWonderer ©   (2004-09-09 10:25:00) 

Уважаемые Мастера!
ЗАДАЧА: сделать ComboBox, у которого в списке несколько десятков коротких вариантов выбора. Обычный не подходит - долго прокручивать вверх - вниз :).
РРЕШЕНИЕ: Взял TBitBtn, при нажатии на который становится видимой  ("выпадает") панель (Panel1.Visible := True), на которой расположен TRadioButton в несколько колонок.
ПРОБЛЕМА: У обычного ComboBox выпадающий список прячется при нажатии ЛЮБОЙ клавиши мыши на ЛЮБОМ элементе формы. Прописать такое же поведение моей выпадающей панели не удаётся: перехват нажатий мыши:
   
type
 TPropertiesSI1 = class(TForm)
 private
 procedure LMouseDownHook(var Message: TMessage); message WM_LBUTTONDOWN;
...
procedure TPropertiesSI1.LMouseDownHook(var Message: TMessage);
Begin
 ShowMessage('OK');
End;


не работает, если курсор находится, например, над TLabel, TBevel или над некоторыми другими элементами окна.

TForm.OnKeyDown (KeyPreview=True) на клавиши мыши не отзывается...

ВОПРОС: Как мне скрыть мою "всплывающую" панель при щелчке мышью на ЛЮБОМ элементе или заголовке окна?
Заранее спасибо!


NAlexey   (2004-09-10 11:53:00) [1]

>EthernalWonderer   (09.09.04 18:38) [4]
Какой еще FAQ. Посмотри как реализован ComboBox. Взгляни в исходники. Или кинь таймер на форму задай интервал сколько надо и нажми на кноку до срабатывания таймера, и ты увидишь для чего нужен WM_CANCELMODE:

procedure TForm1.Button1Click(Sender: TObject);
begin
 panel1.Visible:=true;
end;

procedure TForm1.ApplicationEvents1Message(var Msg: tagMSG;
 var Handled: Boolean);
begin
case Msg.message of
WM_LBUTTONDOWN,
WM_RBUTTONDOWN,
WM_MBUTTONDOWN,
WM_NCLBUTTONDOWN,
WM_NCRBUTTONDOWN,
WM_NCMBUTTONDOWN,
CM_DEACTIVATE:panel1.Visible:=false;
end;
end;

procedure TForm1.Timer1Timer(Sender: TObject);
begin
 MessageBox(Self.Handle, 'Твоя панель видна!', '', MB_OK or MB_ICONASTERISK);
 Timer1.Enabled := False;
end;
;


EthernalWonderer   (2004-09-10 11:06:00) [2]

Всё оказалось так просто:)! БОЛЬШОЕ спасибо easy ©!


easy   (2004-09-09 18:54:00) [3]

unit Unit1;

interface

uses
 Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
 Dialogs, AppEvnts, StdCtrls, ExtCtrls;

type
 TForm1 = class(TForm)
   ApplicationEvents1: TApplicationEvents;
   Button1: TButton;
   Panel1: TPanel;
   RadioGroup1: TRadioGroup;
   procedure ApplicationEvents1Message(var Msg: tagMSG;
     var Handled: Boolean);
   procedure Button1Click(Sender: TObject);
 private
   { Private declarations }
 public
   { Public declarations }
 end;

var
 Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
 panel1.Visible:=true;
end;

procedure TForm1.ApplicationEvents1Message(var Msg: tagMSG;
 var Handled: Boolean);
begin
case Msg.message of
 WM_LBUTTONDOWN,
 WM_RBUTTONDOWN,
 WM_MBUTTONDOWN,
 WM_NCLBUTTONDOWN,
 WM_NCRBUTTONDOWN,
 WM_NCMBUTTONDOWN,
 CM_DEACTIVATE:panel1.Visible:=false;
end;
end;


EthernalWonderer   (2004-09-09 18:38:00) [4]

И вообще, похоже, рекомендация NAlexey ©   (09.09.04 10:55) [1] не совсем корректная, поскольку в FAQ:
"...Переопределите в подклассе TForm оконную процедуру WinProc класса. В примере оконная процедура переопределяется для того чтобы реагировать на сообщение WM_CANCELMODE, показывающее, что выполняется messagebox или какой-либо еще диалог ...".


EthernalWonderer   (2004-09-09 18:16:00) [5]

???


EthernalWonderer   (2004-09-09 14:21:00) [6]

Спасибо, но пока не получается.
Делаю так:

type
 TMyRadioGroup = class(TRadioGroup)
   private
     procedure PanelHide(var Message: TMessage); message WM_CANCELMODE;
   End;

procedure TMyRadioGroup.PanelHide(var Message: TMessage);
Begin
 Parent.Visible := False;
End;


Затем при создании формы создаю панель и её содержимое:

procedure TPropertiesSI1.FormCreate(Sender: TObject);
Begin
 ...
 Panel1 := TPanel.Create(Self);
 With Panel1 Do Begin
   Parent := Self;
   ...
 End;
 RadioGroup1 := TMyRadioGroup.Create(Panel1);
 With RadioGroup1 Do Begin
   Parent := Panel1;
   ...
 End;
 ...
End;


Всё создаётся и работает, но при переводе фокуса на другие контролы формы Parent.Visible = False не выполняется.
Что здесь неверно?


NAlexey   (2004-09-09 10:55:00) [7]

Выпадающий список прячется не только при нажатии на твою форму, но и при потере фокуса твоей программой и прочих событиях отменяющих текущее действие. Реализовано это ч.з WM_CANCELMODE.


Наверх

Титульная страница Поиск, карта сайта Написать письмо