2011-12-21 17 views
1

我正在使用不支持mvvm意義上的綁定的圖表工具。所以我決定使用一種消息傳遞(比如MVVM Light的消息框架)服務,這樣每次viewmodel observablecollection被更新時,都會發送一條消息,當接收到的消息將數據點添加到圖表中時(這將會是在不幸的代碼背後)。你們看到這個計劃有什麼問題嗎?如何處理不支持綁定的圖表?

+0

Codebehind不是邪惡的,尤其是。當它關注這個觀點時。 – Will 2011-12-21 15:14:09

回答

1

我個人認爲消息對於你試圖達到的東西來說有點太過分了,儘管它的味道很重要。你不能使用適配器或附加的行爲模式?這就是他們通常用來替代缺失功能的原因。如果你可以在Xaml中實例化你的圖表(我希望你能這樣做),我建議使用附加的行爲,否則使用和apater(對於沒有公共構造函數或任何其他棘手東西的元素)並在代碼中實例化。

對於任何支持命令式呼叫的班級,只有您可以隨時提出補償行爲。這裏是一個簡單的例子:

代碼:

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Windows; 
using System.Windows.Controls; 
using System.Windows.Data; 
using System.Windows.Documents; 
using System.Windows.Input; 
using System.Windows.Media; 
using System.Windows.Media.Imaging; 
using System.Windows.Navigation; 
using System.Windows.Shapes; 

namespace WpfApplication1 
{ 
    /// <summary> 
    /// Interaction logic for MainWindow.xaml 
    /// </summary> 
    public partial class MainWindow : Window 
    { 
     public MainWindow() 
     { 
      InitializeComponent(); 
     } 

     public Dictionary<int, int> MyValues 
     { 
      get 
      { 
       return Enumerable.Range(1, 3).ToDictionary(k => k, v => v); 
      } 
     } 
    } 

    // component with the 'missing' property 
    public class Imperative : FrameworkElement 
    { 
     public void Add(int x, int y) 
     { 
      MessageBox.Show(string.Format("{0}_{1}", x, y)); 
     } 
    } 

    // compensating behavior 
    public class DeclarativeBehavior : DependencyObject 
    { 
     public static DependencyProperty MissingPropertyProperty = 
      DependencyProperty.RegisterAttached("MissingProperty", 
      typeof(Dictionary<int, int>), 
      typeof(DeclarativeBehavior), 
      new PropertyMetadata((o, e) => 
      { 
       // 
       Imperative imperative = (Imperative)o; 
       Dictionary<int, int> values = (Dictionary<int, int>)e.NewValue; 


       if (imperative != null) 
       { 
        foreach (KeyValuePair<int, int> value in values) 
        { 
         imperative.Add(value.Key, value.Value); 
        } 
       } 
      })); 

     public static void SetMissingProperty(DependencyObject o, Dictionary<int, int> e) 
     { 
      o.SetValue(DeclarativeBehavior.MissingPropertyProperty, e); 
     } 

     public static Dictionary<int, int> GetMissingProperty(DependencyObject o) 
     { 
      return (Dictionary<int, int>)o.GetValue(DeclarativeBehavior.MissingPropertyProperty); 
     } 
    } 
} 

XAML

<Window x:Class="WpfApplication1.MainWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:local="clr-namespace:WpfApplication1" 
     Title="MainWindow" Height="350" Width="525"> 
    <Grid> 
     <!--black box, which supports imperative calls is extended to support declarative calls too--> 
     <local:Imperative local:DeclarativeBehavior.MissingProperty="{Binding MyValues, 
      RelativeSource={RelativeSource AncestorType={x:Type Window}}}" /> 
    </Grid> 
</Window> 
+0

好的。我從來沒有聽說過附加的行爲模式。消息傳遞似乎是最容易實現的。讓我看看他們是如何工作的。謝謝。 – Aks 2011-12-21 13:57:22

+0

當你需要在WPF/SL中擴展'密封'時,這是一個方便的未來事件。 – 2011-12-21 14:01:39

0

你有沒有考慮使用的接口,以保持分離注入您的視圖到視圖模型?我知道這打破了MVVM,但我已經成功地在許多WPF項目中使用了它。我稱之爲MiVVM or Model Interface-to-View ViewModel

該模式很簡單。你的用戶控件應該有一個接口,稱它爲IView。然後在視圖模型,你有型IMyView的二傳手屬性,說

然後在視圖中創建一個名爲依賴屬性這

public MyUserControl : IMyView 
{ 
    public static readonly DependencyProperty ThisProperty = 
     DependencyProperty.Register("This", typeof(IMyView), typeof(MyUserControl)); 

    public MyUserControl() 
    { 
     SetValue(ThisProperty, this); 
    } 
    public IMyView This { get { return GetValue(ThisProperty); } set { /* do nothing */ } } 
} 

終於在XAML中,你可以注入查看直接進入視圖模型使用綁定

<MyUserControl This="{Binding InjectedView, Mode=OneWayToSource}"/> 

試試吧!我已經多次使用這個模式,並且在啓動時獲得了一次注入視圖的接口。這意味着你保持分離(可以測試Viewmodel,因爲IView可以被嘲笑),但是你可以避免許多第三方控件缺乏綁定支持。另外,它的速度很快。你知道綁定使用反射嗎?

最後,我實現了一個圖表控件,該控件使用此模式在支持MVVM的ABT Software Services上同時保持高性能的編程API。圖表組件被稱爲SciChart,它使用即時模式渲染和多個繪圖優化來爲科學/金融應用程序生成非常高性能的圖表。

在上面的博客鏈接中有一個演示項目展示了這種模式。如果您使用的是第三方控件,我會主張嘗試MiVVM的附加屬性實現。

相關問題