簡體   English   中英

Invalidate()自定義控件對每個屬性的更改?

[英]Invalidate() custom control on every property change?

我正在開發一個自定義的winforms控件,該控件公開了許多影響控件外觀的屬性(背景,文本和懸停,單擊以及圖標等不同狀態的不同顏色)。 對這些屬性之一的更改使得必須重新繪制,因此目前每個屬性都有一個getter和setter,該setter調用Invalidate() 這對代碼非常煩人,並且如果一次更改多個屬性,即使最后一個重繪就足夠了,但每個屬性都會導致重繪。

我有以下想法,但我不知道它們是否可行或如何實現:

  1. 緩存屬性更改幾毫秒,然后Invalidate()
  2. 使用某種反射來檢測調用方是否要在下一行中更改另一個屬性,如果是,則延遲對Invalidate()的調用
  3. 可能需要重繪的屬性之前有一些屬性,或者是所有此類屬性的列表,這些屬性在編譯時已擴展到getter / setter

如果這些想法有意義/可行,您能給我一些建議,並指出如何實施它們嗎?

請注意,我將遠離選項2。關於選項1,以某種方式,屬性更改已由系統緩存,只有UI線程返回到處理消息后,它才會重繪。 至於選項3,似乎有些牽連。

但是要回答您的問題,最簡單的方法是在您的班級中創建一個在給定時間間隔觸發的計時器。 然后使用bool,如果為true,則計時器的Tick處理程序將調用Invalidate()並將其設置回false。 最后,制作一個將代替Invalidate的方法,該方法會將布爾值標記為true。

在您的情況下,可能存在一些我不知道的危險,但這是一個示例:

public class InvalidationUserControl : UserControl
{
   bool _isInvalid = false;
   int _data;
   Timer t = new Timer();

   public InvalidationUserControl()
   {
      InitializeComponent();
      t.Interval = 100;  // Go ahead an play with this number, the higher
                         // it is the greater the latency
      t.Tick += t_Tick;
      t.Start();
   }

   void InvalidateIfNeeded()
   {
      _isInvalid = true;
   }

   void t_Tick(object sender, EventArgs e)
   {
      if (_isInvalid)
      {
          _isInvalid = false;
          Invalidate();
      }
   }

   public int Data
   {
       get { return _data; }
       set
       {
           _data = value;
           InvalidateIfNeeded();
       }
   }
}

可能會有更好的方法,但這是一種快速的解決方案,可以完全按照您需要的方式工作。

您所要做的就是調用InvalidateIfNeeded()而不是Invalidate(),它應該可以工作。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM