Delphi: сверните приложение к systray - PullRequest
2 голосов
/ 22 мая 2010

Я хочу свести приложение Delphi к системному каталогу вместо панели задач.

Необходимые шаги:

  1. Создать значок, который затем должен отображаться в системном окне.
  2. Когда пользователь нажимает [-], чтобы свернуть приложение, сделайте следующее:
    1. Скрыть форму.
    2. Добавьте значок (шаг # 1) в системный список.
    3. Скрыть / удалить запись приложения в панели задач.
  3. Когда пользователь дважды щелкает значок приложения в системном окне, сделайте следующее:
    1. Показать форму.
    2. Снова сверните приложение и выведите его на передний план.
    3. Если «WindowState» - это «WS_Minimized», то установить «WS_Normal».
    4. Скрыть / удалить значок приложения в системном окне.
  4. Когда пользователь закрывает приложение, сделайте следующее:
    1. Скрыть / удалить значок приложения в системном окне.

Вот и все. Правильно?

Как можно реализовать это в Delphi?

Я нашел следующий код, но не знаю, почему он работает. Это не следует моим шагам, описанным выше ...

unit uMinimizeToTray;

interface

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

const WM_NOTIFYICON = WM_USER+333; 

type
  TMinimizeToTray = class(TForm)
    procedure FormCreate(Sender: TObject);
    procedure FormClose(Sender: TObject; var Action: TCloseAction);
    procedure CMClickIcon(var msg: TMessage); message WM_NOTIFYICON;
  private
    { Private-Deklarationen }
  public
    { Public-Deklarationen }
  end;

var
  MinimizeToTray: TMinimizeToTray;

implementation

{$R *.dfm}

procedure TMinimizeToTray.CMClickIcon(var msg: TMessage);
begin
  if msg.lparam = WM_LBUTTONDBLCLK then Show;
end;

procedure TMinimizeToTray.FormCreate(Sender: TObject);
VAR tnid: TNotifyIconData;
    HMainIcon: HICON;
begin
  HMainIcon := LoadIcon(MainInstance, 'MAINICON');
  Shell_NotifyIcon(NIM_DELETE, @tnid);
  tnid.cbSize := sizeof(TNotifyIconData);
  tnid.Wnd := handle;
  tnid.uID := 123;
  tnid.uFlags := NIF_MESSAGE or NIF_ICON or NIF_TIP;
  tnid.uCallbackMessage := WM_NOTIFYICON;
  tnid.hIcon := HMainIcon;
  tnid.szTip := 'Tooltip';
  Shell_NotifyIcon(NIM_ADD, @tnid);
end;

procedure TMinimizeToTray.FormClose(Sender: TObject; var Action: TCloseAction);
begin
  Action := caNone;
  Hide;
end;

end.

Ответы [ 4 ]

5 голосов
/ 22 мая 2010

Если это все еще работает, вероятно, проще всего использовать JVCL TJvTrayIcon для автоматической обработки.

4 голосов
/ 22 мая 2010

Я бы порекомендовал использовать CoolTrayIcon. Автор уже проработал все вопросы, связанные с иконками в трее. Это бесплатно с источником и примерами и очень отлажен.

http://subsimple.com/delphi.asp

1 голос
/ 27 октября 2018

Вместо Application.BringToFront; используйте SetforegroundWindow(Application.Handle);

0 голосов
/ 24 мая 2010

В следующем тексте я буду ссылаться на номера шагов, упомянутые в вопросе:

Следующее решение без каких-либо дополнительных компонентов.Это очень просто реализовать.

Шаг # 1:

Просто используйте главный значок приложения (см. Следующий код).

Шаг# 2:

procedure TForm1.ApplicationEvents1Minimize(Sender: TObject);
begin
  Shell_NotifyIcon(NIM_ADD, @TrayIconData);
  Form1.Hide;
end;

Шаг № 3:

procedure TForm1.TrayMessage(var Msg: TMessage);
begin
  if Msg.lParam = WM_LBUTTONDOWN then begin
    Form1.Show;
    Form1.WindowState := wsNormal;
    Application.BringToFront;
    Shell_NotifyIcon(NIM_DELETE, @TrayIconData);
  end;
end;

Шаг № 4:

procedure TForm1.FormDestroy(Sender: TObject);
begin
  Shell_NotifyIcon(NIM_DELETE, @TrayIconData);
end;

Необходимый код в интерфейсной части:

uses
  [...], ShellApi;

const
  WM_ICONTRAY = WM_USER + 1;

type
  TForm1 = class(TForm)
    [...]
    procedure TrayMessage(var Msg: TMessage); message WM_ICONTRAY;
  end;

Единственная проблема: приложение может быть свернуто в systray только один раз.В следующий раз, когда вы захотите минимизировать это, ничего не произойдет.Почему?

Источник: delphi.about.com

...