Delphi如何让程序最小化到任务栏(截取WM_SYSCOMMAND后,调用Shell_NotifyIcon)

现在很多的应用程序都有这样一种功能,当用户选择最小化窗口时,窗口不是象平常那样最小化到任务栏上,而是“最小化”成一个任务栏图标。象FoxMail 
3.0 NetVampire 
3.0等都提供了这样的功能。实现这样的功能实际上并不复杂,在窗口最小化时,窗口会发出WM_SYSCOMMAND消息,你只要需要截取Windows的WM_SYSCOMMAND消息,在窗口最小化时隐藏窗口并调用WindowsAPI函数Shell_NotifyIcon将定义的图标添加到任务栏上,Shell_NotifyIcon的函数定义是这样的:function 
Shell_NotifyIcon(dwMessage:DWORD; lpData: PNotifyIconData): BOOL; stdcall; 
其中的参数dwMessage指定Shell_NotifyIcon函数的操作,可以是NIM_ADD NIM_DELETE 
NIM_MODIFY三个值中的一个,分别对应添加图标、删除图标、修改图标的动作。

---- 参数lpData指向的PNotifyIconData结构的定义如下:

_NOTIFYICONDATAW = 
record 
   
cbSize: DWORD; 
   Wnd: HWND; 
   uID: UINT; 
   uFlags: 
UINT; 
   uCallbackMessage: UINT; 
   hIcon: HICON; 
   szTip: array 
[0..63] of WideChar; 
end;

TNotifyIconData = _NOTIFYICONDATAW; 
---- 
在这个结构中Wnd指明所属的窗口,UCallbackMessage指明回调消息,如果指明了Wnd和 
uCallbackMessage,则当用户对任务栏图标有动作(如点击图标,在图标上移动光标等)。系统都会发送uCallbackMessage消息给Wnd指定的窗口。hIcon是要添加的图标的句柄,szTip 
是图标的提示行(就是当移动光标到图标上,出现的一个小黄方框内出现的文字)。消息。实现上面的功能,最主要的是要处理WM_SYSCOMMAND消息和自定义的图标消息,这些消息在Delphi中并没有相应的事件。这里就需要使用到Delphi的自定义消息处理功能来截取并处理这些消息。

---- 
首先看下面的程序。在执行程序之前,首先要改变Form1的Icon属性,给Form1装入一个图标,否则在任务栏上会出现一块空白。

unit Unit1; 
interface 
uses 
Windows, Messages, SysUtils,  
Classes, Graphics, Controls, Forms, 
Dialogs,ShellAPI;

const 
WM_BARICON=WM_USER+200;

type 
TForm1 = class(TForm) 
private 
    procedure 
WMSysCommand(var 
Message: 
TMessage); message WM_SYSCOMMAND; 
    procedure 
WMBarIcon(var 
Message:TMessage);message WM_BARICON; 
   { Private 
declarations } 
public 
   
{ Public declarations } 
end;

var 
Form1: 
TForm1;

implementation

{$R *.DFM} 
procedure TForm1.WMSysCommand 
(var Message:TMessage); 
var 
   lpData:PNotifyIconData; 
begin 
if Message.WParam = SC_ICON then 
begin 
    
//如果用户最小化窗口则将窗口 
    隐藏并在任务栏上添加图标 
    
lpData := new(PNotifyIconDataA); 
    lpData.cbSize := 
88; 
//SizeOf(PNotifyIconDataA); 
    lpData.Wnd := 
Form1.Handle; 
    lpData.hIcon := 
Form1.Icon.Handle; 
    lpData.uCallbackMessage := 
WM_BARICON; 
    lpData.uID :=0; 
    
lpData.szTip := ‘Samples‘; 
    lpData.uFlags := 
NIF_ICON  
or NIF_MESSAGE or 
NIF_TIP; 
    
Shell_NotifyIcon(NIM_ADD,lpData); 
    dispose(lpData); 
    Form1.Visible := False; 
end 
else 
begin 
    //如果是其它的SystemCommand 
    
消息则调用系统缺省处理函数处理之。 
    
DefWindowProc(Form1.Handle,Message. 
Msg,Message.WParam,Message.LParam); 
end; 
// 
end;

procedure 
TForm1.WMBarIcon(var Message:TMessage); 
var 
   lpData:PNotifyIconData; 
begin 
if (Message.LParam = WM_LBUTTONDOWN) then 
   
begin 
    //如果用户点击任务栏图标则将图标删除并回复窗口。 
    
lpData := new(PNotifyIconDataA); 
    lpData.cbSize := 
88;//SizeOf(PNotifyIconDataA); 
    lpData.Wnd := 
Form1.Handle; 
    lpData.hIcon := 
Form1.Icon.Handle; 
    lpData.uCallbackMessage := 
WM_BARICON; 
    lpData.uID :=0; 
    
lpData.szTip := ‘Samples‘; 
    lpData.uFlags := 
NIF_ICON or NIF_MESSAGE or NIF_TIP; 
    
Shell_NotifyIcon(NIM_DELETE,lpData); 
    dispose(lpData); 
    Form1.Visible := True; 
   end; 
end;

end. 
---- 
运行上面的程序,点击程序窗口标题栏上的最小化按钮,你就可以看到窗口被“最小化”成了一个任务栏图标,点击图标,窗口又会恢复原来的状态。

---- 
从上面的程序可以看到,Delphi的自定义消息处理功能的实现也是十分简单的,首先在Form类的Private定义中加入自定义消息处理函数的定义,定义的描述如下:

procedure UserPro(Var 
Message: 
TMessage):message 
WindowsMessage 
其中UserPro是用户自定义消息处理函数的名称, 
WindowsMessage是Windows消息常量或自定义消息常量。 
---- 然后在程序中加入消息处理函数,函数的一般格式如下:

