使用 WriteValue 手動綁定數據
如果我通過設置 DataSourceUpdateMode = Never 關閉綁定數據源的自動更新,然後使用按鈕更新整個批次(使用 binding.WriteValue),則會出現問題 - 即,僅更新第一個綁定控制項的數據源。所有其他控制項都重置為原始值。
這是因為噹噹前對象發生變化時(如上述WriteValue之後發生的情況),如果ControlUpdateMode = OnPropertyChange,那麼所有其他控制項都會重新從數據源中讀取該值。
避免這個問題的標準方法是什麼?
一種方法是從 BindingSource 派生一個類並添加一個 WriteAllValues 方法。此方法執行以下操作:
(1)對於每個Binding,保存ControlUpdateMode
(2) 對於每個Binding,設置ControlUpdateMode = Never
(3) 對於每個Binding,呼叫WriteValue方法
(4) 對於每個 Binding,將 ControlUpdateMode 重置為保存的值
(5) 對於每個Binding,如果ControlUpdateMode = OnPropertyChange,呼叫ReadValue方法。
你能看出這樣做有什麼問題嗎?
如果使用您自己的類,實現 IEditableObject 會解決問題嗎?
在我正在處理的另一個控制項中,我實現了自己的綁定。我解決這個問題的方法是使用以下程式碼。(我已經做到了最低限度,希望你能遵守!):
Private Shared ControlDoingExplicitUpdate As MyCustomControl = Nothing Private Sub UpdateDataSourceFromControl(ByVal item As Object, ByVal propertyName As String, ByVal value As Object) Dim p As PropertyDescriptor = Me.props(propertyName) Try ControlDoingExplicitUpdate = Me p.SetValue(item, value) Catch ex As Exception Throw Finally ControlDoingExplicitUpdate = Nothing End Try End Sub Private Sub DataBindingSource_CurrentItemChanged(ByVal sender As Object, ByVal e As System.EventArgs) If (ControlDoingExplicitUpdate IsNot Nothing) AndAlso (ControlDoingExplicitUpdate IsNot Me) Then Exit Sub Me.UpdateControlFromDataSource() 'Uses ReadValue End Sub因此,當呼叫 UpdateDataSourceFromControl 時,將為同一 BindingSource 中的所有其他控制項呼叫所有 CurrentItemChanged 事件。但是,由於設置了 ControlDoingExplicitUpdate,它們不會從數據源重新讀取值,除非它們恰好是進行更新的控制項。在所有這些事件完成後,ControlDoingExplicitUpdate 設置為 Nothing,以便恢復正常服務。
我希望你能關注這個,並且 - 再次 - 我問,你能看到這有什麼問題嗎?
我對錶格有類似的要求。在我的情況下,我只希望在點擊表單的“保存”按鈕時發生所有表單控制項的數據綁定。
我發現的最佳解決方案是將每個綁定的 DataSourceUpdateMode 設置為 OnValidation,然後將包含表單的 AutoValidate 屬性設置為 Disable。當您在窗體上的控制項之間更改焦點時,這可以防止綁定。然後在我的 Save 按鈕的 Click 事件中,我手動驗證表單的輸入,如果沒問題,呼叫表單的 ValidateChildren 方法來觸發綁定。
此方法還具有讓您完全控制如何驗證輸入的優勢。預設情況下,WinForms 不包含執行此操作的好方法。