Articles   Members Online:
-Article/Tip Search
-News Group Search over 21 Million news group articles.
-Delphi/Pascal
-CBuilder/C++
-C#Builder/C#
-JBuilder/Java
-Kylix
Member Area
-Home
-Account Center
-Top 10 NEW!!
-Submit Article/Tip
-Forums Upgraded!!
-My Articles
-Edit Information
-Login/Logout
-Become a Member
-Why sign up!
-Newsletter
-Chat Online!
-Indexes NEW!!
Employment
-Build your resume
-Find a job
-Post a job
-Resume Search
Contacts
-Contacts
-Feedbacks
-Link to us
-Privacy/Disclaimer
Embarcadero
Visit Embarcadero
Embarcadero Community
JEDI
Links
How to check if a menu selection has been dispatched by the TPopupList Turn on/off line numbers in source code. Switch to Orginial background IDE or DSP color Comment or reply to this aritlce/tip for discussion. Bookmark this article to my favorite article(s). Print this article
23-Oct-02
Category
VCL-Menu
Language
Delphi 5.x
Views
124
User Rating
No Votes
# Votes
0
Replies
0
Publisher:
DSP, Administrator
Reference URL:
DKB
			Author: Jonas Bilinkevicius

I am creating a dynamic popup menu, fill it and call Popup to show the menu. After 
that method returns I am done with the menu, so I free it (see comment of Peter 
below). The problems is the OnClick events never get called. I found the problem 
but don't see how to get around it. When the menu is created it is added to the 
PopupList which has created a hidden window whose responsibility it is to dispatch 
the wm_Command message sent by all popup menus. The problem is that the wm_Command 
is happening after the Popup menu method returns and after I have freed the menu 
and it has been removed from the PopupList.

How do I get around this? I don't see a mechanism to check if the menu selection 
has been dispatched by the PopupList before freeing the menu item. I guess I could 
make the Popup menu a field of my class and free it in the OnClick Events but I 
won't be able to free the menu if no menu item is selected. I don't like this 
solution since the only place I need the popup is in one method of my class so I 
want to keep it a local variable.

Answer:

You go badly wrong when you think you're done. When Popup returns you are not done 
with the menu, you have just shown it and the user can now make a menu selection or 
close the menu by clicking elsewhere or hittin ESC. Only after that has happended 
are you truely "done" with the menu, if you destroy the VCl wrapper earlier the 
windows menu may visually persist but you have destroyed the link between it and 
your code.

In D5 there is a solution to your problem. Add this unit to your project (no 
further code is needed) and the active form will get the custom messages declared 
in the units interface. You could destroy the popup menu instance when you see 
CM_EXITMENULOOP. This solution does not work in earlier versions of Delphi which 
did not expose the Popuplist to the outside world. In these versions the only 
solution would be to install a WH_CALLWNDPROC hook (thread specific) when the menu 
is popped up and remove it again when it gets the WM_EXITMENULOOP message.

1   unit ExPopupList;
2   
3   interface
4   
5   uses
6     Controls;
7   
8   const
9     CM_MENUCLOSED = CM_BASE - 1;
10    CM_ENTERMENULOOP = CM_BASE - 2;
11    CM_EXITMENULOOP = CM_BASE - 3;
12  
13  implementation
14  
15  uses Messages, Forms, Menus;
16  
17  type
18    TExPopupList = class(TPopupList)
19    protected
20      procedure WndProc(var message: TMessage); override;
21    end;
22  
23    { TExPopupList }
24  
25  procedure TExPopupList.WndProc(var message: TMessage);
26    procedure Send(msg: Integer);
27    begin
28      if Assigned(Screen.Activeform) then
29        Screen.ActiveForm.Perform(msg, message.wparam, message.lparam);
30    end;
31  begin
32    case message.Msg of
33      WM_ENTERMENULOOP:
34        Send(CM_ENTERMENULOOP);
35      WM_EXITMENULOOP:
36        Send(CM_EXITMENULOOP);
37      WM_MENUSELECT:
38        with TWMMenuSelect(message) do
39          if (Menuflag = $FFFF) and (Menu = 0) then
40            Send(CM_MENUCLOSED);
41    end;
42    inherited;
43  end;
44  
45  initialization
46    PopupList.Free;
47    PopupList := TExPopupList.Create;
48    {Note: will be freed by Finalization section of Menus unit}
49  end.


			
Vote: How useful do you find this Article/Tip?
Bad Excellent
1 2 3 4 5 6 7 8 9 10

 

Advertisement
Share this page
Advertisement
Download from Google

Copyright © Mendozi Enterprises LLC