Click here to Skip to main content
Click here to Skip to main content

WPF Charting using MVVM Pattern

By , 19 Oct 2010
 

Introduction

There are tons of articles on the MVVM (Model-View-ViewModel) design pattern, and rightfully so. It's an easy pattern to understand (after you've studied it for a while) and it very nicely separates concerns. Where better to separate concerns than with a Chart and its data? This article shows you how to use the .NET Framework's (free) Datavisualization Chart component using the MVVM model.

Background

This sample was built using Visual Studio 2010 running .NET Framework 4.0. It also uses the WPF Toolkit version 3.5 which has the System.Windows.Controls.DataVisualization namespace. You can download this toolkit from Codeplex here. This solution is new to CodeProject as the previous examples of the DataVisualization namespace were either all for ASPX Charting or WinForms Charting. This particular project is for WPF and includes the entire current set of ChartTypes found in the Datavisualization Namespace.

Using the Code

The zip file for this article (minus the DataVisualization component) is an entire project that allows you to compile and run a sample of every chart type currently supported in WPF. Simply run the project in debug mode, once it comes up, just change the SeriesTypes as shown below on the left, to change the view. Notice below that the Title, Legend Title are also editable. This allows one to see how it was done and add other editable attributes to the Charting component.

ColumnSeries.png

Points of Interest

The View

Views in the MVVM pattern are just the markup in XAML needed for displaying content and style. Be careful when putting code function in the "code-behind" of the View. One typically wants to limit that code to View Only logic such as Animation. The content of the View is handled in the ViewModel via WPF Binding. The MainWindow ("Shell") XAML is shown below:

<Window
    x:Class="WPFCharting.Views.MainWindowView"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"          
    xmlns:cmd="clr-namespace:WPFCharting.Commands" 
    xmlns:ViewModels="clr-namespace:WPFCharting.ViewModels" 
    xmlns:Views="clr-namespace:WPFCharting.Views" 
    Title="MainWindowView" 
    MinHeight="400"
    MinWidth="800"
    Height="Auto" Width="Auto">
    <Window.Resources>
        <ViewModels:MainWindowVM x:Key="VM"></ViewModels:MainWindowVM>
        <cmd:ShowAlterData x:Key="SAD"></cmd:ShowAlterData>
    </Window.Resources>
    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="21*"></ColumnDefinition>
            <ColumnDefinition Width="80*"></ColumnDefinition>
        </Grid.ColumnDefinitions>
        <Border Padding="2" >
            <Border.Background>
                <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,.7">
                    <GradientStop Color="White" Offset="0" />
                    <GradientStop Color="Black" Offset="1" />
                </LinearGradientBrush>
            </Border.Background>
            <Border Padding="1" >
                <Border.Background>
                    <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
                        <GradientStop Color="Black" Offset="0" />
                        <GradientStop Color="White" Offset="1" />
                    </LinearGradientBrush>
                </Border.Background>
                <StackPanel Grid.Column="0" Margin="5,5,5,0" 
                    DataContext="{Binding Source={StaticResource VM}}">
                    <StackPanel.Background>
                        <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
                            <GradientStop Color="Black" Offset="0" />
                            <GradientStop Color="White" Offset="1" />
                        </LinearGradientBrush>
                    </StackPanel.Background>
                    <Views:UcTitle x:Name="XTitle" ></Views:UcTitle>
                    <Views:UcLegendTitle x:Name="XLegendTitle"/>
                    <Views:UcSeriesTitle x:Name="XSeriesTitle" />
                    <Views:UcSeriesTypes x:Name="XSeriesTypes"/>
                    <Border Padding="2,5,2,5" Background="Black">
                        <StackPanel>
                            <Label Foreground="LightBlue" 
				HorizontalContentAlignment="Center">Edit</Label>
                            <Button Command="{Binding Source={StaticResource SAD}}">
				Show/Alter Data</Button>
                            <Button>Reset To Original</Button>
                        </StackPanel>
                    </Border>
                </StackPanel>
            </Border>
        </Border>
        <ContentControl  Grid.Column="1" 
            DataContext="{Binding Source={StaticResource VM}}" 
            Content="{Binding Source={StaticResource VM}, Path=MainChart}" />
    </Grid>
    <Window.Background>
        <LinearGradientBrush EndPoint="1,0.5" StartPoint="0,0.5">
            <GradientStop Color="Black" Offset="0.016" />
            <GradientStop Color="White" Offset="0" />
            <GradientStop Color="Black" Offset="0.205" />
            <GradientStop Color="Black" Offset="0.079" />
            <GradientStop Color="White" Offset="0.212" />
        </LinearGradientBrush>
    </Window.Background>
