程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> 更多編程語言 >> Delphi >> WindowSubClassing之另類運用(之一)

WindowSubClassing之另類運用(之一)

編輯:Delphi

 

Window SubClassing之另類運用(之一)

 

所謂Window SubClassing,中文通常譯為窗口子類化,簡單說來就是截獲並處理窗口過程的技術。可能很多程序員都已經了解這項技術,並且或多或少在自己的程序中使用過它。在微軟的MFC類庫中就大量使用了Window SubClassing方法,以至於有人說“MFC is about Subclassing”。即使你沒有用過,至少你也應該聽說過它。所謂另類,有不循常理、不拘一格的意思。我在這裡將要描述都可以說是一些“旁門左道”的應用,不過或許能夠讓你有耳目一新的感覺。

 

我的第一個應用是所謂“延時自動關閉的對話框”。Windows中用來顯示信息的MessageBox函數非常簡單方便,但是它有一個致命的缺陷,就是除非用戶按下某個按鈕,否則整個程序的執行都會掛起。這對於無人值守的自動化程序來說是無論如何都不能接受的。如果是在比較依賴於時序的應用程序中(例如多線程程序或者基於定時器的應用),MessageBox還可能嚴重干擾整個程序的執行流程。為了解決這個問題,自己定義一個新的、能夠自動關閉的對話框當然是最直觀的做法,但是我發現這也是應用SubClass的一個好地方,因為我們並不需要在UI上花什麼功夫,唯一需要做的就是為對話框增加一條WM_TIMER的消息和對應的處理程序就行了。

 

想法雖然簡單,實現起來卻有一點小小的麻煩。首先指出一點:要實現SubClass,唯一的充分必要條件是我們需要獲得某個特定窗口的句柄。就是這個簡單的要求,對於MessageBox來說卻很棘手,因為它是一個模態對話框,窗口在調用MessageBox之後才建立,而在MessageBox返回的時候就已經撤銷了。我們如何獲得這個窗口呢?

 

這裡的關鍵在於,在調用MessageBox的同時,系統將把應用程序的主線程掛起,在MessageBox返回後才把控制權交還,所以我們沒有獲得這個窗口的機會。既然知道了症結所在,解決方案也就來了:主線程雖然掛起了,但是我可以使用子線程,看你能奈我何?

 

方法已經找到,接下來的實現可以說是勢如破竹了。首先,聲明必須的類型和變量:

type

  TWindowProc = function(AWnd:HWND; uMsg:UINT; wp:WPARAM; lp:LPARAM) : LongInt; stdcall;

 

var

  OldProc : TWindowProc = nil;

 

既然是SubClass,我們免不了要自己寫一個窗口過程。唯一需要處理的就是WM_TIMER       消息,在收到這個消息的時候關閉對話框即可:

function NewProc(AWnd:HWND; uMsg:UINT; wp:WPARAM; lp:LPARAM):LongInt;stdcall;

begin

  Result := 0;

  case uMsg of

    WM_TIMER:

      begin

        KillTimer(AWnd, 1);

        PostMessage(AWnd, WM_COMMAND, IDCANCEL, 0);

      end;

  end;

  if As

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved