我正在尝试在对象编辑期间使用 IsDirty 标志来控制 CanExecute 和 Navigational 控件。
问题是,为了使它工作,我认为我必须对我的 IsDirty 方法使用 onPropertyChanged,以便我的控件获得更改通知。(我希望在我的对象 IsDirty 时禁用某些控件)不幸的是,我得到了一个讨厌的堆栈溢出,因为它螺旋进入一个可怕的 IsDirty 循环......呵呵......
有没有人能够得到类似的东西来工作?我所做的只是在我的 OnPropertyChanged 方法中将 IsDirty 设置为 true。然后在我的 canExecute 方法中,我查看它是否设置为 true,但是在我的控件上,我需要将数据绑定到它……这导致了所有问题。
有谁知道如何实现这样的事情?
这是我的解决方案
:: 在 ViewModelBase 中
Private _isdirty As Boolean = False
Protected Property IsDirty As Boolean
Get
Return _isdirty
End Get
Set(ByVal value As Boolean)
If _isdirty = Not value Then
_isdirty = value
If _isdirty = True Then
DisableNavigation()
Else
EnableNavigation()
End If
End If
End Set
End Property
Private _haschanges As Boolean
Public Property HasChanges As Boolean
Get
Return _haschanges
End Get
Set(ByVal value As Boolean)
If value = Not _haschanges Then
_haschanges = value
OnPropertyChanged("HasChanges")
End If
End Set
End Property
Protected Sub EnableNavigation()
'Keep from firing multiple onPropertyChanged events
If HasChanges = True Then
HasChanges = False
End If
GetEvent(Of DisableNavigationEvent).Publish(False)
End Sub
Protected Sub DisableNavigation()
'Keep from firing multiple onPropertyChanged events
If HasChanges = False Then
HasChanges = True
End If
GetEvent(Of DisableNavigationEvent).Publish(True)
End Sub
::在派生自 ViewModelBase 的 EditViewModelBase 中。
Protected Overrides Sub OnPropertyChanged(ByVal strPropertyName As String)
MyBase.OnPropertyChanged(strPropertyName)
If SetsIsDirty(strPropertyName) Then
If isLoading = False Then
IsDirty = True
Else
IsDirty = False
End If
End If
End Sub
''' <summary>
''' Helps prevent stackoverflows by filtering what gets checked for isDirty
''' </summary>
''' <param name="str"></param>
''' <returns></returns>
''' <remarks></remarks>
Protected Function SetsIsDirty(ByVal str As String) As Boolean
If str = "CurrentVisualState" Then Return False
If str = "TabsEnabled" Then Return False
If str = "IsLoading" Then Return False
If str = "EnableOfficeSelection" Then Return False
Return True
End Function
:: 在我的视图模型中
Public ReadOnly Property SaveCommand() As ICommand
Get
If _cmdSave Is Nothing Then
_cmdSave = New RelayCommand(Of DoctorOffice)(AddressOf SaveExecute, Function() CanSaveExecute())
End If
Return _cmdSave
End Get
End Property
Private Function CanSaveExecute() As Boolean
'if the object is dirty you want to be able to save it.
Return IsDirty
End Function
Private Sub SaveExecute(ByVal param As DoctorOffice)
BeginWait()
GetService(Of Services.IDoctorOfficesService).Update(SelectedDoctorOffice, False)
EndWait()
End Sub