</Window>

Notice there's really not much there, as it is really just a "Shell". There are just two "ContentControls" in the Shell, one is the StackPanel containing the Left side Editing UserControls and the other is the Content Control which "houses" the charts. One note of interest here is that the DataContext of the ChartControl had to be set explicitly as shown (as well as the Content and the Path) statements. Setting the DataContext anywhere else in this project failed. For example, it didn't work in the Grid. Perhaps I misspelled something, but it worked in the ContentControl so I left it there.

The ViewModel which contains (among other things) property getters and setters has a number of private/public properties which are for the WPF MainWindow (Shell). The call to PropChanged is how the ViewModel notifies the View. Those property getters/setters take on a look like this:

  private ContentControl _mainChart;
        /// <summary>
        /// When swapping ChartTypes this is the content which is injected to view
        /// </summary>
        public ContentControl MainChart {
            get { return _mainChart; }
            set {
                PreviousViewList.Add(_mainChart);
                _mainChart = value;
                PropChanged("MainChart");            
            } 
        }

So in the code above, we see the "pattern" of MVVM property "getters/setters". The private variable encapsulates the public get and set methods, the set method will then update the private variable and call PropChanged.

One question that arises is, how do we boot up a MVVM application. In this solution, you will find it being done in the App.cs file using this code:

public partial class App : Application
{
  protected override void OnStartup(StartupEventArgs e)
  {
    MainWindow mw = new MainWindow();
    mw.Show();
 }

The OnStartup event is overridden and the MainWindow is instantiated and shown. From there, the Main Window will instantiate the MainWindowViewModel as shown next. The MainWindow is shown, but how do we start the MainWindowViewModel?

In the MainWindow, we see the MainWindowViewModel's class instantiation happening via XAML. This is done in the Window.Resouces section of the MainWindow.Xaml file. The MVVM pattern states "The View knows the View-Model, and the View-Model knows the Model".

<Window.Resources>
<local:MainWindowVM x:Key="VM"></local:MainWindowVM>
</Window.Resources>

Note however that Binding between the View and the Viewmodel is done via the WPF Binding system so that when a project is run, the getter methods are called at View.Show() time. It (the ViewModel) then becomes a static object, which the charting Series UserControls (of this project) use to bind data. We gave it a name of "VM" for View Model as shown above.

Static Resources and WPF Binding is not a topic for this article; however, it pays to know how they work because certain aspects of the MVVM pattern use XAML based resources as shown above. You can read these articles on MVVM Resources.

Ahh! And now for the Markup that controls which type of ChartSeries is shown. Each of the UserControls in this project represent a different ChartView (Such as this Area control User Control). For Charting, a chart markup in XAML can contain a type of Chart Series. In this case (see Markup below), the PieSeries chart type is shown. NOTE: What is lacking in the Charting Framework; however, is an Generic Series object of which to bind to at design time. For example, there is no ChartingToolKit:Series generic type which would allow chart series types to be injected at run time changing the views of data. So as an alternative to this limitation, this project has 1 UserControl per chart type. This was the only way known to the author to do this in XAML.

<chartingToolkit:LineSeriesx:Name="XPieSeries"
DataContext="{Binding}"
DependentValueBinding="{Binding Path=Value}"
IndependentValueBinding="{Binding Path=Key}"
ItemsSource="{Binding Path=data}"/>

If you are experimenting with Chart Series types (see XAML above), make sure to set up the Dependent and Independent Value Bindings to the correct Paths. This author lost a considerable amount of time with charts not showing up simply because the Value, and Key paths were bound to the wrong Axis. Notice also the generic Binding being used, there is no Source specified in these UserControls. This is due to WPFs nice DataContext inheritance effect. The MainWindowView sets the DataContext, so no explicit DataContext statements are needed in these UserControls which inherit this DataContext.

In the most current iteration of this project, there are 7 different UserControls found in the Views folders which are used to swap the content of the MainWindow Shell. These UserControls are the charttype implementations e.g. BarSeries, PieSeries, ColumnSeries, etc. Driven by the command pattern of the MVVM architecture, each of these classes use a static getInstance() getter, setter method to ensure the fastest possible swapping of the Chart Views.

You will find the implementation of the Command to swap the views in the Command folder. It is just a wrapper class invokable from the MainWindow View. This class "ShowSeries" is simply a select statement that gets the current instance of the Charttype. It then injects the Chart view into the MainWindow. While this is not a formalized IOC or Dependency Injection pattern, it simulates the same thing. In particular, adding the concept of Singleton Pattern (getInstance) for the sake of speed. BTW you'll find these Views are able to be injected rather fast due to the Singleton getInstance method.

The View Model

So what's easier than using an ObservableCollection of something when working with WPF? It's a wrapper class made just for exposing data to the View. What's really nice is that it is a generic collection that allows you to define the type (to be displayed). These three lines of code is all you need to wire-up a Chart in the View Model. The code in the zip file will show you how to notify the WPF layer of any changes.

private ObservableCollection<KeyValuePair<string, int>> _data;
   public ObservableCollection<KeyValuePair<string,int>> data {
          get { return _data; }          
 }

The XAML above shows how the ViewModel delivers the data to the chart.

On the left hand side of the MainWindow, there is a "controller" that allows you to edit content within the Chart itself. It uses the ViewModel as does the UserControls (ChartTypes) to get and set the properties. This is an instance whereby multiple controls are all bound to the same ViewModel and demonstrates how the ViewModel can host separate concerns. Imagine a Webbrowser application that has navigation links on the left. The ViewModel can actually serve multiple ContentControls at the same time, without violating Separation of Concerns. However, keep in mind that the adage of "One Time and One Place" an "Each Object is responsible for itself" will guide you in determining how much is too much code within one class. This is why the Command interface is nice because it moves implementation out of the ViewModel. In this example, the Commands back-end the setter properties of the View Model.

The Model

Finally, we come to the point where we implement the Data Layer in the Model for the class. Nothing more than a concrete class of Observable collection of a KeyValuePair<string,int> type:

public class MainWindowModel : ObservableCollection<KeyValuePair<string, int>>
 {
    public MainWindowModel()
      {
          init();
       }
    public void init()
    {
        Add(new KeyValuePair<string, int>("Dog", 30));
        Add(new KeyValuePair<string, int>("Cat", 25));
        Add(new KeyValuePair<string, int>("Rat", 5));
        Add(new KeyValuePair<string, int>("Hampster", 8));
        Add(new KeyValuePair<string, int>("Rabbit", 12));
     }
     public ObservableCollection<KeyValuePair<string, int>> getData()
     {
        return this;
        }
    }

Voila! That's all there is to this. Now imagine that you want to have SQL Connections or XML Readers providing content. As you can see, you have many options. You can create new methods within this class above, or you can create other back-end classes that update this class. The good news is that if you are able to follow this contract of a KeyValuePair<string,int> then the implementation is hidden from the View. You could have many different getData methods in this class.

History

