有沒有在C#中檢查對象是否掛起的方法?我有一個TreeView,我需要知道它是否仍然掛起。檢查掛起佈局
myTreeView.BeginUpdate();
myTreeView.SuspendLayout();
// Do Stuff.
myTreeView.EndUpdate();
myTreeView.ResumeLayout();
因爲我有這個代碼遞歸函數我想知道如果TreeView已被暫停。
有沒有在C#中檢查對象是否掛起的方法?我有一個TreeView,我需要知道它是否仍然掛起。檢查掛起佈局
myTreeView.BeginUpdate();
myTreeView.SuspendLayout();
// Do Stuff.
myTreeView.EndUpdate();
myTreeView.ResumeLayout();
因爲我有這個代碼遞歸函數我想知道如果TreeView已被暫停。
從verminity的答案繼你有一個選項:
使用下面的類,你需要將其掛起
public class SuspendAwareTreeView : TreeView
{
public readonly T RealControl;
private int suspendCount;
public bool IsSuspended
{
get { return suspendCount > 0; }
}
public Suspendable(T real) { this.RealControl = real; }
public void SuspendLayout()
{
this.suspendCount++;
this.RealControl.SuspendLayout();
}
public void ResumeLayout()
{
this.RealControl.ResumeLayout();
this.suspendCount--;
}
}
然後使用這個類的一切內部。
顯然這不會工作,如果你曾經將類傳遞給僅僅期望控件或者其他控件以外的東西來設置它。
如果這是你將被迫去與各種不到愉快的解決方案的情況下:
對於您的需求當且僅當你控制這個完全運行在運行時版本(即受控企業環境)以下邪惡但有效的破解是合適的。只要你測試任何時候你升級它可能會繼續努力工作。
public class ControlInvader
{
private static readonly System.Reflection.FieldInfo layoutSuspendCount =
typeof(Control).GetField("layoutSuspendCount",
System.Reflection.BindingFlags.Instance |
System.Reflection.BindingFlags.NonPublic);
private readonly Control control;
public bool IsSuspended
{
get
{
return 0 != (byte)layoutSuspendCount.GetValue(this.control);
}
}
public Suspendable(Control control) { this.control = control; }
}
將此附加到您的TreeView,然後您可以隨時檢查該值。
重申這是脆弱並且完全不適合的環境,其中底層運行時的版本沒有嚴格控制,並且您可以在這裏處理可能的重大努力以解決這個突變問題。 你會很好地包含一個靜態初始化程序,該初始化程序檢查該字段是否實際存在並且是正確的類型,如果不是,則會中止。
就讓我們來看看在Reflector在從Control的SuspendLayout方法顯示如下:
public void SuspendLayout()
{
this.layoutSuspendCount = (byte) (this.layoutSuspendCount + 1);
if (this.layoutSuspendCount == 1)
{
this.OnLayoutSuspended();
}
}
因爲它不設置任何公開的標誌,和OnLayoutSuspended()方法是內部無論如何都不知道控制權何時被暫停。
您可以使用新的Suspend和ResumeLayout方法創建樹視圖的子類,但由於基本方法不是虛擬的,因此很難保證它們在所有情況下都會被調用。
爲什麼你不能使用反射來獲得layoutSuspendCount成員? – 2009-04-23 04:21:19
好吧,這是一種遲到的回答,但在內部,控制器正在跟蹤計數,並且只會在最簡歷語句中恢復。那麼,爲什麼你在第一時間關心它,你只要確保你叫暫停,並在finally塊恢復它:
void Recursive(Control c)
{
c.SuspendLayout();
try
{
if (existCondition) return;
// do stuff
Recursive(c);
}
finally
{
c.ResumeLayout(true);
}
}
這工作,因爲下面是如何控制內部反應您的通話以下順序:
c.SuspendLayout() // 1st call suspends layout
c.SuspendLayout() // 2nd and subsequent call only increase the count and does nothing.
....
c.ResumeLayout(true) // this decrease the count to 1 and does NOT actually resumes layout.
c.ResumeLayout(true) // this set the count to 0 and REALLY resumes layout.
HTH
目前尚不清楚你的意思是什麼 「暫停」。 – 2009-04-22 14:38:20
我會標記這個來表示你正在使用什麼類庫... WinForms或者WPF。 – 2009-04-22 15:13:08