翻譯|使用教程|編輯:龔雪|2021-11-15 10:03:21.883|閱讀 276 次
概述:DevExpress WinForm創建的應用程序可利用MVVM設計模式,本文主要為大家介紹這其中的第三種屬性依賴,歡迎下載最新版體驗!
# 界面/圖表報表/文檔/IDE等千款熱門軟控件火熱銷售中 >>
相關鏈接:
根據您綁定的屬性,存在以下三種可能的情況:
獲取工具下載 - DevExpress WinForm v21.2
屬性依賴是來自同一個ViewModel的兩個屬性之間的關系,當一個屬性發生變化時,另一個屬性會更新其值。
在“MVVM 最佳實踐”演示中,多個模塊演示了以下設置:
對于使用示例 UI 的每個演示模塊,將 View 元素綁定到 ViewModel 屬性的代碼都是相同的。
C#
mvvmContext.ViewModelType = typeof(MultViewModel); var fluentAPI = mvvmContext.OfType<MultViewModel>(); fluentAPI.SetBinding(editor1, e => e.EditValue, x => x.Operand1); fluentAPI.SetBinding(editor2, e => e.EditValue, x => x.Operand2); fluentAPI.SetBinding(resultLabel, l => l.Text, x => x.ResultText);
VB.NET
mvvmContext.ViewModelType = GetType(MultViewModel) Dim fluentAPI = mvvmContext.OfType(Of MultViewModel)() fluentAPI.SetBinding(editor1, Sub(e) e.EditValue, Sub(x) x.Operand1) fluentAPI.SetBinding(editor2, Sub(e) e.EditValue, Sub(x) x.Operand2) fluentAPI.SetBinding(resultLabel, Sub(l) l.Text, Sub(x) x.ResultText)
然而,屬性依賴在每個模塊中的聲明都不同。
OnPropertyChanged 方法
在POCO ViewModels中,您可以聲明OnXChanged方法,其中 X 是屬性名稱。 當相關屬性的值發生變化時,框架會調用這些方法。
C#
public class MultViewModel { public virtual int Operand1 { get; set; } public virtual int Operand2 { get; set; } public virtual int Result { get; set; } public virtual string ResultText { get; set; } protected void OnOperand1Changed() { UpdateResult(); } protected void OnOperand2Changed() { UpdateResult(); } protected void OnResultChanged() { UpdateResultText(); } void UpdateResult() { Result = Operand1 * Operand2; } void UpdateResultText() { ResultText = string.Format("The result is: {0:n0}", Result); } }
VB.NET
Public Class MultViewModel Public Overridable Property Operand1() As Integer Public Overridable Property Operand2() As Integer Public Overridable Property Result() As Integer Public Overridable Property ResultText() As String Protected Sub OnOperand1Changed() UpdateResult() End Sub Protected Sub OnOperand2Changed() UpdateResult() End Sub Protected Sub OnResultChanged() UpdateResultText() End Sub Private Sub UpdateResult() Result = Operand1 * Operand2 End Sub Private Sub UpdateResultText() ResultText = String.Format("The result is: {0:n0}", Result) End Sub End Class
自定義更新方法
如果您的更新方法未被稱為“On...Changed”,請使用 DevExpress.Mvvm.DataAnnotations.BindableProperty 屬性告訴框架它應該在屬性值更改時調用此方法。 在下面的代碼示例中,DevExpress.Mvvm.POCO.RaisePropertyChanged 是一個 DevExpress 擴展方法,它將更新通知發送到依賴屬性。
C#
public class SumViewModel { [BindableProperty(OnPropertyChangedMethodName = "NotifyResultAndResultTextChanged")] public virtual int Operand1 { get; set; } [BindableProperty(OnPropertyChangedMethodName = "NotifyResultAndResultTextChanged")] public virtual int Operand2 { get; set; } public int Result { get { return Operand1 + Operand2; } } public string ResultText { get { return string.Format("The result is: {0:n0}", Result); } } protected void NotifyResultAndResultTextChanged() { this.RaisePropertyChanged(x => x.Result); this.RaisePropertyChanged(x => x.ResultText); } }
VB.NET
Public Class SumViewModel <BindableProperty(OnPropertyChangedMethodName := "NotifyResultAndResultTextChanged")> Public Overridable Property Operand1() As Integer <BindableProperty(OnPropertyChangedMethodName := "NotifyResultAndResultTextChanged")> Public Overridable Property Operand2() As Integer Public ReadOnly Property Result() As Integer Get Return Operand1 + Operand2 End Get End Property Public ReadOnly Property ResultText() As String Get Return String.Format("The result is: {0:n0}", Result) End Get End Property Protected Sub NotifyResultAndResultTextChanged() Me.RaisePropertyChanged(Function(x) x.Result) Me.RaisePropertyChanged(Function(x) x.ResultText) End Sub End Class
依賴屬性
使用 DevExpress.Mvvm.DataAnnotations.DependsOnProperties 屬性標記依賴屬性。 請注意,與前面的示例不同,下面的代碼僅使用一個依賴項:“ResultText”取決于兩個“Operand”屬性,您不能使用此屬性創建鏈式依賴項。
C#
public class MultViewModelEx { public virtual int Operand1 { get; set; } public virtual int Operand2 { get; set; } [DependsOnProperties("Operand1", "Operand2")] public string ResultText { get { return string.Format("The result is: {0:n0}", Operand1 * Operand2); } } }
VB.NET
Public Class MultViewModelEx Public Overridable Property Operand1() As Integer Public Overridable Property Operand2() As Integer <DependsOnProperties("Operand1", "Operand2")> Public ReadOnly Property ResultText() As String Get Return String.Format("The result is: {0:n0}", Operand1 * Operand2) End Get End Property End Class
Metadata類
在這種方法中,您創建自定義更新方法并使用單獨的元數據類將屬性與這些方法鏈接起來。 如果 BindableProperty 屬性按名稱引用更新方法,則 OnPropertyChangedCall 方法使用 lambda 表達式來檢索方法。 重命名自定義更新方法時,元數據類顯示編譯錯誤。
C#
//View Model code [System.ComponentModel.DataAnnotations.MetadataType(typeof(Metadata))] public class SumViewModel_MetaPOCO { public virtual int Operand1 { get; set; } public virtual int Operand2 { get; set; } public virtual int Result { get; set; } public string ResultText { get { return string.Format("The result is: {0:n0}", Result); } } protected void NotifyResultAndResultTextChanged() { Result = Operand1 + Operand2; this.RaisePropertyChanged(x => x.Result); this.RaisePropertyChanged(x => x.ResultText); } //Metadata class public class Metadata : IMetadataProvider<SumViewModel_MetaPOCO> { void IMetadataProvider<SumViewModel_MetaPOCO>.BuildMetadata(MetadataBuilder<SumViewModel_MetaPOCO> builder) { builder.Property(x => x.Result) .DoNotMakeBindable(); builder.Property(x => x.Operand1). OnPropertyChangedCall(x => x.NotifyResultAndResultTextChanged()); builder.Property(x => x.Operand2). OnPropertyChangedCall(x => x.NotifyResultAndResultTextChanged()); } } }
VB.NET
<System.ComponentModel.DataAnnotations.MetadataType(GetType(Metadata))> Public Class SumViewModel_MetaPOCO Public Overridable Property Operand1() As Integer Public Overridable Property Operand2() As Integer Public Overridable Property Result() As Integer Public ReadOnly Property ResultText() As String Get Return String.Format("The result is: {0:n0}", Result) End Get End Property Protected Sub NotifyResultAndResultTextChanged() Result = Operand1 + Operand2 Me.RaisePropertyChanged(Function(x) x.Result) Me.RaisePropertyChanged(Function(x) x.ResultText) End Sub 'Metadata class Public Class Metadata Implements IMetadataProvider(Of SumViewModel_MetaPOCO) Private Sub IMetadataProviderGeneric_BuildMetadata(ByVal builder As MetadataBuilder(Of SumViewModel_MetaPOCO)) Implements IMetadataProvider(Of SumViewModel_MetaPOCO).BuildMetadata builder.Property(Function(x) x.Result).DoNotMakeBindable() builder.Property(Function(x) x.Operand1).OnPropertyChangedCall(Function(x) x.NotifyResultAndResultTextChanged()) builder.Property(Function(x) x.Operand2).OnPropertyChangedCall(Function(x) x.NotifyResultAndResultTextChanged()) End Sub End Class End Class
集合綁定
要使用數據源記錄填充多項目控件,請使用 SetItemsSourceBinding 方法。
C#
var fluentApi = mvvmContext1.OfType<ViewModelClass>(); fluentApi.SetItemsSourceBinding( Target ItemSelector, SourceSelector, MatchExpression, CreateExpression, DisposeExpression, ChangeExpression );
VB.NET
Dim fluentApi = mvvmContext1.OfType(Of ViewModelClass)() fluentApi.SetItemsSourceBinding(Target ItemSelector, SourceSelector, MatchExpression, CreateExpression, DisposeExpression, ChangeExpression)
在 MVVM 最佳實踐演示中,以下代碼使用自定義實體類的對象填充列表框。 SetBinding 方法將編輯器的 SelectedItem 屬性與檢索相應實體對象的 ViewModel SelectedEntity 屬性綁定。
C#
//View code mvvmContext.ViewModelType = typeof(ViewModel); var fluentApi = mvvmContext.OfType<ViewModel>(); fluentApi.SetItemsSourceBinding( listBox, lb => lb.Items, x => x.Entities, (item, entity) => object.Equals(item.Value, entity), entity => new ImageListBoxItem(entity), null, (item, entity) => { ((ImageListBoxItem)item).Description = entity.Text; } ); fluentApi.SetBinding(listBox, lb => lb.SelectedValue, x => x.SelectedEntity); //ViewModel code public class ViewModel { public virtual Entity SelectedEntity { get; set; } public virtual ObservableCollection<Entity> Entities { get; set;} protected void OnSelectedEntityChanged() { //"Remove" is a custom ViewModel method that deletes a selected entity this.RaiseCanExecuteChanged(x => x.Remove()); } protected void OnEntitiesChanged() { SelectedEntity = Entities.FirstOrDefault(); } } //Model code public class Entity { public Entity(int id) { this.ID = id; this.Text = "Entity " + id.ToString(); } public int ID { get; private set; } public string Text { get; set; } }
VB.NET
'View code mvvmContext.ViewModelType = GetType(ViewModel) Dim fluentApi = mvvmContext.OfType(Of ViewModel)() fluentApi.SetItemsSourceBinding( listBox, Function(lb) lb.Items, Function(x) x.Entities, Function(item, entity) Object.Equals(item.Value, entity), Function(entity) New ImageListBoxItem(entity), Nothing, Function(item, entity) CType(item, ImageListBoxItem).Description = entity.Text ) fluentApi.SetBinding(listBox, Function(lb) lb.SelectedValue, Function(x) x.SelectedEntity) 'ViewModel code Public Class ViewModel Public Overridable Property SelectedEntity() As Entity Public Overridable Property Entities() As ObservableCollection(Of Entity) Protected Sub OnSelectedEntityChanged() '"Remove" is a custom ViewModel method that deletes a selected entity Me.RaiseCanExecuteChanged(Function(x) x.Remove()) End Sub Protected Sub OnEntitiesChanged() SelectedEntity = Entities.FirstOrDefault() End Sub End Class 'Model code Public Class Entity Public Sub New(ByVal id As Integer) Me.ID = id Me.Text = "Entity " & id.ToString() End Sub Private privateID As Integer Public Property ID() As Integer Get Return privateID End Get Private Set(ByVal value As Integer) privateID = value End Set End Property Public Property Text() As String End Class
觸發器
觸發器允許您在 ViewModel 屬性更改時修改 UI(視圖)。 在 DevExpress 演示中,復選框綁定到 ViewModel “IsActive”屬性。 當此屬性的值更改時,觸發器會更改 UI 元素(標簽)的背景顏色。
C#
//ViewModel code public class ViewModel { public virtual bool IsActive { get; set; } } //ViewModel code var fluent = mvvmContext.OfType<ViewModel>(); fluent.SetBinding(checkEdit, c => c.Checked, x => x.IsActive); fluent.SetTrigger(x => x.IsActive, (active) => { if(active) label.Appearance.BackColor = Color.LightPink; else label.Appearance.BackColor = Color.Empty; });
VB.NET
'ViewModel code Public Class ViewModel Public Overridable Property IsActive() As Boolean End Class 'ViewModel code Private fluent = mvvmContext.OfType(Of ViewModel)() fluent.SetBinding(checkEdit, Function(c) c.Checked, Function(x) x.IsActive) fluent.SetTrigger(Function(x) x.IsActive, Sub(active) If active Then label.Appearance.BackColor = Color.LightPink Else label.Appearance.BackColor = Color.Empty End If End Sub)
DevExpress WinForm擁有180+組件和UI庫,能為Windows Forms平臺創建具有影響力的業務解決方案。DevExpress WinForms能完美構建流暢、美觀且易于使用的應用程序,無論是Office風格的界面,還是分析處理大批量的業務數據,它都能輕松勝任!
更多產品正版授權詳情及優惠,歡迎咨詢
DevExpress技術交流群5:742234706 歡迎一起進群討論
本站文章除注明轉載外,均為本站原創或翻譯。歡迎任何形式的轉載,但請務必注明出處、不得修改原文相關鏈接,如果存在內容上的異議請郵件反饋至chenjj@fc6vip.cn
文章轉載自:慧都網