我有一个表SampleData,它有一个子表,Measurements。在我的WinForm,frmMain上,一个SampleData对象绑定到SampleDataBindingSource; MeasurementsBindingSource将SampleDataBindingSource作为其数据源,将Measurements作为其DataMember。一组文本框绑定到SampleDataBindingSource; datagridview绑定到MeasurementsBindingSource。
对于frmMain,我还有一个presen类,preMain,它包含一个SampleData类型的属性CurrentSample。 SampleDataBindingSource.DataSource
绑定到preMain的CurrentSample属性。
当分配了测量中的足够属性时,它会计算FiringFactor,如果FiringFactor不是1,它会将另一个Measurement项添加到CurrentSample的Measurement实体集中:
Partial Class Measurement
Private Sub UpdateFiringFactor()
Dim necessaryDataIsAvailable As Boolean = (Me.CrucibleMass IsNot Nothing And _
Me.CrucibleSampleFiredMass IsNot Nothing And _
Me.CrucibleSampleMass IsNot Nothing)
If necessaryDataIsAvailable Then
Me.FiringFactor = CDbl((Me.CrucibleSampleFiredMass - Me.CrucibleMass) / (Me.CrucibleSampleMass - Me.CrucibleMass))
If Me.FiringFactor <> 1 Then
Me.SampleData.AddNewMeasurement()
End If
End If
End Sub
Private Sub OnCrucibleMassChanged()
UpdateFiringFactor()
End Sub
Private Sub OnCrucibleSampleFiredMassChanged()
UpdateFiringFactor()
End Sub
Private Sub OnCrucibleSampleMassChanged()
UpdateFiringFactor()
End Sub
End Class
当我在datagridview中输入CrucibleMass,CrucibleSampleMass和CrucibleSampleFiredMass的值时,UpdateFiringFactor方法确实正确运行,我最终将另一个Measurement项添加到CurrentSample的Measurements实体集中。但是,datagridview不显示新行,MeasurementsBindingSource只有1条记录(但CurrentSample.Measurements.Count = 2
)。
为什么CurrentSample.Measurements
中的更改不会传播到MeasurementsBindingSource
?我尝试了MeasurementsBindingSource.ResetBindings(False)
,MeasurementsDataGridView.Refresh
,SampleDataBindingSource.ResetBindings(False)
,但似乎没有更新MeasurementsBindingSource
或其datagridview。
答案 0 :(得分:0)
这是我在entityset / bindingsource问题中找到的解决方案:
Imports System.ComponentModel
Partial Class Measurement
Public Sub ChangeCrucibleMass(ByVal thisMass As Double)
CrucibleMass = thisMass
UpdateFiringFactor()
End Sub
Public Sub ChangeCrucibleSampleMass(ByVal thisMass As Double)
CrucibleSampleMass = thisMass
UpdateFiringFactor()
End Sub
Public Sub ChangeCrucibleSampleFiredMass(ByVal thisMass As Double)
CrucibleSampleFiredMass = thisMass
UpdateFiringFactor()
End Sub
Private Sub UpdateFiringFactor()
If AllDataAreAvailable() Then
FiringFactor = (CrucibleSampleFiredMass - CrucibleMass) / (CrucibleSampleMass - CrucibleMass)
Me.Sample.OnMeasurementsChanged(Nothing, Nothing)
End If
End Sub
Private Function AllDataAreAvailable() As Boolean
AllDataAreAvailable = False
Dim allFieldsHaveValue As Boolean = (CrucibleMass IsNot Nothing And CrucibleSampleFiredMass IsNot Nothing And CrucibleSampleMass IsNot Nothing)
If allFieldsHaveValue Then
Dim denominatorIsNotZero As Boolean = (CrucibleSampleMass - CrucibleMass) <> 0
Return denominatorIsNotZero
End If
End Function
End Class
Partial Class Sample
Public Sub OnMeasurementsChanged(ByVal sender As Object, ByVal e As System.ComponentModel.PropertyChangedEventArgs) Handles Me.PropertyChanged
If Me.Measurements.Count > 0 AndAlso Me.Measurements.Last.FiringFactor IsNot Nothing AndAlso Me.Measurements.Last.FiringFactor <> 1 Then
Me.Measurements.Add(New Measurement With {.CrucibleMass = Me.Measurements.Last.CrucibleMass})
RaiseEvent RefreshMeasurementsBinding()
End If
End Sub
Private Sub OnCreated()
Me.Measurements.Add(New Measurement)
End Sub
Public Event RefreshMeasurementsBinding()
End Class
以下是表单的截图:
代码隐藏:
Imports System.ComponentModel
Public Class Form1
Private WithEvents newSample As Sample
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
newSample = SampleConduit.GetSample(1)
'newSample = New Sample
Me.SampleBindingSource.DataSource = newSample
OnRefreshMeasurementsBinding()
End Sub
Private Sub OnRefreshMeasurementsBinding() Handles newSample.RefreshMeasurementsBinding
Me.MeasurementsBindingSource.DataSource = newSample.Measurements.GetNewBindingList
End Sub
Private Sub MeasurmentsDataGridView_CellClick(ByVal sender As Object, ByVal e As System.Windows.Forms.DataGridViewCellEventArgs) Handles MeasurmentsDataGridView.CellClick
Me.MeasurementsBindingSource.EndEdit()
Dim currentMeasurement = CType(Me.MeasurementsBindingSource.Current, Measurement)
Select Case e.ColumnIndex
Case 0
currentMeasurement.ChangeCrucibleMass(GetMeasurement)
Case 1
currentMeasurement.ChangeCrucibleSampleMass(GetMeasurement)
Case 2
currentMeasurement.ChangeCrucibleSampleFiredMass(GetMeasurement)
End Select
End Sub
Private Function GetMeasurement() As Double
Return CDbl(InputBox("Measurement:", "Get Measurement", "0"))
End Function
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnSave.Click
Dim currentSample = CType(Me.SampleBindingSource.Current, Sample)
SampleConduit.SaveSample(currentSample)
End Sub
End Class
解决方案取决于Sample类中的RefreshMeasurementsBinding事件和表单中的OnRefreshMeasurementsBinding方法。经常将MeasurementsBindingSource设置为Measurements实体集上的GetNewBindingList方法似乎有些麻烦,但它可以工作。
在此论坛帖子中查看关于EntitySets和BindingSource以及GetNewBindingList的第3项: