Author: Jonas Bilinkevicius
How to run an application in systray mode
Answer:
Solve 1:
Nothing special. It's just a normal application hiding all of its forms and
displaying an icon in the systray. The shell takes care of displaying the icon.
Just send a message with all info to the shell. Here is an example:
1 var
2 Nid: TNOTIFYICONDATA;
3
4 prodecure ShowTrayIcon();
5 begin
6 nid.cbSize := sizeof(TNOTIFYICONDATA);
7 nid.Wnd := Form1.Handle;
8 nid.uID := 1;
9 nid.uFlags := NIF_ICON or NIF_MESSAGE or NIF_TIP;
10 nid.uCallbackMessage := WM_MYMESSAGE; {or make it Nil if you don't need it}
11 nid.hIcon := LoadIcon(0, IDI_EXCLAMATION); {replace this by your icon}
12 lstrcpy(nid.szTip, 'This is my hint');
13 Shell_NotifyIcon(NIM_ADD, @nid);
14 end;
15
16 //Only have Win32 code for the callback:
17
18 function WndProc(hwnd: HWND; msg: integer; wParam: WPARAM;
19 lParam: LPARAM): LRESULT; stdcall;
20 begin
21 case msg of
22 WM_MYMESSAGE:
23 begin
24 case (LOWORD(lParam)) of
25 WM_LBUTTONDOWN:
26 begin
27 MessageBox(hwnd, 'You pressed the left mouse button', 'Caption',
28 MB_YESNO or MB_SETFOREGROUND or MB_SYSTEMMODAL);
29 end;
30 WM_RBUTTONDOWN:
31 begin
32 PostQuitMessage(0);
33 result := 0;
34 end
35 else
36 begin
37 result := 0;
38 end;
39 end;
40 result := 1; {true}
41 end;
42 WM_CLOSE:
43 begin
44 PostQuitMessage(0);
45 result := 0;
46 {Exit;}
47 end;
48 WM_DESTROY:
49 begin
50 PostQuitMessage(0);
51 result := 0;
52 {Exit;}
53 end;
54 end;
55 result := DefWindowProc(hwnd, msg, wParam, lParam);
56 end;
Solve 2:
Try this and don't forget the TImageList holding your icon:
57 unit Main;
58
59 interface
60
61 uses
62 Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
63 Shellapi, ImgList, VersionMonitor;
64
65 type
66 TForm1 = class(TForm)
67 ImageList1: TImageList;
68 procedure FormCreate(Sender: TObject);
69 procedure FormDestroy(Sender: TObject);
70 procedure FormCloseQuery(Sender: TObject; var CanClose: Boolean);
71 private
72 { Private Declarations }
73 Data: PNotifyIconData;
74 wm_notifyicon: Cardinal;
75 notifyHandle: THandle;
76 procedure MyOnClose(var message: TMessage); message WM_CLOSE;
77 public
78 { Public Declarations }
79 procedure NotifyIconEvnt(var Param: TMessage);
80 end;
81
82 var
83 Form1: TForm1;
84
85 implementation
86
87 {$R *.DFM}
88
89 procedure TForm1.FormCreate(Sender: TObject);
90 var
91 aIcon: TIcon;
92 begin
93 wm_notifyicon := RegisterWindowMessage('wm_notifyicon');
94 notifyHandle := AllocateHWnd(NotifyIconEvnt);
95 aIcon := TIcon.Create;
96 ImageList1.GetIcon(0, aIcon);
97 new(Data);
98 Data.cbSize := sizeof(TNotifyIconData);
99 Data.Wnd := notifyHandle;
100 Data.uFlags := NIF_ICON or NIF_MESSAGE or NIF_TIP;
101 Data.uCallbackMessage := WM_NOTIFYICON;
102 Data.hIcon := aIcon.handle;
103 StrCopy(Data.szTip, 'Tooltip hint');
104 Shell_NotifyIcon(NIM_ADD, Data);
105 SetWindowLong(Application.Handle, GWL_EXSTYLE, WS_EX_TOOLWINDOW);
106 Form1.Visible := False;
107 end;
108
109 procedure TForm1.FormDestroy(Sender: TObject);
110 begin
111 Shell_NotifyIcon(NIM_DELETE, Data);
112 DeallocateHWnd(notifyHandle);
113 dispose(Data);
114 end;
115
116 procedure TForm1.MyOnClose(var message: TMessage);
117 begin
118 Beep;
119 Close;
120 end;
121
122 procedure TForm1.NotifyIconEvnt(var Param: TMessage);
123 begin
124 case Param.LParam of
125 WM_LBUTTONDOWN:
126 begin
127 Form1.Visible := True;
128 end;
129 WM_RBUTTONDOWN:
130 begin
131 Form1.Visible := False;
132 end;
133 WM_CLOSE:
134 begin
135 DeallocateHWnd(notifyHandle);
136 Close;
137 end;
138 end;
139 end;
140
141 procedure TForm1.FormCloseQuery(Sender: TObject; var CanClose: Boolean);
142 begin
143 DeallocateHWnd(notifyHandle);
144 CanClose := True;
145 end;
146
147 end.
|