全國最多中醫師線上諮詢網站-台灣中醫網
發文 回覆 瀏覽次數:2449
推到 Plurk!
推到 Facebook!

關於OnPaint()與各元件的關係疑問..

尚未結案
cc12345
一般會員


發表:32
回覆:35
積分:13
註冊:2005-01-24

發送簡訊給我
#1 引用回覆 回覆 發表時間:2005-02-16 11:22:05 IP:61.219.xxx.xxx 未訂閱
小弟目前開發的程式, 會在一個TTabSheet上放滿一個一個排列整齊的格子, 每個格子上都需要寫上一些文字,我的程式結構為Form上面放了一個TMyPageCtrl,TMyPageCtrl上放個TMyTabSheet,TMyTabSheet放一堆TPanelDraw.. 其中 TMyPageCtrl繼承自TPageControl, TMyTabSheet繼承自TTabSheet, TPanelDraw繼承自TPAnel. 現在問題是, 1. 當TPanelDraw需要重繪時, 它會收到WM_PAINT嗎? 我看Online Help裡頭的OnPaint,發現只有少數幾個元件具有OnPaint的event. 2. 是否有元件不會收到WM_PAINT, 那他們如何處理需要重繪的需要? 3. 為什麼Form的重繪機制是FormPaint(), PaintBox的是PaintBoxPaint(),而不需要攔截WM_PAINT? 謝謝大家 !
m8815010
版主


發表:99
回覆:372
積分:289
註冊:2003-11-13

發送簡訊給我
#2 引用回覆 回覆 發表時間:2005-02-16 11:44:31 IP:61.63.xxx.xxx 未訂閱
引言: 小弟目前開發的程式, 會在一個TTabSheet上放滿一個一個排列整齊的格子, 每個格子上都需要寫上一些文字,我的程式結構為Form上面放了一個TMyPageCtrl,TMyPageCtrl上放個TMyTabSheet,TMyTabSheet放一堆TPanelDraw.. 其中 TMyPageCtrl繼承自TPageControl, TMyTabSheet繼承自TTabSheet, TPanelDraw繼承自TPAnel. 現在問題是, 1. 當TPanelDraw需要重繪時, 它會收到WM_PAINT嗎? 我看Online Help裡頭的OnPaint,發現只有少數幾個元件具有OnPaint的event. 2. 是否有元件不會收到WM_PAINT, 那他們如何處理需要重繪的需要? 3. 為什麼Form的重繪機制是FormPaint(), PaintBox的是PaintBoxPaint(),而不需要攔截WM_PAINT? 謝謝大家 !
cc12345你好: > class="code"> In .h ~~ class TForm1 : public TForm { __published: // IDE-managed Components TPanel *Panel1; void __fastcall FormCreate(TObject *Sender); private: // User declarations TWndMethod OldPanelWndProc; void __fastcall PanelWndProc(TMessage& Message); public: // User declarations __fastcall TForm1(TComponent* Owner); }; //--------------------------------------------------------------------------- extern PACKAGE TForm1 *Form1; ~~ In .cpp ~~ TForm1 *Form1; int i=0; //--------------------------------------------------------------------------- __fastcall TForm1::TForm1(TComponent* Owner) : TForm(Owner) { OldPanelWndProc = Panel1->WindowProc; Panel1->WindowProc = PanelWndProc; } //--------------------------------------------------------------------------- void __fastcall TForm1::PanelWndProc(TMessage& Message) { OldPanelWndProc(Message); if (Message.Msg==WM_PAINT) this->Caption=IntToStr( i); } ~~ 上例,可以由i值的變化得知其實TPanel元件是有收到WM_PAINT訊息的!(當然例如TPanel被cover時,然後又被移開時)! 上述的訊息攔截方式並不唯一,以自已習慣就好,參著!
cc12345
一般會員


發表:32
回覆:35
積分:13
註冊:2005-01-24

發送簡訊給我
#3 引用回覆 回覆 發表時間:2005-02-16 12:09:04 IP:61.219.xxx.xxx 未訂閱
謝謝 m8815010兄, 1. 我試著在您的code加上一行, void __fastcall TForm1::PanelWndProc(TMessage& Message) { OldPanelWndProc(Message); if (Message.Msg==WM_PAINT) { this->Caption=IntToStr( i); Panel1->Caption=IntToStr( i); // 加這一行 } } 發現程式不停的跑, 數字會一直不斷的加, 為什麼Panel會不斷的收到WM_PAINT, 難道是因為每寫一次Caption就觸發一次? 如果是這樣的話, 是不是表示Panel其實是不適合用來畫文字? 2. 這個方法似乎是Form來通知Panel需要重劃了, 有沒有可能是由Panel來自行接收Window所發的重繪message,然後自行重劃一次就好了? 謝謝 !!
m8815010
版主


發表:99
回覆:372
積分:289
註冊:2003-11-13

發送簡訊給我
#4 引用回覆 回覆 發表時間:2005-02-16 13:45:01 IP:61.63.xxx.xxx 未訂閱
引言: 謝謝 m8815010兄, 1. 我試著在您的code加上一行, void __fastcall TForm1::PanelWndProc(TMessage& Message) { OldPanelWndProc(Message); if (Message.Msg==WM_PAINT) { this->Caption=IntToStr( i); Panel1->Caption=IntToStr( i); // 加這一行 } } 發現程式不停的跑, 數字會一直不斷的加, 為什麼Panel會不斷的收到WM_PAINT, 難道是因為每寫一次Caption就觸發一次? 如果是這樣的話, 是不是表示Panel其實是不適合用來畫文字? 2. 這個方法似乎是Form來通知Panel需要重劃了, 有沒有可能是由Panel來自行接收Window所發的重繪message,然後自行重劃一次就好了? 謝謝 !!
cc12345兄你好: 是這樣的,例如這一行: < class="code">Panel1->Caption="12345"; 當你執行這一行時,Panel1的caption會被重設成"12345",然而實際上底層的運作是Panel1元件重繪一次,所以重繪完後自然新的caption也就繪上去了!所以事實上Panel元件是這樣達成你的一個重設caption的指令!也就是說其實它收到一次WM_PAINT訊息,為了你這行指令! 所以說由於你多加了那一行,導至Panel元件一有收到WM_PAINT時,就會執行你加的那一行,而那一行又觸發另一個WM_PAINT訊息、……一直recursive下去! 所以它本身接收message並沒問題,是你加的那一行導至它這樣的運作了! 關於第二點,不管什麼元件,一定是收到一個WM_PAINT訊息,則執行一次重繪動作,因為windows世界是message trigger的! 至於訊息發送過程我的經驗是,user先造成了需要重繪的因,如你托了一個視窗把Panel物件蓋著,接著再移開這個視窗,造成Panel需要重繪!於是O.S.最先知道這件事,然後O.S.告訴你寫的Application,application再把WM_PAINT送給裏面的Panel元件,而元件收到訊息後,再依訊息的種類去做該做的事! 我的感覺,在builderc中,你要說是application送WM_PAINT給panel,或是說Form1(panel的父親)送給panelWM_PANIT都可以的! 反正重點就是元件收到WM_PAINT一次,才會repaint自已一次,系統也不會沒事狂送很多個WM_PAINT給它! 小小心得!
cc12345
一般會員


發表:32
回覆:35
積分:13
註冊:2005-01-24

發送簡訊給我
#5 引用回覆 回覆 發表時間:2005-02-16 18:39:24 IP:61.219.xxx.xxx 未訂閱
多謝 m8815010兄, 再請教一個問題, 我的程式結構為 Form -- --- PageControl -- --- TabSheet -- --- Panel 我在Panel上按下mouse, 可否攔到message ? 及其click時, 相對於Form or PageControl or TabSheet 任一parent的座標位置 ? 謝謝 !
m8815010
版主


發表:99
回覆:372
積分:289
註冊:2003-11-13

發送簡訊給我
#6 引用回覆 回覆 發表時間:2005-02-16 21:00:13 IP:203.73.xxx.xxx 未訂閱
引言: 多謝 m8815010兄, 再請教一個問題, 我的程式結構為 Form -- --- PageControl -- --- TabSheet -- --- Panel 我在Panel上按下mouse, 可否攔到message ? 及其click時, 相對於Form or PageControl or TabSheet 任一parent的座標位置 ? 謝謝 !
cc12345兄你好: 可以的,直接利用 class="code">ClientToScreen(); ScreenToClient(); All!
系統時間:2024-05-12 7:22:48
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!