Procedure UserClass.UserPro(Var Message:TMessage); 
   
var 
//加入定义 
   
Begin 
//加入程序语句 
   
End; 
   其中UserClass是封装自定义消息处理函数的类的名称。 
------------------------------------------------------------------------------------------------
最后,Delphi的自定义消息处理函数要涉及到Windows的消息的结构,在这里我就不多说了,大家可以参考Windows 
API帮助和Delphi的相关帮助信息。相信大家如果掌握了Delphi的自定义消息处理函数,一定可以编写出象VB一样简洁,象C++一样功能强大的程序来的。

参考:http://www.cnblogs.com/key-ok/p/4594662.html

时间: 2024-10-12 22:55:41

Delphi如何让程序最小化到任务栏(截取WM_SYSCOMMAND后,调用Shell_NotifyIcon)的相关文章

WPF程序最小化到任务通知栏

我们通常使用的桌面软件,都可以最小化到任务通知栏,并且可以从任务通知栏再打开当前软件,或者通过软件的快捷方式从任务通知栏呼出. 我们可以通过下面的方式把WPF程序最小化到任务栏.由于WPF并没有实现Notification的功能,我们需要借助于WinForm中NotifyIcon来实现,请看代码: using WinForms = System.Windows.Forms; private WinForms.NotifyIcon _notifyIcon; private WinForms.Con

win10程序最小化后任务栏没有显示的解决方法

通常情况下我们会在电脑打开很多应用程序,当我们暂时不需要使用的时候我们会将它最小化,最小化后会以缩略图的形式出现在任务栏中,等我们有需要的时候再打开就行.但是今天用电脑时发现将程序最小化之后任务栏中却看不到程序的最小化窗口(注意为win10操作系统),这样使用带来非常的不方便,那么为什么会出现这种情况呢?经研究发现出现这种问题主要是由于资源管理器出现问题所引起的,下面为大家介绍解决方法.1.打开任务管理器,右击任务栏选择任务管理器或者同时按下[ctrl+shift+esc]组合键打开:2.找到[

delphi中最小化其他程序及所有程序最小化(使用 shell.minimizeAll 和自己寻找窗口这两种办法)

1.所有程序最小化 uses ComObj; var shell : OleVariant; begin shell := CreateOleObject('Shell.Application'); shell.minimizeAll; end; 2.最小化其他程序 spy++ 查找要最小化的程序classname var Indicador :Integer; begin // Find the window by Classname Indicador := FindWindow(PChar

转 点击关闭时最小化到任务栏

来源:http://www.2cto.com/kf/201401/274489.html 现在很多软件如360杀毒软件.酷狗音乐都拥有最小化至任务栏并在系统托盘区留下图标,我的项目同样需要该功能.所以本文主要叙述如何使用C#让窗体最小化至任务栏,同时在系统托盘区的图标点击左键能显示窗体,右键能关联控件显示3个常用功能.主要涉及到的控件是NotifyIcon和ContextMenuStrip,此类文章较多,希望作者以自己的独特视角给予大家帮助. 一.界面操作 1.创建"Windows窗体应用程序&

将VMware工作站最小化到托盘栏

目录 前言 将VMware最小化到托盘栏的方法 1.下载 Trayconizer 2.解压 trayconizerw.zip 3.创建 VMware 快捷方式 4.修改 VMware 快捷方式 5.运行 前言 因为一直要用到虚拟机,每次最小化的时候,总是占用任务栏,很不爽,于是在网上搜索了一番,终于找到一个可以用的方法. 将VMware最小化到托盘栏的方法 首先下载一个软件,叫做Trayconizer,最好把这个文件放在固定的目录下,比如我放在了D盘下的ProgramFiles目录下. 1.下载

outlook 关闭时最小化到任务栏的完美解决方法

最近使用Outlook,但是发现很容易被关闭退出,不能实现关闭最小化. 在网上了找了很久也使用了outlook on the desktop的插件,但是安装该插件后运行报错而弃用.最后找到了一个叫keepoutlookrunning的com 的加载项完美解决,下载地址:keepoutlookrunning. 安装方法:见百度文库 注意:改插件需要 "Microsoft Visual C++ 2010 可再发行组件包"的支持,如遇到安装时无法安装加载项时请先安装组件包,组件包下载地址 插

delphi程序最小化任务栏控件 托盘

unit MyTray; interface uses   Windows,Messages,SysUtils,Classes,Graphics,Controls, Forms,Dialogs,ShellApi,ExtCtrls,StdCtrls; const //自定义托盘消息   WM_TrayMsg=WM_USER+10; type //恢复窗口的方式,左双击,右双击,左单击,右双击   TRMode=(LDbClick,RDbClick,LCLick,RClick);   TMyTray

MFC程序最小化到托盘

1.在资源中的Icon中导入一个自己喜欢的图标,ID命名为IDR_MAINFRAME,将先前的IDR_MAINFRAME的图标删除掉: 2.在自己的Dialog头文件中定义一个变量  NOTIFYICONDATA m_nid,关于该结构体的具体信息可以查阅MSDN: 3.添加消息响应函数OnInitDialog(),并在该函数中添加以下代码,这样程序一启动,就在托盘中显示出了自己应用程序的图标. 1 //---------------------------托盘显示---------------

Centos程序最小化后,窗口标签都消失找不到窗口的问题

我是用的centos版本是CentOs 7. 在“顶部面板”或者 “底部面板” 右击选择“添加组件”),如下图所示: 在搜索框里输入“窗口列表”(window list),选中“窗口列表”即可.如下图所示: 当然同windows一样,也可以使用Alt+Tab组合键来切换最小化的窗口.