  • 4th Update: Fixed Links in main article 10/19/2010
  • 3rd Update: Clarified the View's Code Behind Statement, added links to Browse Code. Clarified other content. 10/15/2010
  • 2nd Edition: Included all Chart Types, MVVM Commanding, View Injection as well as good examples of Binding, to show how to change content in a chart after it shows data. Lots of comments in the code. 10/12/2010 XZZ0195
  • Kenny Rogers and the 1st Edition: 10/12/2010 XZZ0195

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

About the Author

Mr. Javaman
Technical Writer
United States United States
Member
Mr Javaman

Sign Up to vote   Poor Excellent
Add a reason or comment to your vote: x
Votes of 3 or less require a comment

Comments and Discussions

 
You must Sign In to use this message board.
Search this forum  
    Spacing  Noise  Layout  Per page   
GeneralRe: WPF Chart animationmemberxzz01953 Aug '11 - 4:28 
The animation is a property of each series. It looks like this:
 
<chartingToolkit:AreaSeries
        x:Name="XAreaSeries"
        AnimationSequence="FirstToLast"
         DependentValuePath="Value"
         IndependentValuePath="Key"
         ItemsSource="{Binding Path=IntChartItems}" >

GeneralMy vote of 5groupSparkling_ouc18 Oct '10 - 21:42 
nice
GeneralMy vote of 3memberMaxim Maximov15 Oct '10 - 12:57 
aaa
GeneralMessage Removedmemberxzz019515 Oct '10 - 13:13 
Message Removed
GeneralRe: My vote of 3memberMaxim Maximov15 Oct '10 - 22:16 
The purpose of your article implies that you will demonstrate best practice. That begginner open your article and he will think that he will do it the same way. What's doing logic in View's codebehind? Is it really impossible to do it without commands? And open your code using ReSharper and see your codeSmile | :) .
GeneralRe: My vote of 3memberxzz019516 Oct '10 - 0:15 
The logic that I did place into the Codebehind was mentioned in the article as the Singleton pattern getInstance() static method. It is a cheap way to obtain, Inversion of Control for the usercontrol chart series injection into the Shell's MainWindow ContentControl. That is the only code in any View's code behind. I realize it is not best practice and mentioned the possibility of View Highjacking in the article. Please advise on what you would do, so I can investigate and implement.
 
I set the article at Beginner because they won't have to do anything for WPF charting other than to alter the data in the Model. That's pretty cool, I thought...
 
I have downloaded Resharper and look at the fine mess I most likely created and post back to you.
 
Thank you for your comments, I look forward to working with you.
GeneralRe: My vote of 3mvpPete O'Hanlon15 Oct '10 - 21:20 
Maxim - you have done yourself no favours here. When you vote 3, it means that you have a problem with the article. Now, common courtesy would dictate that you tell the author why you have a problem with the article so that they can rectify or clarify any issues. By providing such a useless comment, you have shown that you are incapable of coherent thought or making cogent articles. In short, you are a moronic buffoon, a paltroon of the lowest order, a pimple on the buttcheek of humanity.

I have CDO, it's OCD with the letters in the right order; just as they ruddy well should be

Forgive your enemies - it messes with their heads

My blog | My articles | MoXAML PowerToys | Onyx


GeneralCode has been scanned by Resharper...memberxzz019516 Oct '10 - 1:16 
Maxim;
 
The original Resharper scan found 312, I was able to get this count down to 9 issues. Note, I didn't necessarily agree with many of the suggestions but changed them anyway. I don't necessarialy feel that implicit variable declarations in place of strong typing is best. Comments?
 
It found a number of Unused Usings, this is a result mostly of VS2010 when you create new UserControls and Windows, does reducing the unused Usings help in any way?
 
It taught me about the ?? operator (never used it before). I will use it from here on out.
 
I'll upload new code next week (Monday).
 
BTW This is first time I've used Resharper, I tend to like it, but I can't stand how it adjusted my content menu... I want cut and copy menuitems where they were. Is there any way to adjust this? It did a fine job or renaming namespaces in both XAML and CodeBehind. It found a readonly issue that I thought was good. It seems to have slowed down VS2010 a bit when using it. But overall I like it. Is it worth $200.00?
 
Thanks for your post Maxim.
GeneralA "dangerous" statement.mvpPete O'Hanlon14 Oct '10 - 23:57 
"Views in the MVVM pattern are just the markup in XAML needed for displaying content and style. There should be no code-behind logic within the View as that is handled in the View-Model via WPF Binding."
 
This is an inaccurate statement, and one that could trip up a newbie to MVVM. There are plenty of occasions where the view should have code behind - far too many examples of MVVM have to take tortuous and complicated routes to trigger off something on a view from a VM, when this could be simply achieved in the view; typical examples would be complex transition effects.
 
A ViewModel exists solely for the purpose of providing logic for a view to "talk" to a model. It should not be made any more complex than it needs to be.
 
Apart from that, this is an interesting article. I'll award a 5 when you clarify the View statement.

I have CDO, it's OCD with the letters in the right order; just as they ruddy well should be

Forgive your enemies - it messes with their heads

My blog | My articles | MoXAML PowerToys | Onyx


GeneralRe: A "dangerous" statement. [modified]memberxzz019515 Oct '10 - 4:11 
Pete;
I too tripped on the no code behind design goal in my early MVVM days. I also tripped on the Relay Command pattern for the View Model per Josh Smith's excellent article on MVVM. As I kept studying this pattern, I realized (like we so often do as programmers), that this is only a recommendation and does not have to be strictly followed. I also found via frequent refactoring of work I've done in MVVM projects, that my refactoring brought me to slightly different conclusions than say the Relay Command.
 
For example, in Agile and good OOP/OOD the "Code once principal", "Separation of Concerns", and "Each object Responsible for itself" in my opinion, does not lend itself to packing the View Model with zillions of lines of code. In my early refactorings, I would actually put Button click events into Code behind of the View, it is absolutely the easiest thing to do, no question, but it violates "separation of concerns" if the support logic for what is done is included in the View's code behind. So from this perspective, (not liking the relay command pattern and the code behind solutions), Agile led me to say "Hey, there should be a Command Folder that supports only Commands", that way I could create a base command class that supported all commands and allowed me pretty much to only code up the Execute stuff. If you look at the last line of code, you'll see that the problem of updating the ViewModel was solved. But, this breaks OOP in that the View Model's getInstance() method is PUBLIC. It doesn't have to be there if I implement the event model, but for now it suffices for this project. Let's just say this project should be run in Secure locations only (as it stands now).
 
Back to the no code behind "suggestion", it is good for this reason: Testing. If the GUI is truly only GUI as this project demonstrates, then one can test all View Model and command objects on their own. This is a really powerful concept and a good goal for all programmers. In fact the ASP.NET MVC pattern pretty much says the same thing. In MVC you cannot put anything in Code Behind of View because there is no Code Behind file generated at all. One might ask how do I invoke commands (in WPF and Sliverlight)? The answer is best suggested by doing it at the control level (via the command attribute) within the XAML setting up a static resource that points to that command. We don't need the Relay logic, because to me, that's jumping through Hoops to set up a delegate just so the code can be executed in the View Model. It makes the View Model too much in my opinion. All for the sake of gaining internal access to the Getter and Setters. For me, I'd rather maintain 10 lines of code rather than 110. If there's a problem with a command, one will just go to the command folder. If in WPF or Silverlight we want to Invoke a command, we just do it from the GUI in a loosely coupled way and allow the command to update the ViewModel. The delegate can be moved to the Command object instead of the View Model.
 
Lastly, the MVVM pattern is NOT the rule of the land, rather it's a pattern that can be tweaked to fit your needs. However, it didn't come about over-night, so if we follow their suggestions, we are tapping into all the endless hours of problems that were solved by it, without knowing the reasons why...That's the best part, we don't have to trip over all the maintainence issues this pattern solves if we try to "just accept it". Then again, that's not easy to do for us hyper-analyticals that want to know the reasons why.
 
Believe me, I spent quite a bit of time on this project investigating IOC, UNITY, PRISM, even WF 4.0. I wanted a UNITY/PRISM solution but found those frameworks will take me some ramp up time that I didn't have. This project, is a compromise on IOC in that the View injection is being handled in a "get 'er done" manner which does have some concerns. Yet, it works!!!!

modified on Friday, October 15, 2010 10:19 AM

GeneralRe: A "dangerous" statement.mvpPete O'Hanlon15 Oct '10 - 4:47 
You do know that I'm one of the main advocates for MVVM don't you? I know all the reasons you've listed, hell I've used them myself in the past. However, the testing argument falls down at the first hurdle here because I am talking about leaving view only code in the view. Josh Smith, the guru of MVVM, talks about this in his book on Avanced MVVM. Suppose you have a property that you want to use just to control a transition in a view - why write 100s of lines of VM code when you can write 3 lines of view code? It only applies to the view, so that's why it should stay there - there's a reason that the bit in the middle is called the ViewModel after all.
 
xzz0195 wrote:
Lastly, the MVVM pattern is NOT the rule of the land, rather it's a pattern that can be tweaked to fit your needs. However, it didn't come about over-night, so if we follow their suggestions, we are tapping into all the endless hours of problems that were solved by it, without knowing the reasons why...That's the best part, we don't have to trip over all the maintainence issues this pattern solves if we try to "just accept it". Then again, that's not easy to do for us hyper-analyticals that want to know the reasons why.

 
Again - check out who I am - I know this seems an arrogant statement, but I have spent many an hour locked in conversations with the likes of Sacha, Josh, Bill Kempf, Dan Vaughan, Karl Shifflett and all the other WPF Disciples. A lot of the things you are talking about were solved by the Disciples - of whom I am a member.
 
I'm sorry, but I'm going to have to vote 4 for your article, precisely because you are advocating something that will cause problems if somebody blindly follows it.

I have CDO, it's OCD with the letters in the right order; just as they ruddy well should be

Forgive your enemies - it messes with their heads

My blog | My articles | MoXAML PowerToys | Onyx


GeneralRe: A "dangerous" statement.memberxzz019515 Oct '10 - 5:48 
My apologies, Pete, I didn't know your credentials. Congratulations on the work you've done. I totally agree with you on "why write hundreds of lines when you can do it in 3." Didn't mean to advocate anything that will cause problems, rather I'd like to explore this further if you don't mind....
 
One of the big problems I encountered in early MVVM was indeed, View Transition. I read all types of articles on it. Where should it be done? What I saw, curiously was that there was not much out there on the subject. In Josh's article he clearly showed the App.cs files as the bootstapper and how to inject the View into the shell, but I never was able to see what best practice was on a Shell that had a left hand side navigator and an right hand side content page. My big problem was, if I had many Views that had their own Navigators how would those naviators interface with the Shell and the View being displayed at the same time? (Each View having it's own closely coupled Navigator)
 
My Solution:
I know (in this project and others I've done) I broke a rule on using the Singleton getInstance() pattern as you will see on all UserContols. I've even done this on The ViewModel and on some projects, the View. It gives me the flexibility to invoke a View injection as Unity would do, but with the Public method, it opened up the design for Highjacking. I agree with you that in a Navigator/Main Content Shell type solution, that the navigator button clicks definitely could have code behind to inject the view. I also believe it can all be done in the command object itself by simply moving the injection logic to the command using either static getters for the View or a Delgate call similar to Josh's RelayCommand. Agile refactoring brought me there. Put all commands in a Command Folder and use the Commanding support in XAML (2 lines of code) as a static reference to call them. Let the commands do the injection, this works nice because that model can inject both new navigators as well as main content from one place. Further refactoring of this injection methodoloy as seen in this project will no doubt lead me to Event base injection. I just haven't gotten there yet. Just like Josh's RelayCommand delegation, it's the same thing, just moved to the command itself.
 
Now as to your statement that no-code behind in View can lead to problems. First, I agree that View specific code, which can't be done in XAML (or even if it is preferred to be done in the code behind) is OK. However, you mentioned problems, I was wondering what problems do you know about as I'd like to consider them from an experienced MVVM'r rather than discover them myself. Also, what are your thoughts on ASP.MVC where they don't even allow code-behind pages?
 
Regards,
And Thank you for the dialog on this great subject of MVVM... I look forward to hearing more based on your experience.
GeneralRe: A "dangerous" statement.mvpPete O'Hanlon15 Oct '10 - 10:27 
xzz0195 wrote:
My big problem was, if I had many Views that had their own Navigators how would those naviators interface with the Shell and the View being displayed at the same time? (Each View having it's own closely coupled Navigator)

 
Ah yes - tight coupling - it's a sod. As a side thought, have you investigated the use of the Mediator pattern to help decouple views and navigators? It's a powerful tool in the arsenal.
 
xzz0195 wrote:
However, you mentioned problems, I was wondering what problems do you know about as I'd like to consider them from an experienced MVVM'r rather than discover them myself.

 
One problem that I've had in the past is where I have visuals that need to be updated, e.g. I've had animations that required code to manipulate them. Rather than delegating this task to a VM and having to inject the view into the VM somehow in order to get access to the animations, it's cleaner to do this in the view. Ultimately, it's only triggering visuals, so it can be visually tested.
 
Looking at ASP.NET MVC - it's a fine framework, but an important thing to remember is that MVC already has the concept of the mediator and the observer pattern built right into it (so circumventing a lot of issues).

I have CDO, it's OCD with the letters in the right order; just as they ruddy well should be

Forgive your enemies - it messes with their heads

My blog | My articles | MoXAML PowerToys | Onyx


GeneralRe: A "dangerous" statement.memberxzz019515 Oct '10 - 11:02 
I'll look into the mediatior again. I read about it but didn't commit to knowledge. Thanks for tip!
 
Yes I too have found that kicking off animations is so much easier (at times) in code behind of the View, and have done that a few times myself.
 
Regards and Thanks Again!
GeneralRe: A "dangerous" statement.mvpPete O'Hanlon15 Oct '10 - 11:11 
You're welcome. I look forward to reading more from you in the future.

I have CDO, it's OCD with the letters in the right order; just as they ruddy well should be

Forgive your enemies - it messes with their heads

My blog | My articles | MoXAML PowerToys | Onyx


GeneralArticle Content Adjusted to reflect Code Behind in View is OK.memberxzz019515 Oct '10 - 9:17 
Pete;
I've made a change to the article to reflect your advice! Thanks! The article now states that code in the View is ok in code-behind if that code is for that View only.
 
Thanks again! Smile | :)
GeneralRe: Article Content Adjusted to reflect Code Behind in View is OK.mvpPete O'Hanlon15 Oct '10 - 9:56 
Perfect. Vote adjusted.

I have CDO, it's OCD with the letters in the right order; just as they ruddy well should be

Forgive your enemies - it messes with their heads

My blog | My articles | MoXAML PowerToys | Onyx


GeneralMy vote of 5memberSlacker00714 Oct '10 - 8:57 
Awesome! Keep up the good work.
GeneralRe: My vote of 5memberxzz019515 Oct '10 - 4:21 
Thanks Slack.. Post back if you have any questions/suggestions.
GeneralMy vote of 5mvpNishant Sivakumar14 Oct '10 - 4:26 
Interesting stuff here Thumbs Up | :thumbsup:
GeneralRe: My vote of 5memberxzz019514 Oct '10 - 5:15 
Let me know if you have any questions on design or the internals of how this works, be glad to answer questions, make changes etc. Wink | ;)

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Permalink | Advertise | Privacy | Mobile
Web01 | 2.6.130516.1 | Last Updated 19 Oct 2010
Article Copyright 2010 by Mr. Javaman
Everything else Copyright © CodeProject, 1999-2013
Terms of Use
Layout: fixed | fluid