首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 相關知識

Delphi 判斷程序 30 秒無鍵盤鼠標操作自動關閉實現

     編輯:PHP 相關知識

Delphi 應用需實現「無操作超時自動退出」功能。核心思路:**應用級消息鉤子**攔截 `WM_MOUSEMOVE`、`WM_KEYDOWN` 重置計時器,`TTimer` 定期檢查超時並調用 `Close`。本文提供完整單元代碼、關鍵點解析、多表單/MDI 擴展建議。

完整單元代碼 (Unit1.pas)

unit Unit1;

interface

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

type
  TForm1 = class(TForm)
    Memo1: TMemo;
    Button1: TButton;
    Timer1: TTimer;
    procedure Timer1Timer(Sender: TObject);
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    procedure AppMessageHandler(var Msg: TMsg; var Handled: Boolean);
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

{ TForm1 }

// 應用級消息處理器:捕獲鼠標移動、鍵盤按下
procedure TForm1.AppMessageHandler(var Msg: TMsg; var Handled: Boolean);
begin
  if (Msg.message = WM_MOUSEMOVE) or (Msg.message = WM_KEYDOWN) then
    Timer1.Tag := 0; // 重置空閒計數
end;

// 定時器事件:每秒檢查
procedure TForm1.Timer1Timer(Sender: TObject);
begin
  Timer1.Tag := Timer1.Tag + 1; // Tag 用作秒計數器
  if Timer1.Tag >= 30 then      // 超過 30 秒
    Close;                      // 關閉主窗體 → 應用退出
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
  Close; // 手動關閉按鈕
end;

end.

關鍵實現細節

  1. Application.OnMessage:在項目源碼 (`.dpr`) 或主窗體 `OnCreate` 中註冊:
    Application.OnMessage := Form1.AppMessageHandler;
    這使主窗體能攔截**全應用範圍**的鼠標/鍵盤消息,不僅限於當前表單。
  2. Timer1.Interval = 1000:設計時屬性設置為 1000 毫秒 (1 秒)。
  3. Timer1.Tag:利用組件 `Tag` 屬性存儲空閒秒數,避免額外變量。
  4. 消息過濾:僅處理 `WM_MOUSEMOVE` (鼠標移動) 和 `WM_KEYDOWN` (鍵盤按下)。如需包含點擊,加 `WM_LBUTTONDOWN`、`WM_RBUTTONDOWN`。
  5. Close vs Application.Terminate:`Close` 觸發 `OnClose`/`OnCloseQuery`,允許用戶取消;若需強制退出用 `Application.Terminate`。

項目源碼註冊示例 (Project1.dpr)

program Project1;

uses
  Forms,
  Unit1 in 'Unit1.pas' {Form1};

{$R *.res}

begin
  Application.Initialize;
  Application.MainFormOnTaskbar := True;
  Application.CreateForm(TForm1, Form1);
  // 關鍵:註冊應用消息鉤子
  Application.OnMessage := Form1.AppMessageHandler;
  Application.Run;
end.

擴展:多表單 / MDI 應用

  • 消息鉤子註冊在 **主窗體** 或 **Application** 級別,自動覆蓋所有子窗體。
  • 若有模態對話框 (`ShowModal`),消息泵被阻塞,計時器不會運行,超時邏輯暫停 —— 符合預期 (用戶正在操作對話框)。
  • 若需在模態框也生效,需在對話框單元同樣註冊 `Application.OnMessage` 或使用全局鉤子 (`SetWindowsHookEx`)。

現代替代:Windows 系統級空閒檢測

uses Winapi.Windows;

function GetIdleTime: DWORD;
var
  li: TLastInputInfo;
begin
  li.cbSize := SizeOf(TLastInputInfo);
  if GetLastInputInfo(li) then
    Result := GetTickCount - li.dwTime
  else
    Result := 0;
end;

// 定時器中調用
if GetIdleTime >= 30000 then Close;

優點:系統級、跨進程、不依賴消息鉤子、更準確 (包含所有輸入設備)。缺點:需 Vista+,無法區分「本應用」與「其它應用」的操作。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved